ThinkPHP 前台视图实现类似于Yii的自动验证

ThinkPHP model类其实自带这个功能 可以写一个基础类继承Model

模型层代码:

<?php
namespace Manager\Model;
use Think\Model;
class BaseModel extends Model {
    public function autoValidation($data,$type) {
        if(false === $this->options['validate'] ){
            // 关闭自动验证
            return true;
        }
        if(!empty($this->options['validate'])) {
            $_validate   =   $this->options['validate'];
            unset($this->options['validate']);
        }elseif(!empty($this->_validate)){
            $_validate   =   $this->_validate;
        }
        // 属性验证
        if(isset($_validate)) { // 如果设置了数据自动验证则进行数据验证
            if($this->patchValidate) { // 重置验证错误信息
                $this->error = array();
            }
            foreach($_validate as $key=>$val) {
                // 验证因子定义格式
                // array(field,rule,message,condition,type,when,params)
                // 判断是否需要执行验证
                if(empty($val[5]) || ( $val[5]== self::MODEL_BOTH && $type < 3 ) || $val[5]== $type ) {
                    if(0==strpos($val[2],'{%') && strpos($val[2],'}'))
                        // 支持提示信息的多语言 使用 {%语言定义} 方式
                        $val[2]  =  L(substr($val[2],2,-1));
                    $val[3]  =  isset($val[3])?$val[3]:self::EXISTS_VALIDATE;
                    $val[4]  =  isset($val[4])?$val[4]:'regex';
                    // 判断验证条件
                    switch($val[3]) {
                        case self::MUST_VALIDATE:   // 必须验证 不管表单是否有设置该字段
                            if(false === $this->_validationField($data,$val))
                                return false;
                            break;
                        case self::VALUE_VALIDATE:    // 值不为空的时候才验证
                            if('' != trim($data[$val[0]]))
                                if(false === $this->_validationField($data,$val))
                                    return false;
                            break;
                        default:    // 默认表单存在该字段就验证
                            if(isset($data[$val[0]]))
                                if(false === $this->_validationField($data,$val))
                                    return false;
                    }
                }
            }
            // 批量验证的时候最后返回错误
            if(!empty($this->error)) return false;
        }
        return true;
    }

}

这个 autoValidation 方法 在Model里本来就有的 但是权限是protected 而我们是想在控制器类中调用 所以这里权限必须是public

控制器代码:

我是写在CommonController里 其他控制器继承Common就可以了

    public function checkField($model = null) {
        $fieldname = I('fieldname');
        $curval = I('curval');
        $model = ucfirst($model) ?:ucfirst(CONTROLLER_NAME);
        $modelobj = D($model);
        if(I('id')) { // 修改数据时验证
            $res = $modelobj->autoValidation(array($fieldname=>$curval,'id'=>I('id')),3);
        } else { // 新增数据时验证
            $res = $modelobj->autoValidation(array($fieldname=>$curval),3);
        }
        if(!$res) {
            $this->ajaxReturn(array('status'=>'error','msg'=>$modelobj->getError()));
        } else {
            $this->ajaxReturn(array('status'=>'ok','msg'=>'成功'));
        }
    }

视图层代码:

    // 表单验证
    $("input").blur(function () {
        var fieldname = $(this).attr('name');
        var curval = $(this).val();
        var id = $("input[name=id]").val();
        if(id) {
            var postdata = {fieldname:fieldname,curval:curval,id:id};
        } else {
            var postdata = {fieldname:fieldname,curval:curval};
        }
        var _this = $(this);
        $.ajax({
            type:'POST',
            data:postdata,
            url:'{:U("checkField")}',
            success:function (d) {
                if(d.status == 'error') {
                    _this.parent().siblings('.layui-word-aux').html("<i class='iconfont' style='color:red;'>&#xe623;</i>"+d.msg);
                } else {
                    _this.parent().siblings('.layui-word-aux').html("<i class='iconfont' style='color:green;'>&#xe609;</i>");
                }
            }
        })
    })

input表单一旦失去焦点 就会以ajax方式请求控制器里的checkField方法 这个方法刚才在Common控制器里写了 就是用来进行表单验证的

视图层的代码可以根据自己的需求修改

这里需要注意:在编辑数据的页面,一定要传此记录的主键ID,因为有些字段我是要求unique规则唯一验证的 不传主键ID unique规则就会失效 我在视图层进行了简单的判断

 

posted @ 2017-06-19 10:03  代码小伙  阅读(299)  评论(0编辑  收藏  举报