加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 站长学院 > PHP教程 > 正文

cakephp-3.0 – 在验证失败时,beforeMarshal不会修改请求数据

发布时间:2020-12-13 21:54:14 所属栏目:PHP教程 来源:网络整理
导读:错误还是功能?如果我使用beforeMarshal更改请求数据并且存在验证错误,则不会返回修改请求数据. 这个问题可能与How to use Trim() before validation NotEmpty?有关. Modifying Request Data Before Building Entities If you need to modify request data b
错误还是功能?如果我使用beforeMarshal更改请求数据并且存在验证错误,则不会返回修改请求数据.

这个问题可能与How to use Trim() before validation NotEmpty?有关.

Modifying Request Data Before Building Entities
If you need to modify request data before it is converted into entities,you can use the Model.beforeMarshal event. This event lets you manipulate the request data just before entities are created. 07001

根据该书,无论是否存在验证错误,我都希望请求数据始终更改.

示例或测试用例:

// /src/Model/Table/UsersTable.php
namespace AppModelTable;
use CakeORMTable;
// Required for beforeMarshal event:
use CakeEventEvent;
use ArrayObject;
// Required for Validation:
use CakeValidationValidator;

class UsersTable extends Table {

  public function beforeMarshal(Event $event,ArrayObject $data,ArrayObject $options) {
    $data['firstname'] = trim($data['firstname']);
  }

  public function validationDefault(Validator $validator) {
    $validator
      ->add('firstname',[
        'minLength'   => [ 'rule' => ['minLength',2],'message' => 'Too short.' ],])
      ;
    return $validator;
  }
}

如果我输入“d”(Space-d),则会显示验证错误,但空格本身不会在表单中删除.我会表示只显示“d”的表单,因为使用beforeMarshal事件从请求数据中删除了空格.那么……错误还是功能?

我的解决方案是在控制器中使用trim() – 函数而不是beforeMarshal事件:

// /src/Controller/UsersController.php
// ...
public function add() {
  $user = $this->Users->newEntity();
  if ($this->request->is('post')) {
    // Use trim() here instead of beforeMarshal?
    $this->request->data['firstname'] = trim($this->request->data['firstname']);
    $user = $this->Users->patchEntity($user,$this->request->data );
    if ( $this->Users->save($user) ) {
      $this->Flash->succeed('Saved');
      return $this->redirect(['controller' => 'Users','action' => 'index']);
    } else {
      $this->Flash->error('Error');
    }
  }
  $this->set('user',$user);
}

这样,即使存在验证错误,也会删除空间.或者我错过了另一个类似于beforeMarshal的功能,它实际上是在修改请求数据吗?

解决方法

beforeMarshal的主要目的是帮助用户在可以自动解决简单错误时,或者在需要重新构建数据以便将其放入正确的列时,通过验证过程.

beforMarshal事件仅在验证过程开始时触发,其中一个原因是beforeMarshal允许更改验证规则和保存选项,例如字段白名单.此事件结束后即触发验证.

正如文档所解释的,如果某个字段未通过验证,它将自动从数据数组中删除,而不会被复制到实体中.这是为了防止实体对象中存在不一致的数据.

此外,beforeMarshal中的数据是请求的副本.这是因为保留原始用户输入很重要,因为它可能在其他地方使用.

如果您需要修剪列并向用户显示修剪结果,我建议您在控制器中执行此操作:

$this->request->data = array_map(function ($d) {
    return is_string($d) ? trim($d) : $d;
},$this->request->data);

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读