dpjhq00684 2014-01-03 13:01
浏览 43
已采纳

创建一个简单的MVC - 不确定验证实现

I'm creating a simple MVC app to learn more about MVC. I have a controller which uses a UserService class to get the desired users:

class UserController extends Controller{
   public function Index(){
      $data['users'] = UserService::getAll();
      $this->view->render($data);
   }

   public function Add(){
      UserService::insert($_POST['username'],$_POST['password']);
   }
}

The UserService class uses an ORM (idiorm) to get the data:

class UserService{
   public static function getAll(){
      return Model::factory('User')->find_many();
   }

   public static function insert($username,$password){
      $user = Model::factory('User')->create();
      $user->username = $username;
      $user->password = $password; //no good practice in real life offcourse...
      return $user->save();
   }
}

How do I fit in some validation in here? Like checking if the values aren't empty, that the password matches a certain validation pattern, ...

Should I do something like:

//controller

public function Add(){
   if(UserValidationService::checkPassword($_POST['password'])){
      UserService::insert($_POST['username'],$_POST['password']);
   }else{
      //set some errordata and show the view
   }
}

Or should I do the validation in the service (model) and return errors?

I'm a little confused on how to put the validation right.

Code update

class UserController extends Controller{
   public function Add(){
      $result = UserService::insert($_POST['username'],$_POST['password']);
      if($result[0]){
         //result ok, show view
      }else{
         //result not ok, pass errors to view
      }
   }
}

class UserService{
   $errors = "";
   public static function insert($username,$password){
      if(empty($username)){
         $errors .= "Please enter a username.";
      }
      if(empty($password)){
         $errors .= "Please enter a password.";
      }
      if(empty($errors)){
         $user = Model::factory('User')->create();
         $user->username = $username;
         $user->password = $password; //no good practice in real life offcourse...
         $user->save();
         return array(true,$user);
      }else{
         return array(false,$errors);
      }
   }
}
  • 写回答

1条回答 默认 最新

  • douyong1886 2014-01-03 13:07
    关注

    Validation for this kind of constraints should be a model-based validation. This is because you cannot rely on the thing a single model will be used by a single controller.

    Your model for registering a user might be used from 5 different pages, relying on 5 different controllers. Or even by a third party. It will be an overkill to make validations in each controller. You need just to handle the return value of the model.

    In your mode you can have

    if(empty($param)) {
       return array(false, self::EMPTY_PARAM);
    }
    if(strlen($param)<self::MINIMUM_LENGTH) {
       return array(false, self::MINIMUM_LENGTH_NOT_REACHED);
    }
    

    so in your controller you are checking:

       if(!$model_response[0]) {
          return json_encode(array('success' => 0, 'error_msg' => 'Error message, or the constant value from the model, or something else to get proper error message'));
       }
    

    You can simplify by only returning false, the example I added is to handle different errors, so you can send proper string/json to the view.

    /* $model_response here is the return value of the model
     * I did not used associative array returning so
     * if the model return the one I said, the first key (`0`)
     * will be false. So we are checking if the first key is false
     * then testing the second key (`1`) what is its return value
     * in order to handle the error (it's mostly a pseudo code)
     */
    if(!$model_response[0]) {
        switch($model_respose[1]):
            case UserModel::EMPTY_PARAM:
                $error_msg = 'Username or password cannot be empty';
            break;
            case UserModel::MINIMUM_LENGTH_NOT_REACHED:
                $errpr_msg = 'Username and password should be at least' . UserModel::MIN_LENGTH . 'characters long';
            break;
         endswitch;
         return json_encode(array('success' => 0, 'error_msg' => $error_msg));
    }
    

    So you just set the constraints by the model (EMPTY_PARAM, MIN_LENGTH, etc...) and handle them by the controller. You can decide to not handle some of them. The model will return false anyway, but the end user will not see the proper message.

    Thus, if a third party uses your model, i.e. you have partnerships and they have gate and use your model to bring you registrations, and they forgot to tell the user that the min length is 6 characters, they still will be unable to insert into your app usernames with less than 6 chars, but their users won't see why their registration is not done.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥20 sub地址DHCP问题
  • ¥15 delta降尺度计算的一些细节,有偿
  • ¥15 Arduino红外遥控代码有问题
  • ¥15 数值计算离散正交多项式
  • ¥30 数值计算均差系数编程
  • ¥15 redis-full-check比较 两个集群的数据出错
  • ¥15 Matlab编程问题
  • ¥15 训练的多模态特征融合模型准确度很低怎么办
  • ¥15 kylin启动报错log4j类冲突
  • ¥15 超声波模块测距控制点灯,灯的闪烁很不稳定,经过调试发现测的距离偏大