Zend Framework 2 表单错误未显示
Zend Framework 2 Form Errors Not Showing
我想弄清楚为什么 Zend Form 没有向我的表单返回错误。
当我查看:Zdendframework/library/form/form.php 文件时,我可以看到正在生成错误:
public function isValid()
{
if ($this->hasValidated) {
return $this->isValid;
}
...
if (!$result) {
$this->setMessages($filter->getMessages());
}
return $result;
}
如果我 var_dump($filter->getMessages(),我看到了错误。
然而,当我返回我的表单并尝试转储消息时,有 none 可用。
我的控制器
$prg = $this->prg();
if ($prg instanceof Response) {
return $prg;
} elseif ($prg === false) {
return $this->getVM()->setVariables([
'form' => $this->registerForm
]);
}
$this->registerForm->setData($prg);
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->updateForm]);
}
我的表格:
public function __construct(
InputFilterInterface $inputFilter,
$name = null,
$options = array()
) {
parent::__construct('register', $options);
$this->register = $inputFilter;
}
public function init()
{
$this->add(
[
'name' => 'csrfcheck',
'type' => 'csrf'
]
);
$this->add(
[
'name' => 'user',
'type' => UserFieldset::class,
'options' => [
'use_as_base_fieldset' => true
]
]
);
$this->add(
[
'name' => 'submit',
'type' => 'submit',
'attributes' => [
'value' => 'Update User',
'class' => 'btn green',
]
]
);
$this->getInputFilter()->add($this->register, 'user');
$this->setValidationGroup(
[
'csrfcheck',
'user' => [
'id',
'email',
'firstName',
'lastName',
'roles',
'state'
]
]
);
}
我的 FieldSet
public function __construct(
ObjectManager $objectManager,
User $userPrototype,
$name = null,
$options = array()
) {
parent::__construct($name, $options);
$this->objectManager = $objectManager;
$this->setHydrator(new DoctrineObject($objectManager));
$this->setObject($userPrototype);
}
public function init()
{
$this->add(
[
'name' => 'id',
'type' => 'hidden',
]
);
$this->add(
[
'name' => 'uuid',
'type' => 'hidden',
]
);
$this->add(
[
'name' => 'email',
'type' => 'email',
'options' => [
'label' => 'E-Mail',
'instructions' => 'Your email address',
],
'attributes' => [
'class' => 'form-control input-large'
]
]
);
$this->add(
[
'name' => 'firstName',
'type' => 'text',
'options' => [
'label' => 'Firstname',
'instructions' => 'Alphanumeric characters (A,b,c,d,e..)',
],
'attributes' => [
'class' => 'form-control',
'type' => 'text',
'pattern' => "^[a-zA-Z-]{2,128}$",
]
]
);
$this->add(
[
'name' => 'lastName',
'type' => 'text',
'options' => [
'label' => 'Last name',
'instructions' => 'Alphanumeric characters, optional ( \' )',
],
'attributes' => [
'class' => 'form-control',
'pattern' => "^[a-zA-Z'-]{2,128}$",
]
]
);
$this->add(
[
'name' => 'state',
'type' => 'select',
'options' => [
'label' => 'User State',
'value_options' => [
0 => 'Active',
1 => 'Locked',
2 => 'Deleted'
]
],
'attributes' => [
'class' => 'form-control'
]
]
);
//@TODO Multiple set to true to make this work remove attributes if this breaks other forms
$this->add(
[
'name' => 'roles',
'type' => 'DoctrineModule\Form\Element\ObjectSelect',
'options' => [
'object_manager' => $this->objectManager,
'target_class' => HierarchicalRole::class,
'property' => 'name',
'find_method' => [
'name' => 'getAccessibleRoles'
],
'label' => 'Role'
],
'attributes' => [
'multiple' => true,
]
]
);
我的过滤器
function __construct(
ObjectManager $objectManager,
ObjectRepository $objectRepository
) {
$this->add(
[
'name' => 'id',
'required' => true,
'filters' => [
['name' => 'Int']
]
]
);
$this->add(
[
'name' => 'uuid',
'required' => false
]
);
$this->add(
[
'name' => 'firstName',
'required' => true,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 1,
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'lastName',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 1,
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'email',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 3,
'max' => 255
]
],
[
'name' => 'EmailAddress',
'options' => [
'useDomainCheck' => true, //Set to false in order to validate local developer test mails: myemail.dev
'message' => "This is not a valid email address"
],
]
]
]
);
$this->add(
[
'name' => 'password',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'passwordRepeat',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'roles',
'required' => false,
'validators' => [
]
]
);
$this->add( array(
'name' => 'state',
'required' => false
));
}
还有我的观点
<div class="portlet-body form">
<!-- BEGIN FORM-->
<div class="portlet-body form">
<?php
$form = $this->form;
$form->setAttribute('action', $this->url());
$form->setAttribute('class', 'form-horizontal form-bordered');
$form->get('user')->get('roles')->setAttribute('class','form-control input-small select2me');
$form->get('submit')->setValue('Register new user');
$form->get('submit')->setAttribute('class','btn green');
$form->prepare();
$csrf = $form->get('csrfcheck');
$user = $form->get('user');
$id = $user->get('id');
$state = $user->get('state');
$email = $user->get('email');
$firstname = $user->get('firstName');
$lastname = $user->get('lastName');
$role = $user->get('roles');
$sub = $form->get('submit');
?>
<?= $this->form()->openTag($form); ?>
<?= $this->formElement($csrf); ?>
<?= $this->formElement($id); ?>
<?= $this->formElement($state); ?>
<div class='form-body'>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($email); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($email).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($email))) echo '<div class="alert alert-danger">'.$this->formElementErrors($email).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($firstname); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($firstname).'</div>'; ?>
</div>
<?php echo '<div class="alert alert-danger">'.$this->formElementErrors($firstname).'</div>'; ?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($lastname); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($lastname).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($lastname))) echo '<div class="alert alert-danger">'.$this->formElementErrors($lastname).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($role); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group input-large">'.$this->formElement($role).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($role))) echo '<div class="alert alert-danger">'.$this->formElementErrors($role).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($state); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group input-large">'.$this->formElement($state).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($state))) echo '<div class="alert alert-danger">'.$this->formElementErrors($state).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?= $this->formElement($sub); ?>
</div>
</div>
</div>
</div>
<?= $this->form()->closeTag(); ?>
编辑
在控制器中,如果我转储这个:
$result = $this->registerForm->getInputFilter()->getMessages();
die(var_dump($result));
这输出:
array (size=1)
'user' =>
array (size=1)
'firstName' =>
array (size=1)
'isEmpty' => string 'Value is required and can't be empty' (length=36)
从评论和 HappyCoder 本身推断,问题出在控制器中,错误的表单返回到视图。
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->updateForm]);
}
应该是:
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->registerForm]);
}
我想弄清楚为什么 Zend Form 没有向我的表单返回错误。
当我查看:Zdendframework/library/form/form.php 文件时,我可以看到正在生成错误:
public function isValid()
{
if ($this->hasValidated) {
return $this->isValid;
}
...
if (!$result) {
$this->setMessages($filter->getMessages());
}
return $result;
}
如果我 var_dump($filter->getMessages(),我看到了错误。
然而,当我返回我的表单并尝试转储消息时,有 none 可用。
我的控制器
$prg = $this->prg();
if ($prg instanceof Response) {
return $prg;
} elseif ($prg === false) {
return $this->getVM()->setVariables([
'form' => $this->registerForm
]);
}
$this->registerForm->setData($prg);
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->updateForm]);
}
我的表格:
public function __construct(
InputFilterInterface $inputFilter,
$name = null,
$options = array()
) {
parent::__construct('register', $options);
$this->register = $inputFilter;
}
public function init()
{
$this->add(
[
'name' => 'csrfcheck',
'type' => 'csrf'
]
);
$this->add(
[
'name' => 'user',
'type' => UserFieldset::class,
'options' => [
'use_as_base_fieldset' => true
]
]
);
$this->add(
[
'name' => 'submit',
'type' => 'submit',
'attributes' => [
'value' => 'Update User',
'class' => 'btn green',
]
]
);
$this->getInputFilter()->add($this->register, 'user');
$this->setValidationGroup(
[
'csrfcheck',
'user' => [
'id',
'email',
'firstName',
'lastName',
'roles',
'state'
]
]
);
}
我的 FieldSet
public function __construct(
ObjectManager $objectManager,
User $userPrototype,
$name = null,
$options = array()
) {
parent::__construct($name, $options);
$this->objectManager = $objectManager;
$this->setHydrator(new DoctrineObject($objectManager));
$this->setObject($userPrototype);
}
public function init()
{
$this->add(
[
'name' => 'id',
'type' => 'hidden',
]
);
$this->add(
[
'name' => 'uuid',
'type' => 'hidden',
]
);
$this->add(
[
'name' => 'email',
'type' => 'email',
'options' => [
'label' => 'E-Mail',
'instructions' => 'Your email address',
],
'attributes' => [
'class' => 'form-control input-large'
]
]
);
$this->add(
[
'name' => 'firstName',
'type' => 'text',
'options' => [
'label' => 'Firstname',
'instructions' => 'Alphanumeric characters (A,b,c,d,e..)',
],
'attributes' => [
'class' => 'form-control',
'type' => 'text',
'pattern' => "^[a-zA-Z-]{2,128}$",
]
]
);
$this->add(
[
'name' => 'lastName',
'type' => 'text',
'options' => [
'label' => 'Last name',
'instructions' => 'Alphanumeric characters, optional ( \' )',
],
'attributes' => [
'class' => 'form-control',
'pattern' => "^[a-zA-Z'-]{2,128}$",
]
]
);
$this->add(
[
'name' => 'state',
'type' => 'select',
'options' => [
'label' => 'User State',
'value_options' => [
0 => 'Active',
1 => 'Locked',
2 => 'Deleted'
]
],
'attributes' => [
'class' => 'form-control'
]
]
);
//@TODO Multiple set to true to make this work remove attributes if this breaks other forms
$this->add(
[
'name' => 'roles',
'type' => 'DoctrineModule\Form\Element\ObjectSelect',
'options' => [
'object_manager' => $this->objectManager,
'target_class' => HierarchicalRole::class,
'property' => 'name',
'find_method' => [
'name' => 'getAccessibleRoles'
],
'label' => 'Role'
],
'attributes' => [
'multiple' => true,
]
]
);
我的过滤器
function __construct(
ObjectManager $objectManager,
ObjectRepository $objectRepository
) {
$this->add(
[
'name' => 'id',
'required' => true,
'filters' => [
['name' => 'Int']
]
]
);
$this->add(
[
'name' => 'uuid',
'required' => false
]
);
$this->add(
[
'name' => 'firstName',
'required' => true,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 1,
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'lastName',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 1,
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'email',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'min' => 3,
'max' => 255
]
],
[
'name' => 'EmailAddress',
'options' => [
'useDomainCheck' => true, //Set to false in order to validate local developer test mails: myemail.dev
'message' => "This is not a valid email address"
],
]
]
]
);
$this->add(
[
'name' => 'password',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'passwordRepeat',
'required' => false,
'filters' => [
['name' => 'StringTrim']
],
'validators' => [
[
'name' => 'StringLength',
'options' => [
'max' => 128
]
]
]
]
);
$this->add(
[
'name' => 'roles',
'required' => false,
'validators' => [
]
]
);
$this->add( array(
'name' => 'state',
'required' => false
));
}
还有我的观点
<div class="portlet-body form">
<!-- BEGIN FORM-->
<div class="portlet-body form">
<?php
$form = $this->form;
$form->setAttribute('action', $this->url());
$form->setAttribute('class', 'form-horizontal form-bordered');
$form->get('user')->get('roles')->setAttribute('class','form-control input-small select2me');
$form->get('submit')->setValue('Register new user');
$form->get('submit')->setAttribute('class','btn green');
$form->prepare();
$csrf = $form->get('csrfcheck');
$user = $form->get('user');
$id = $user->get('id');
$state = $user->get('state');
$email = $user->get('email');
$firstname = $user->get('firstName');
$lastname = $user->get('lastName');
$role = $user->get('roles');
$sub = $form->get('submit');
?>
<?= $this->form()->openTag($form); ?>
<?= $this->formElement($csrf); ?>
<?= $this->formElement($id); ?>
<?= $this->formElement($state); ?>
<div class='form-body'>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($email); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($email).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($email))) echo '<div class="alert alert-danger">'.$this->formElementErrors($email).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($firstname); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($firstname).'</div>'; ?>
</div>
<?php echo '<div class="alert alert-danger">'.$this->formElementErrors($firstname).'</div>'; ?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($lastname); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group">'.$this->formElement($lastname).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($lastname))) echo '<div class="alert alert-danger">'.$this->formElementErrors($lastname).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($role); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group input-large">'.$this->formElement($role).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($role))) echo '<div class="alert alert-danger">'.$this->formElementErrors($role).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"><?= $this->formLabel($state); ?></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?php echo '<div class="form-group input-large">'.$this->formElement($state).'</div>'; ?>
</div>
<?php if (!empty($this->formElementErrors($state))) echo '<div class="alert alert-danger">'.$this->formElementErrors($state).'</div>';?>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-3"></label>
<div class="col-md-5">
<div class="input-group" style="text-align:left">
<?= $this->formElement($sub); ?>
</div>
</div>
</div>
</div>
<?= $this->form()->closeTag(); ?>
编辑
在控制器中,如果我转储这个:
$result = $this->registerForm->getInputFilter()->getMessages();
die(var_dump($result));
这输出:
array (size=1) 'user' => array (size=1) 'firstName' => array (size=1) 'isEmpty' => string 'Value is required and can't be empty' (length=36)
从评论和 HappyCoder 本身推断,问题出在控制器中,错误的表单返回到视图。
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->updateForm]);
}
应该是:
if ( ! $this->registerForm->isValid($prg) ) {
return new ViewModel(['form' => $this->registerForm]);
}