为什么Symfony5表单的username字段跳过Assert断言校验?
问题根因
username校验跳过的核心原因是User实体的setUsername方法参数类型声明不兼容表单默认值转换逻辑:
- Symfony表单组件默认会把用户提交的空字段值转换为
null,而你给setUsername定义了强制string类型的入参 - 当提交空username时,组件尝试调用
setUsername(null)会直接触发PHP类型不匹配错误,流程根本走不到后续的实体Assert断言校验环节,所以看起来就像校验规则被跳过了 - 其余字段校验能正常生效,是因为那些字段的setter没有加强制非空的类型声明,空值可以正常传入实体触发Assert校验
解决办法
任选一种即可:
- 修改实体setUsername参数为可空类型
允许null值传入实体,这样实体的@Assert\NotBlank规则就能正常触发校验:
public function setUsername(?string $username): self { $this->username = $username; return $this; }
- 在UserType的username字段配置中手动加校验约束
直接在表单层提前做非空校验,校验不通过就不会调用setter方法,也不会进入后续业务处理逻辑:
->add('username', TextType::class, [ 'required'=>true, 'invalid_message' => 'Username must not be empty!', 'constraints' => [ new NotBlank([ 'message' => 'Fill username field' ]) ] ])
补充说明
你在字段配置里加的required=true只是HTML5的前端校验属性,你已经在form标签上加了novalidate禁用了前端校验,所以这个属性对后端校验没有任何作用,不要误以为加了required=true后端就会自动添加非空校验规则。
内容的提问来源于stack exchange,提问作者Szymon D.
相关产品推荐
相关产品推荐

