单选按钮:在大海捞针中找不到输入?
Radio button: input was not found in the haystack?
每当我提交表单时,我都会收到此消息:
The input was not found in the haystack.
这是针对 shipping-method
元素(单选按钮)的。无法弄清楚这是什么意思,该元素的 POST 数据不为空。
public function getInputFilter()
{
if (!$this->inputFilter) {
$inputFilter = new InputFilter();
// Some other basic filters
$inputFilter->add(array(
'name' => 'shipping-method',
'required' => true,
'filters' => array(
array('name' => 'StripTags'),
array('name' => 'StringTrim')
),
'validators' => array(
array(
'name' => 'StringLength',
'options' => array(
'encoding' => 'UTF-8',
'max' => 20,
),
),
array(
'name' => 'Db\RecordExists',
'options' => array(
'table' => 'shipping',
'field' => 'shipping_method',
'adapter' => $this->dbAdapter
)
),
),
));
$inputFilter->get('shipping-address-2')->setRequired(false);
$inputFilter->get('shipping-address-3')->setRequired(false);
$this->inputFilter = $inputFilter;
}
return $this->inputFilter;
}
我一直在寻找 <select>
的解决方案。
这是示例 POST 数据:
object(Zend\Stdlib\Parameters)#143 (1) {
["storage":"ArrayObject":private] => array(9) {
["shipping-name"] => string(4) "TEST"
["shipping-address-1"] => string(4) "test"
["shipping-address-2"] => string(0) ""
["shipping-address-3"] => string(0) ""
["shipping-city"] => string(4) "TEST"
["shipping-state"] => string(4) "TEST"
["shipping-country"] => string(4) "TEST"
["shipping-method"] => string(6) "Ground"
["submit-cart-shipping"] => string(0) ""
}
}
更新:
form.phtml
<div class="form-group">
<?= $this->formRow($form->get('shipping-method')); ?>
<?= $this->formRadio($form->get('shipping-method')
->setValueOptions(array(
'Ground' => 'Ground',
'Expedited' => 'Expedited'))
->setDisableInArrayValidator(true)); ?>
</div>
ShippingForm.php
$this->add(array(
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => array(
'label' => 'Shipping Method',
'label_attributes' => array(
'class' => 'lbl-shipping-method'
),
)
));
昨天刚发生过这件事。
select 和 multi select ZF2+ 元素有一个内置的 in_array 验证器。
记住过滤器出现在验证器之前。
您可能在这里做的太多了——在 ZF2 表单中很少需要过滤或添加验证器 ot select 和多个 select 表单元素。内置的元素验证器非常强大,ZF 为我们做了很多工作。
尝试删除元素的过滤器和验证器,例如:
$inputFilter->add(array(
'name' => 'shipping-method',
'required' => true,
));
我还看到了另一种极端情况:在控制器(或视图)中的某处更改 select 元素的 valueOptions,导致在视图和表单验证中使用不同的 valueOptions(在我们的例子中,它替换了元素与验证前的新元素)。
我认为你的问题在于你在设置 InArray 验证器之后添加你的值选项,因此验证器没有大海捞针。
试试这个
$this->add(array(
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => array(
'label' => 'Shipping Method',
'label_attributes' => array(
'class' => 'lbl-shipping-method'
),
'value_options' => array(
'Ground' => 'Ground',
'Expedited' => 'Expedited'
),
'disable_inarray_validator' => TRUE,
)
));
并从您的视图中删除 setValueOptions 和 setDisableInArrayValidator。
希望这有效。
问题出在您使用 setValueOptions()
和 setDisableInArrayValidator()
时。您应该在您的代码中更早地执行此操作,因为它在验证您的表单之前从未设置过,因此 inputfilter 仍然包含默认值作为 InArray
验证器。在检查输入过滤器的验证之后,您可以为 shipping_methods.
设置不同的选项
您应该将 setValueOptions()
和 setDisableInArrayValidator()
移到 $form->isValid()
之前。通过在表单本身中设置正确的选项或在控制器中执行此操作。最好的方法是将所有选项都放在一个地方,并在 class.
表格内进行
$this->add([
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => [
'value_options' => [
'Ground' => 'Ground',
'Expedited' => 'Expedited'
],
'disable_inarray_validator' => true,
'label' => 'Shipping Method',
'label_attributes' => [
'class' => 'lbl-shipping-method',
],
],
]);
您可能想要更改的另一个小细节是设置值选项。它们现在是硬编码的,但您的输入过滤器正在检查数据库记录是否存在。使用数据库记录填充值选项。如果代码仍然包含旧方法但数据库有一些新方法,则它们不同步。
class ShippingForm extends Form
{
private $dbAdapter;
public function __construct(AdapterInterface $dbAdapter, $name = 'shipping-form', $options = [])
{
parent::__construct($name, $options)
// inject the databaseAdapter into your form
$this->dbAdapter = $dbAdapter;
}
public function init()
{
// adding form elements to the form
// we use the init method to add form elements as from this point
// we also have access to custom form elements which the constructor doesn't
$this->add([
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => [
'value_options' => $this->getDbValueOptions(),
'disable_inarray_validator' => true,
'label' => 'Shipping Method',
'label_attributes' => [
'class' => 'lbl-shipping-method',
],
],
]);
}
private function getDbValueOptions()
{
$statement = $this->dbAdapter->query('SELECT shipping_method FROM shipping');
$rows = $statement->execute();
$valueOptions = [];
foreach ($rows as $row) {
$valueOptions[$row['shipping_method']] = $row['shipping_method'];
}
return $valueOptions;
}
}
每当我提交表单时,我都会收到此消息:
The input was not found in the haystack.
这是针对 shipping-method
元素(单选按钮)的。无法弄清楚这是什么意思,该元素的 POST 数据不为空。
public function getInputFilter()
{
if (!$this->inputFilter) {
$inputFilter = new InputFilter();
// Some other basic filters
$inputFilter->add(array(
'name' => 'shipping-method',
'required' => true,
'filters' => array(
array('name' => 'StripTags'),
array('name' => 'StringTrim')
),
'validators' => array(
array(
'name' => 'StringLength',
'options' => array(
'encoding' => 'UTF-8',
'max' => 20,
),
),
array(
'name' => 'Db\RecordExists',
'options' => array(
'table' => 'shipping',
'field' => 'shipping_method',
'adapter' => $this->dbAdapter
)
),
),
));
$inputFilter->get('shipping-address-2')->setRequired(false);
$inputFilter->get('shipping-address-3')->setRequired(false);
$this->inputFilter = $inputFilter;
}
return $this->inputFilter;
}
我一直在寻找 <select>
的解决方案。
这是示例 POST 数据:
object(Zend\Stdlib\Parameters)#143 (1) {
["storage":"ArrayObject":private] => array(9) {
["shipping-name"] => string(4) "TEST"
["shipping-address-1"] => string(4) "test"
["shipping-address-2"] => string(0) ""
["shipping-address-3"] => string(0) ""
["shipping-city"] => string(4) "TEST"
["shipping-state"] => string(4) "TEST"
["shipping-country"] => string(4) "TEST"
["shipping-method"] => string(6) "Ground"
["submit-cart-shipping"] => string(0) ""
}
}
更新: form.phtml
<div class="form-group">
<?= $this->formRow($form->get('shipping-method')); ?>
<?= $this->formRadio($form->get('shipping-method')
->setValueOptions(array(
'Ground' => 'Ground',
'Expedited' => 'Expedited'))
->setDisableInArrayValidator(true)); ?>
</div>
ShippingForm.php
$this->add(array(
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => array(
'label' => 'Shipping Method',
'label_attributes' => array(
'class' => 'lbl-shipping-method'
),
)
));
昨天刚发生过这件事。
select 和 multi select ZF2+ 元素有一个内置的 in_array 验证器。
记住过滤器出现在验证器之前。
您可能在这里做的太多了——在 ZF2 表单中很少需要过滤或添加验证器 ot select 和多个 select 表单元素。内置的元素验证器非常强大,ZF 为我们做了很多工作。
尝试删除元素的过滤器和验证器,例如:
$inputFilter->add(array(
'name' => 'shipping-method',
'required' => true,
));
我还看到了另一种极端情况:在控制器(或视图)中的某处更改 select 元素的 valueOptions,导致在视图和表单验证中使用不同的 valueOptions(在我们的例子中,它替换了元素与验证前的新元素)。
我认为你的问题在于你在设置 InArray 验证器之后添加你的值选项,因此验证器没有大海捞针。
试试这个
$this->add(array(
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => array(
'label' => 'Shipping Method',
'label_attributes' => array(
'class' => 'lbl-shipping-method'
),
'value_options' => array(
'Ground' => 'Ground',
'Expedited' => 'Expedited'
),
'disable_inarray_validator' => TRUE,
)
));
并从您的视图中删除 setValueOptions 和 setDisableInArrayValidator。
希望这有效。
问题出在您使用 setValueOptions()
和 setDisableInArrayValidator()
时。您应该在您的代码中更早地执行此操作,因为它在验证您的表单之前从未设置过,因此 inputfilter 仍然包含默认值作为 InArray
验证器。在检查输入过滤器的验证之后,您可以为 shipping_methods.
您应该将 setValueOptions()
和 setDisableInArrayValidator()
移到 $form->isValid()
之前。通过在表单本身中设置正确的选项或在控制器中执行此操作。最好的方法是将所有选项都放在一个地方,并在 class.
$this->add([
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => [
'value_options' => [
'Ground' => 'Ground',
'Expedited' => 'Expedited'
],
'disable_inarray_validator' => true,
'label' => 'Shipping Method',
'label_attributes' => [
'class' => 'lbl-shipping-method',
],
],
]);
您可能想要更改的另一个小细节是设置值选项。它们现在是硬编码的,但您的输入过滤器正在检查数据库记录是否存在。使用数据库记录填充值选项。如果代码仍然包含旧方法但数据库有一些新方法,则它们不同步。
class ShippingForm extends Form
{
private $dbAdapter;
public function __construct(AdapterInterface $dbAdapter, $name = 'shipping-form', $options = [])
{
parent::__construct($name, $options)
// inject the databaseAdapter into your form
$this->dbAdapter = $dbAdapter;
}
public function init()
{
// adding form elements to the form
// we use the init method to add form elements as from this point
// we also have access to custom form elements which the constructor doesn't
$this->add([
'name' => 'shipping-method',
'type' => 'Zend\Form\Element\Radio',
'options' => [
'value_options' => $this->getDbValueOptions(),
'disable_inarray_validator' => true,
'label' => 'Shipping Method',
'label_attributes' => [
'class' => 'lbl-shipping-method',
],
],
]);
}
private function getDbValueOptions()
{
$statement = $this->dbAdapter->query('SELECT shipping_method FROM shipping');
$rows = $statement->execute();
$valueOptions = [];
foreach ($rows as $row) {
$valueOptions[$row['shipping_method']] = $row['shipping_method'];
}
return $valueOptions;
}
}