I have a form (Zend\Form\Form
) with some nested fieldsets (Zend\Form\Fieldset
) in it. The construction is pretty similar to that in the Form Collections tutorial.
Storage\Form\MyForm
|_'Storage\Form\Fieldset\FooFieldset'
|_'Storage\Form\Fieldset\BarFieldset'
|_'Storage\Form\Fieldset\BazFieldset'
...
MyForm
class MyForm {
public function __construct()
{
...
$this->add(
[
'type' => 'Storage\Form\Fieldset\FooFieldset',
'options' => [
'use_as_base_fieldset' => true
]
]
);
}
}
FooFieldset
class FooFieldset extends Fieldset implements InputFilterProviderInterface
{
public function __construct()
{
parent::__construct('foo');
$this->setHydrator(new ClassMethodsHydrator())->setObject(new Foo()); // dependencies!
}
}
It works, but the fieldset class has two dependencies in it. I want to inject them. In order to do it, I created a FooFieldsetFactory
and extended the /module/MyModule/config/module.config.php
by:
'service_manager' => [
'factories' => [
'Storage\Form\Fieldset\FooFieldset' => 'Storage\Form\Fieldset\Factory\FooFieldsetFactory',
],
],
The factory is simply being ignored. I guess, the service locator first tries to find the class by namespace and only if nothing is found, takes a look in the invokables
and factories
. OK. Then I created an alias:
'service_manager' => [
'factories' => [
'Storage\Form\Fieldset\FooFieldset' => 'Storage\Form\Fieldset\Factory\FooFieldsetFactory',
],
],
'aliases' => [
'Storage\Form\Fieldset\Foo' => 'Storage\Form\Fieldset\FooFieldset',
],
... and tried to use it instead of Storage\Form\Fieldset\FooFieldset
in my form class. But now I get an exception:
Zend\Form\FormElementManager::get was unable to fetch or create an instance for Storage\Form\Fieldset\Foo
I've also tried this directly:
'service_manager' => [
'factories' => [
'Storage\Form\Fieldset\Foo' => 'Storage\Form\Fieldset\Factory\FooFieldsetFactory',
],
],
No effect, the same error.
And this also didn't work (the same error):
'form_elements' => [
'factories' => [
'Storage\Form\Fieldset\Foo' => 'Storage\Form\Fieldset\Factory\FooFieldsetFactory',
],
],
So the referencing a service for a fieldset seems not to work. Or am I doing something wrong?
How to use services for form fieldsets?
UPDATE
With some debuggin I found out, that my Foo
fieldset factory cannot be found, because it has not be added to the factories
list of the Zend\Form\FormElementManager
. Here is the place in the Zend\Form\Factory
:
So my config
'form_elements' => [
'factories' => [
'Storage\Form\Fieldset\Foo' => 'Storage\Form\Fieldset\Factory\FooFieldsetFactory',
],
],
is ignored. How to fix this?
UPDATE Additional information, how I'm creating my Form
object.
/module/Foo/config/module.config.php
return [
'controllers' => [
'factories' => [
'Foo\Controller\My' => 'Foo\Controller\Factory\MyControllerFactory'
]
],
'service_manager' => [
'factories' => [
'Foo\Form\MyForm' => 'Foo\Form\Factory\MyFormFactory',
],
],
];
/module/Foo/src/Foo/Form/Factory/MyFormFactory.php
namespace Foo\Form\Factory;
use ...;
class MyFormFactory implements FactoryInterface
{
public function createService(ServiceLocatorInterface $serviceLocator)
{
$form = new MyForm();
$form->setAttribute('method', 'post')
->setHydrator(new ClassMethods())
->setInputFilter(new InputFilter());
return $form;
}
}
/module/Foo/src/Foo/Controller/Factory/MyControllerFactory.php
namespace Foo\Controller\Factory;
use ...;
class MyControllerFactory implements FactoryInterface
{
public function createService(ServiceLocatorInterface $serviceLocator)
{
$fooPrototype = new Foo();
$realServiceLocator = $serviceLocator->getServiceLocator();
// $myForm = $realServiceLocator->get('Foo\Form\MyForm'); <-- This doesn't work correctly for this case. The FormElementManager should be used instead.
$formElementManager = $realServiceLocator->get('FormElementManager');
$myForm = $formElementManager->get('Foo\Form\MyForm');
return new MyController($myForm, $fooPrototype);
}
}