Skip to content
This repository was archived by the owner on Jan 30, 2020. It is now read-only.

Commit 1f773ec

Browse files
committed
Merge branch 'hotfix/form_elements-service-config' into develop
Forward port #164
2 parents 8d9b178 + bb98e05 commit 1f773ec

File tree

3 files changed

+128
-3
lines changed

3 files changed

+128
-3
lines changed

CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,12 @@ All notable changes to this project will be documented in this file, in reverse
4040
statement to the `ElementFactory`, fixing an error whereby checks for
4141
`Traversable` creation options would lead to a service creation exception;
4242
these now correctly identify traversable options and convert them to an array.
43+
- [#164](https://github.com/zendframework/zend-form/pull/164) fixes how the
44+
`FormElementManagerFactory` factory initializes the plugin manager instance,
45+
ensuring it is injecting the relevant configuration from the `config` service
46+
and thus seeding it with configured form/form element services. This means
47+
that the `form_elements` configuration will now be honored in non-zend-mvc
48+
contexts.
4349

4450
## 2.10.1 - 2017-04-26
4551

src/FormElementManagerFactory.php

Lines changed: 25 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99

1010
use Interop\Container\ContainerInterface;
1111
use Zend\ServiceManager\AbstractPluginManager;
12+
use Zend\ServiceManager\Config;
1213
use Zend\ServiceManager\FactoryInterface;
1314
use Zend\ServiceManager\ServiceLocatorInterface;
1415

@@ -28,11 +29,32 @@ class FormElementManagerFactory implements FactoryInterface
2829
*/
2930
public function __invoke(ContainerInterface $container, $name, array $options = null)
3031
{
31-
if ($this->isV3Container()) {
32-
return new FormElementManager\FormElementManagerV3Polyfill($container, $options ?: []);
32+
$pluginManager = $this->isV3Container()
33+
? new FormElementManager\FormElementManagerV3Polyfill($container, $options ?: [])
34+
: new FormElementManager\FormElementManagerV2Polyfill($container, $options ?: []);
35+
36+
// If this is in a zend-mvc application, the ServiceListener will inject
37+
// merged configuration during bootstrap.
38+
if ($container->has('ServiceListener')) {
39+
return $pluginManager;
40+
}
41+
42+
// If we do not have a config service, nothing more to do
43+
if (! $container->has('config')) {
44+
return $pluginManager;
3345
}
3446

35-
return new FormElementManager\FormElementManagerV2Polyfill($container, $options ?: []);
47+
$config = $container->get('config');
48+
49+
// If we do not have form_elements configuration, nothing more to do
50+
if (! isset($config['form_elements']) || ! is_array($config['form_elements'])) {
51+
return $pluginManager;
52+
}
53+
54+
// Wire service configuration for forms and elements
55+
(new Config($config['form_elements']))->configureServiceManager($pluginManager);
56+
57+
return $pluginManager;
3658
}
3759

3860
/**

test/FormElementManagerFactoryTest.php

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
use Interop\Container\ContainerInterface;
1111
use PHPUnit\Framework\TestCase;
1212
use Zend\Form\ElementInterface;
13+
use Zend\Form\Element\Number;
1314
use Zend\Form\FormElementManager;
1415
use Zend\Form\FormElementManagerFactory;
1516
use Zend\ServiceManager\ServiceLocatorInterface;
@@ -70,4 +71,100 @@ public function testFactoryConfiguresPluginManagerUnderServiceManagerV2()
7071
$elements = $factory->createService($container->reveal());
7172
$this->assertSame($element, $elements->get('test'));
7273
}
74+
75+
public function testConfiguresFormElementsServicesWhenFound()
76+
{
77+
$element = $this->prophesize(ElementInterface::class)->reveal();
78+
$config = [
79+
'form_elements' => [
80+
'aliases' => [
81+
'test' => Number::class,
82+
],
83+
'factories' => [
84+
'test-too' => function ($container) use ($element) {
85+
return $element;
86+
},
87+
],
88+
],
89+
];
90+
91+
$container = $this->prophesize(ServiceLocatorInterface::class);
92+
$container->willImplement(ContainerInterface::class);
93+
94+
$container->has('ServiceListener')->willReturn(false);
95+
$container->has('config')->willReturn(true);
96+
$container->get('config')->willReturn($config);
97+
98+
$factory = new FormElementManagerFactory();
99+
$elements = $factory($container->reveal(), 'FormElementManager');
100+
101+
$this->assertInstanceOf(FormElementManager::class, $elements);
102+
$this->assertTrue($elements->has('test'));
103+
$this->assertInstanceOf(Number::class, $elements->get('test'));
104+
$this->assertTrue($elements->has('test-too'));
105+
$this->assertSame($element, $elements->get('test-too'));
106+
}
107+
108+
public function testDoesNotConfigureFormElementsServicesWhenServiceListenerPresent()
109+
{
110+
$element = $this->prophesize(ElementInterface::class)->reveal();
111+
$config = [
112+
'form_elements' => [
113+
'aliases' => [
114+
'test' => Number::class,
115+
],
116+
'factories' => [
117+
'test-too' => function ($container) use ($element) {
118+
return $element;
119+
},
120+
],
121+
],
122+
];
123+
124+
$container = $this->prophesize(ServiceLocatorInterface::class);
125+
$container->willImplement(ContainerInterface::class);
126+
127+
$container->has('ServiceListener')->willReturn(true);
128+
$container->has('config')->shouldNotBeCalled();
129+
$container->get('config')->shouldNotBeCalled();
130+
131+
$factory = new FormElementManagerFactory();
132+
$elements = $factory($container->reveal(), 'FormElementManager');
133+
134+
$this->assertInstanceOf(FormElementManager::class, $elements);
135+
$this->assertFalse($elements->has('test'));
136+
$this->assertFalse($elements->has('test-too'));
137+
}
138+
139+
public function testDoesNotConfigureFormElementsServicesWhenConfigServiceNotPresent()
140+
{
141+
$container = $this->prophesize(ServiceLocatorInterface::class);
142+
$container->willImplement(ContainerInterface::class);
143+
144+
$container->has('ServiceListener')->willReturn(false);
145+
$container->has('config')->willReturn(false);
146+
$container->get('config')->shouldNotBeCalled();
147+
148+
$factory = new FormElementManagerFactory();
149+
$elements = $factory($container->reveal(), 'FormElementManager');
150+
151+
$this->assertInstanceOf(FormElementManager::class, $elements);
152+
}
153+
154+
public function testDoesNotConfigureFormElementServicesWhenConfigServiceDoesNotContainFormElementsConfig()
155+
{
156+
$container = $this->prophesize(ServiceLocatorInterface::class);
157+
$container->willImplement(ContainerInterface::class);
158+
159+
$container->has('ServiceListener')->willReturn(false);
160+
$container->has('config')->willReturn(true);
161+
$container->get('config')->willReturn(['foo' => 'bar']);
162+
$container->has('MvcTranslator')->willReturn(false); // necessary due to default initializers
163+
164+
$factory = new FormElementManagerFactory();
165+
$elements = $factory($container->reveal(), 'FormElementManager');
166+
167+
$this->assertInstanceOf(FormElementManager::class, $elements);
168+
$this->assertFalse($elements->has('foo'));
169+
}
73170
}

0 commit comments

Comments
 (0)