0

状況:

「Country」ドロップダウン、「PostalCode」テキストフィールド、「City」テキストフィールドを含むフォーム。

国ドロップダウンには、ベルギーとフランスの 2 つの項目があります (有効値としてそれぞれ BE と FR の国コードがあります)。

「PostalCode」フィールドは CJuiAutoComplete フィールドであり、国のドロップダウンから選択された値に応じて、「BeCity/getBelgianPostalCodes」または「FrCity/getFrenchPostalCodes」からオートコンプリート データを取得する必要があります。

これら 2 つのアクションは、互いに独立して完全に機能し、正しいオートコンプリート データを生成します。ただし、国のドロップダウンで選択した値に基づいて動的に機能させる方法がわかりません。選択した国をセッション状態にして、そこから sourceUrl を動的に生成しようとしました。生成された html のソースを調べると、選択した国に応じて生成された sourceUrl は正しいですが、ロードされた最初の国から値を取得します。おそらく、キャッシングの問題か何かがありますか?

コードは次のとおりです。

形:

<div class="row">
        <?php echo $form->labelEx($model,'Country'); ?>
        <?php echo $form->dropDownList($model,
                        'CountryCode',
                        CHtml::listData(Country::model()->findAllByAttributes(array('Visible'=>1)),'Code','Name'),
                        array('ajax'=>array(
                              'type'=>'POST',
                              'url'=>CController::createUrl('request/setRequestCountryCode'),
                              'data'=>'js:{CountryCode: $(this).val()}'))
                        ); ?>
        <?php echo $form->error($model,'CountryCode'); ?>
    </div>

        <div class="row">
        <?php echo $form->labelEx($model,'PostalCode'); ?>
        <?php 

                $this->widget('zii.widgets.jui.CJuiAutoComplete', array(
                'name'=>'Request_PostalCode',
                'value'=>$model->PostalCode,
//                'source'=>$this->createUrl('BeCity/GetBelgianPostalCodes'),
                'sourceUrl'=>$this->createUrl(RequestController::actionGetPostalCodeAction()),
                'options'=>array(
                        'minLength'=>'1',
                        'showAnim'=>'fold',
                        'cache'=>'false',
                        'select'=> 'js:function(event, ui)
                            {
                                $("#Request_PostalCode").val(ui.item.value);
                                $("#Request_City").val(ui.item.city);
                                return false;
                            }'

                )
                ));

                ?>
        <?php echo $form->error($model,'PostalCode'); ?>
    </div>

    <div class="row">
        <?php echo $form->labelEx($model,'City'); ?>
        <?php echo $form->textField($model,'City',array('size'=>50,'maxlength'=>250)); ?>
        <?php echo $form->error($model,'City'); ?>
    </div>

リクエストコントローラー:

    public static function actionSetRequestCountryCode()
        {
            $countryCode = $_POST['CountryCode'];
            Yii::app()->user->setState('RequestCountryCode',$countryCode);
        }

        public static function actionGetPostalCodeAction()
        {
            $countryCode = Yii::app()->user->getState('RequestCountryCode');

            if($countryCode == 'BE')
                return 'BeCity/GetBelgianPostalCodes';
            elseif($countryCode == 'FR')
                return 'FrCity/GetFrenchPostalCodes';
            else
                return '';
        }

BeCity コントローラー:

public function actionGetBelgianPostalCodes()
        {                     
            $res =array();

            if (isset($_GET['term'])) {
                    // http://www.yiiframework.com/doc/guide/database.dao
                    $qtxt ="SELECT
                            DISTINCT
                            CONCAT(bc.PostalCode, ' - ', bc.NameNL) as label,
                            bc.PostalCode as value,
                            bc.NameNL as city
                            FROM be_city bc
                            WHERE bc.PostalCode LIKE :qterm
                            ORDER BY bc.PostalCode, bc.NameNL ASC";
                    $command =Yii::app()->db->createCommand($qtxt);
                    $command->bindValue(":qterm", $_GET['term'].'%', PDO::PARAM_STR);
                    $res = $command->queryAll();
            }

            echo CJSON::encode($res);
            Yii::app()->end();
        }

FrCity コントローラー:

