【问题标题】:Yii Ajax Validation in widget not working小部件中的 Yii Ajax 验证不起作用
【发布时间】:2015-10-16 04:53:33
【问题描述】:

我在我的小部件中使用 Ajax 验证。这是代码。

小部件功能

public function run(){

if(!Yii::app()->user->isGuest){
    $this->controller->redirect('/');
}

$model= new LoginForm;

// if it is ajax validation request
if(isset($_POST['ajax']) && $_POST['ajax']==='login-form')
{
    echo CActiveForm::validate($model);
    Yii::app()->end();
}
    if(isset($_POST['LoginForm']))
    {

        $model->attributes=$_POST['LoginForm'];
        // validate user input and redirect to the previous page if valid
        // blah blah.......

小部件视图:

<?php $form=$this->beginWidget('CActiveForm', array(
    'id'=>'login-form',
    'enableAjaxValidation'=> true,
    'enableClientValidation'=>true,
    'clientOptions'=>array(
        'validateOnSubmit'=>true,
    ),
)); ?>


    <div class="row">
        <?php echo $form->textField($model,'username',array('placeholder'=>'email','class'=>'form-control')); ?>
        <?php echo $form->error($model,'username'); ?>
    </div>

    <div class="row">
        <?php echo $form->passwordField($model,'password',array('placeholder'=>'password','class'=>'form-control')); ?>
        <?php echo $form->error($model,'password'); ?>
    </div>


    <div class="row buttons">
        <?php echo CHtml::submitButton('Login', array('class'=>'btn btn-primary btn-block')); ?>
    </div>
    ...
  • 现在表单没有提交。单击登录后,没有任何反应。
  • 如果我使 enableAjaxValidation 失效,表单可以工作,但 AJAX 不能工作。
  • 如果我将 enableClientValidation 设为 false,表单可以工作但仍然没有 AJAX。

有什么想法吗?谢谢。

【问题讨论】:

    标签: php ajax yii


    【解决方案1】:

    问题是您使用的是单个提交按钮,而不是 ajax 提交按钮。

    为此,您可以使用来自 Yii Bootstrap(或 Yii 助推器)的 ajaxSubmitButton 小部件。

    所以,在 SiteController 中:

    ...
    $model= new LoginForm;
    
    if(isset($_POST['ajax']) && $_POST['ajax']==='login-form')
    {
      echo CActiveForm::validate($model);
      Yii::app()->end();
    }
    if(isset($_POST['LoginForm']))
    {
      $model->unsetAttributes();
      $model->attributes=$_POST['LoginForm'];
    
      if($model->validate() && $model->login())
      {
        $array = array('login' => 'success');
        $json = json_encode($array);
        echo $json;
    
        Yii::app()->end();
      }
      else{ //This is the important point
        if(Yii::app()->getRequest()->getIsAjaxRequest()) 
        {
          $array=$model->getErrors();
          $json = json_encode($array);
          echo $json; //JSON containing the errors set in /models/LoginForm.php
          Yii::app()->end(); 
        }
      }
    }
    ...
    

    在你看来:

    <?php $form=$this->beginWidget('CActiveForm', array(
      'id'=>'login-form',
      'enableAjaxValidation'=> true,
      'enableClientValidation'=>true,
      'clientOptions'=>array(
         'validateOnSubmit'=>true,
       ),
      )); 
    ?>
    
    <div class="row">
        <?php echo $form->textField($model,'username',array('placeholder'=>'email','class'=>'form-control')); ?>
        <?php echo $form->error($model,'username'); ?>
    </div>
    
    <div class="row">
        <?php echo $form->passwordField($model,'password',array('placeholder'=>'password','class'=>'form-control')); ?>
        <?php echo $form->error($model,'password'); ?>
    </div>
    
    <div class="row" >
        <?php 
          /** THIS IS THE AJAX SUBMIT BUTTON **/
         $this->widget('bootstrap.widgets.TbButton', array(
                            'buttonType' => 'ajaxSubmit', 
                            'label' => 'Login', 
                            'ajaxOptions' => array(
                                   'success' => 
                                       'function(data){
                                           var obj = $.parseJSON(data);
                                           if(obj.login=="success"){
                                              //...
                                              // $(location).attr("href","BASEURL/someController/someAction")
                                           }
                                           else{
                                               if("username" in obj){
                                                   $("#LoginForm_username_em_").text(obj.username[0]);
                                                   $("#LoginForm_username_em_").show();
                                                   $("#LoginForm_username").css({"background":"#FEE","border-color":"#C00"});
                                               }
    
                                               if("password" in obj){
                                                   $("#LoginForm_password_em_").text(obj.password[0]);
                                                   $("#LoginForm_password").css({"display":"block"});
                                                   $("#LoginForm_password").css({"background":"#FEE","border-color":"#C00"});
                                               }
                                              $("#LoginForm_password_em_").show();
                                           }
                              }'),
                        ));
        ?>
    </div>
    

    要使用 Yii Bootstrap(或 Yii Booster)的 ajaxSubmitButton 小部件,您必须从 http://yiibooster.clevertech.biz/ 下载它,将其解压到 /protected/extensions 文件夹中,并将其包含在 /protected/config/main.php :

    ...
    Yii::setPathOfAlias('bootstrap',dirname(__FILE__).'/../extensions/bootstrap'); //booster insead of bootstrap if you download the Yii Booster.
    
    return array(
      ...
      'components'=>array(
        ...
        'bootstrap'=>array(
            'class'=>'ext.bootstrap.components.Bootstrap', // assuming you extracted bootstrap under extensions
        ),
      )
    )
    

    Yii Booster 有许多其他小部件,因此我使用它。如果您不想为 ajax 提交按钮使用 Yii 助推器,只需使用 CHtml::ajaxSubmitButton

    【讨论】:

    • 感谢您的帮助。但我不认为上面的代码有效。我试过 var obj = $.parseJSON(data);但它总是在控制台中返回无效令牌。
    • 试试这个:在 login.php 中,在 'ajaxOptions' 中:.. 'ajaxOptions' => array( 'success' => 'function(data){ var obj = $.parseJSON(data) ; alert(data); if(obj.login=="success"){ ... } else{ ..}
    • 通过该警报,您可能会看到 JSON 返回的内容。不过,我认为您错过了 LoginForm.php 模型中的某些内容。在其中,您必须为错误设置例外规则: ... public function rules() { return array( array('username', 'required', 'message'=>'Username required.'), array( 'password', 'required', 'message'=>'Password required.'), ); }
    • 另外,在 LoginForm.php 中: public function authenticate($attribute,$params) { if(!$this->hasErrors()) { $this->_identity=new UserIdentity($this- >用户名,$this->密码); if(!$this->_identity->authenticate()) $this->addError('password','密码不正确');这样,您的 JSON 将根据情况返回它需要返回的任何内容
    • 我忘了说在SiteController.php中,在函数actionLogin()中,登录成功时添加如下代码:if($model->validate() && $model->login()) { $array = array('登录' => '成功'); $json = json_encode($array);回声 $json; Yii::app()->end(); }(我在上面的代码中对其进行了编辑)。
    【解决方案2】:

    Ajax 验证需要一点小心。 请在控制台查看 ajax 调用的响应。在 ajax 验证中,ajax 调用的输出应该是纯 json。如果来自小部件的 ajax 验证可能包含一些带有 ajax 调用响应的 html。

    看看http://www.yiiframework.com/forum/index.php/topic/12222-ajax-validation-in-widget-does-not-work/希望对你有帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-01-08
      • 2015-11-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多