0

I have a fieldset with a field called "company" which is not required by default. Now there is a form which adds this fieldset and now "company" should be required. Is there a way to do this in e. g. the form factory? Or can I rewrite the input filters of the fieldset in my inputfilter class binded to the form?

Thanks for any response!

Fieldset

class MyFieldset extends Fieldset implements InputFilterProviderInterface {

    public function init() {
        $this->add([
            'name' => 'company',

            'options' => [
                'label' => 'Firma'
            ],

            'attributes' => [
                'id' => 'address-company'
            ]
        ]);
    }

    public function getInputFilterSpecification() {
        return [
            'company' => [
                'required' => false,

                'filters' => [
                    ['name' => 'StripTags'],
                    ['name' => 'StringTrim'],
                    ['name' => 'ToNull']
                ],

                'validators' => [
                    [
                        'name' => 'StringLength',

                        'options' => [
                            'encoding' => 'UTF-8',
                            'min' => 1,
                            'max' => 128
                        ]
                    ]
                ]
            ],
        ];
    }
}

Form

class MyForm extends Form {

    public function init() {
        $this->add([
            'type' => MyFieldset::class,
            'name' => 'test',

            'options' => [
                'use_as_base_fieldset' => true
            ]
        ]);
    }

}

Form Factory

class MyFormFactory implements FactoryInterface {

    public function __invoke(ContainerInterface $container, $requestedName, array $options = null) {
        $hydratorManager = $container->get('HydratorManager');
        $inputFilterManager = $container->get('InputFilterManager');

        $form = new MyForm();
        $form->setHydrator($hydratorManager->get(DoctrineObject::class));
        $form->setInputFilter($inputFilterManager->get(MyInputFilter::class));
        $form->bind(new Entity());

        return $form;
    }

}
Dominik Barann
  • 675
  • 2
  • 10
  • 25
  • Could have a look at [this answer](https://stackoverflow.com/a/44311301/1155833) on one of my questions and combine that with [this answer](https://stackoverflow.com/a/45187053/1155833). The first is about separating your InputFilters from your Fieldsets. The second is about creating an additional option allowing you to set Inputs with type of a Fieldset (so another Fieldset) to (not) required. Then you override the default isValid method to allow for that check. Takes a bit of work, but makes using Fieldsets and Collections a lot easier/cleaner :) Btw, links about ZF2, but might help. – rkeet Sep 04 '17 at 14:58

2 Answers2

1

The only way I can think of doing it is.

In your fieldset use:

private $companyRequired = FALSE;

public function setCompanyRequired($companyRequired)
{
    $this->companyRequired = (bool) $companyRequired;
}

public function getInputFilterSpecification()
{
    return [
        'company' => [
            'required' => $this->companyRequired,
            'filters' => [
                ['name' => 'StripTags'],
                ['name' => 'StringTrim'],
                ['name' => 'ToNull']
            ],
            'validators' => [
                [
                    'name' => 'StringLength',
                    'options' => [
                        'encoding' => 'UTF-8',
                        'min' => 1,
                        'max' => 128
                    ]
                ]
            ]
        ],
    ];
}

in the form where the company is required place this in your init() method after adding the fieldset:

$this->get('test')->setCompanyRequired(TRUE);

As the getInputFilterSpecification() method is not read until you validate your form this should work.

Garry
  • 1,455
  • 1
  • 15
  • 34
1

I have previously answered a similar question relating to over loading the default input filter options of a nested fieldset.

You can do the same inside the form using the Zend\InputFilter\InputFilterProviderInterface

class MyForm extends Form implements InputFilterProviderInterface
{

    public function init() 
    {
        //..
    }

    public function getInputFilterSpecification()
    {
        return [
            'test' => [
                'type' => 'Zend\\InputFilter\\InputFilter',
                'company' => [
                    'required' => true,
                ],
            ],
        ];
    }

}

Or alternately, you can achieve the same by manually configuring the fieldset's input filter inside MyFormFactory;

class MyFormFactory implements FactoryInterface 
{

    public function __invoke(ContainerInterface $container, $requestedName, array $options = null) 
    {
        //.. same code

        $form->getInputFilter()  // fetch the input filter you just attached.
            ->get('test')        // the name of the neseted fieldset (another input filter)
            ->get('company')     // the name of the input
            ->setRequired(true); // set required to true :)

        return $form;
    }

}
AlexP
  • 9,906
  • 1
  • 24
  • 43