public function actionGetFrenchPostalCodes()
        {                     
            $res =array();

            if (isset($_GET['term'])) {
                    // http://www.yiiframework.com/doc/guide/database.dao
                    $qtxt ="SELECT
                            DISTINCT
                            CONCAT(fc.PostalCode, ' - ' , fc.NameFR) AS label,
                            fc.PostalCode as value,
                            fc.NameFR as city
                            FROM fr_city fc
                            WHERE fc.PostalCode LIKE :qterm
                            ORDER BY fc.PostalCode ASC, fc.NameFR ASC";
                    $command =Yii::app()->db->createCommand($qtxt);
                    $command->bindValue(":qterm", $_GET['term'].'%', PDO::PARAM_STR);
                    $res =$command->queryAll();
            }

            echo CJSON::encode($res);
            Yii::app()->end();
        }

セッション変数を使用するのは正しい方法ですか、それともより良い方法がありますか?

キャッシングの問題はどうですか?

助けてくれてありがとう

4

1 に答える 1

1

OK、1 つのアクション (関数) で国パラメーターを取得し、2 つの別個のアクションに再ルーティングする代わりに、その 1 つのアクションですべてのロジックを実行することで、それを機能させることができました。

形:

    <div class="row">
        <?php echo $form->labelEx($model,'Country'); ?>
        <?php echo $form->dropDownList($model,
                        'CountryCode',
                        CHtml::listData(Country::model()->findAllByAttributes(array('Visible'=>1)),'Code','Name')

                        ); ?>
        <?php echo $form->error($model,'CountryCode'); ?>
    </div>

        <div class="row">
        <?php echo $form->labelEx($model,'PostalCode'); ?>
        <?php 

                $this->widget('zii.widgets.jui.CJuiAutoComplete', array(
                'name'=>'Request_PostalCode',
                'value'=>$model->PostalCode,
                'source'=>'js: function(request, response) {
                                $.ajax({
                                    url: "'.$this->createUrl('Request/GetPostalCodes').'",
                                    dataType: "json",
                                    data: {
                                        term: request.term,
                                        countryCode: $("#Request_CountryCode").val()
                                    },
                                    success: function (data) {
                                            response(data);
                                    }
                                })
                             }',
                'options'=>array(
                        'minLength'=>'1',
                        'showAnim'=>'fold',
                        'select'=> 'js:function(event, ui)
                            {
                                $("#Request_PostalCode").val(ui.item.value);
                                $("#Request_City").val(ui.item.city);
                                return false;
                            }'

                )
                ));

                ?>
        <?php echo $form->error($model,'PostalCode'); ?>
    </div>

    <div class="row">
        <?php echo $form->labelEx($model,'City'); ?>
        <?php echo $form->textField($model,'City',array('size'=>50,'maxlength'=>250)); ?>
        <?php echo $form->error($model,'City'); ?>
    </div>

リクエストコントローラー:

public function actionGetPostalCodes() {

    $countryCode = $_GET['countryCode'];

    $res =array();

    if (isset($_GET['term'])) 
    {

        $qtxt = '';

        if($countryCode == 'BE')
            $qtxt ="SELECT
                    DISTINCT
                    CONCAT(bc.PostalCode, ' - ', bc.NameNL) as label,
                    bc.PostalCode as value,
                    bc.NameNL as city
                    FROM be_city bc
                    WHERE bc.PostalCode LIKE :qterm
                    ORDER BY bc.PostalCode, bc.NameNL ASC";

        elseif($countryCode == 'FR')
            $qtxt ="SELECT
                    DISTINCT
                    CONCAT(fc.PostalCode, ' - ' , fc.NameFR) AS label,
                    fc.PostalCode as value,
                    fc.NameFR as city
                    FROM fr_city fc
                    WHERE fc.PostalCode LIKE :qterm
                    ORDER BY fc.PostalCode ASC, fc.NameFR ASC";

        if($qtxt != '')
        {
            $command =Yii::app()->db->createCommand($qtxt);
            $command->bindValue(":qterm", $_GET['term'].'%', PDO::PARAM_STR);
            $res = $command->queryAll();
        }
    }

    echo CJSON::encode($res);
    Yii::app()->end();

}
于 2012-09-19T08:14:56.737 に答える