Skip to content

Commit 16cab61

Browse files
author
Hugo Hamon
committed
[Form] use new service locator in DependencyInjectionExtension class, so that form types can be made private at some point.
1 parent fb65bd6 commit 16cab61

File tree

9 files changed

+337
-249
lines changed

9 files changed

+337
-249
lines changed

src/Symfony/Bundle/FrameworkBundle/Resources/config/form.xml

+25-15
Original file line numberDiff line numberDiff line change
@@ -30,17 +30,13 @@
3030

3131
<!-- DependencyInjectionExtension -->
3232
<service id="form.extension" class="Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension" public="false">
33-
<argument type="service" id="service_container" />
34-
<!-- All services with tag "form.type" are inserted here by FormPass -->
35-
<argument type="collection" />
36-
<!-- All services with tag "form.type_extension" are inserted here by FormPass -->
37-
<argument type="collection" />
38-
<!-- All services with tag "form.type_guesser" are inserted here by FormPass -->
39-
<argument type="collection" />
33+
<argument type="service-locator" /><!-- All services with tag "form.type" are stored in a service locator by FormPass -->
34+
<argument type="collection" /><!-- All services with tag "form.type_extension" are stored here by FormPass -->
35+
<argument type="iterator" /><!-- All services with tag "form.type_guesser" are stored here by FormPass -->
4036
</service>
4137

4238
<!-- ValidatorTypeGuesser -->
43-
<service id="form.type_guesser.validator" class="Symfony\Component\Form\Extension\Validator\ValidatorTypeGuesser">
39+
<service id="form.type_guesser.validator" class="Symfony\Component\Form\Extension\Validator\ValidatorTypeGuesser" public="false">
4440
<tag name="form.type_guesser" />
4541
<argument type="service" id="validator.mapping.class_metadata_factory" />
4642
</service>
@@ -61,7 +57,7 @@
6157

6258
<service id="form.choice_list_factory" alias="form.choice_list_factory.cached" public="false"/>
6359

64-
<service id="form.type.form" class="Symfony\Component\Form\Extension\Core\Type\FormType">
60+
<service id="form.type.form" class="Symfony\Component\Form\Extension\Core\Type\FormType" public="false">
6561
<argument type="service" id="form.property_accessor" />
6662
<tag name="form.type" />
6763
</service>
@@ -71,7 +67,7 @@
7167
<service id="form.type.checkbox" class="Symfony\Component\Form\Extension\Core\Type\CheckboxType">
7268
<deprecated>The "%service_id%" service is deprecated since Symfony 3.1 and will be removed in 4.0.</deprecated>
7369
</service>
74-
<service id="form.type.choice" class="Symfony\Component\Form\Extension\Core\Type\ChoiceType">
70+
<service id="form.type.choice" class="Symfony\Component\Form\Extension\Core\Type\ChoiceType" public="false">
7571
<tag name="form.type" />
7672
<argument type="service" id="form.choice_list_factory"/>
7773
</service>
@@ -158,7 +154,7 @@
158154
</service>
159155

160156
<!-- FormTypeHttpFoundationExtension -->
161-
<service id="form.type_extension.form.http_foundation" class="Symfony\Component\Form\Extension\HttpFoundation\Type\FormTypeHttpFoundationExtension">
157+
<service id="form.type_extension.form.http_foundation" class="Symfony\Component\Form\Extension\HttpFoundation\Type\FormTypeHttpFoundationExtension" public="false">
162158
<argument type="service" id="form.type_extension.form.request_handler" />
163159
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\FormType" />
164160
</service>
@@ -173,20 +169,34 @@
173169
</service>
174170

175171
<!-- FormTypeValidatorExtension -->
176-
<service id="form.type_extension.form.validator" class="Symfony\Component\Form\Extension\Validator\Type\FormTypeValidatorExtension">
172+
<service id="form.type_extension.form.validator" class="Symfony\Component\Form\Extension\Validator\Type\FormTypeValidatorExtension" public="false">
177173
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\FormType" />
178174
<argument type="service" id="validator" />
179175
</service>
180-
<service id="form.type_extension.repeated.validator" class="Symfony\Component\Form\Extension\Validator\Type\RepeatedTypeValidatorExtension">
176+
<service id="form.type_extension.repeated.validator" class="Symfony\Component\Form\Extension\Validator\Type\RepeatedTypeValidatorExtension" public="false">
181177
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\RepeatedType" />
182178
</service>
183-
<service id="form.type_extension.submit.validator" class="Symfony\Component\Form\Extension\Validator\Type\SubmitTypeValidatorExtension">
179+
<service id="form.type_extension.submit.validator" class="Symfony\Component\Form\Extension\Validator\Type\SubmitTypeValidatorExtension" public="false">
184180
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\SubmitType" />
185181
</service>
186-
<service id="form.type_extension.upload.validator" class="Symfony\Component\Form\Extension\Validator\Type\UploadValidatorExtension">
182+
<service id="form.type_extension.upload.validator" class="Symfony\Component\Form\Extension\Validator\Type\UploadValidatorExtension" public="false">
187183
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\FormType" />
188184
<argument type="service" id="translator"/>
189185
<argument type="string">%validator.translation_domain%</argument>
190186
</service>
187+
188+
<service id="deprecated.form.registry" class="stdClass">
189+
<property name="registry" type="collection">
190+
<property type="service" id="form.type_guesser.validator" />
191+
<property type="service" id="form.type.choice" />
192+
<property type="service" id="form.type.form" />
193+
<property type="service" id="form.type_extension.form.http_foundation" />
194+
<property type="service" id="form.type_extension.form.validator" />
195+
<property type="service" id="form.type_extension.repeated.validator" />
196+
<property type="service" id="form.type_extension.submit.validator" />
197+
<property type="service" id="form.type_extension.upload.validator" />
198+
</property>
199+
<deprecated>The service "%service_id%" is internal and deprecated since Symfony 3.3 and will be removed in Symfony 4.0</deprecated>
200+
</service>
191201
</services>
192202
</container>

src/Symfony/Bundle/FrameworkBundle/Resources/config/form_csrf.xml

+9-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
66

77
<services>
8-
<service id="form.type_extension.csrf" class="Symfony\Component\Form\Extension\Csrf\Type\FormTypeCsrfExtension">
8+
<service id="form.type_extension.csrf" class="Symfony\Component\Form\Extension\Csrf\Type\FormTypeCsrfExtension" public="false">
99
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\FormType" />
1010
<argument type="service" id="security.csrf.token_manager" />
1111
<argument>%form.type_extension.csrf.enabled%</argument>
@@ -14,5 +14,13 @@
1414
<argument>%validator.translation_domain%</argument>
1515
<argument type="service" id="form.server_params" />
1616
</service>
17+
18+
<service id="deprecated.form.registry.csrf" class="stdClass">
19+
<property name="registry" type="collection">
20+
<property type="service" id="form.type_extension.csrf" />
21+
</property>
22+
<deprecated>The service "%service_id%" is internal and deprecated since Symfony 3.3 and will be removed in Symfony 4.0</deprecated>
23+
</service>
24+
1725
</services>
1826
</container>

src/Symfony/Bundle/FrameworkBundle/Resources/config/form_debug.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
</service>
1414

1515
<!-- DataCollectorTypeExtension -->
16-
<service id="form.type_extension.form.data_collector" class="Symfony\Component\Form\Extension\DataCollector\Type\DataCollectorTypeExtension">
16+
<service id="form.type_extension.form.data_collector" class="Symfony\Component\Form\Extension\DataCollector\Type\DataCollectorTypeExtension" public="false">
1717
<tag name="form.type_extension" extended-type="Symfony\Component\Form\Extension\Core\Type\FormType" />
1818
<argument type="service" id="data_collector.form" />
1919
</service>

src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Compiler/FormPassTest.php

+68-80
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@
1313

1414
use PHPUnit\Framework\TestCase;
1515
use Symfony\Bundle\FrameworkBundle\DependencyInjection\Compiler\FormPass;
16+
use Symfony\Component\DependencyInjection\Argument\IteratorArgument;
17+
use Symfony\Component\DependencyInjection\Argument\ServiceLocatorArgument;
1618
use Symfony\Component\DependencyInjection\ContainerBuilder;
1719
use Symfony\Component\DependencyInjection\Definition;
1820
use Symfony\Component\DependencyInjection\Reference;
@@ -27,8 +29,7 @@ class FormPassTest extends TestCase
2729
{
2830
public function testDoNothingIfFormExtensionNotLoaded()
2931
{
30-
$container = new ContainerBuilder();
31-
$container->addCompilerPass(new FormPass());
32+
$container = $this->createContainerBuilder();
3233

3334
$container->compile();
3435

@@ -37,47 +38,33 @@ public function testDoNothingIfFormExtensionNotLoaded()
3738

3839
public function testAddTaggedTypes()
3940
{
40-
$container = new ContainerBuilder();
41-
$container->addCompilerPass(new FormPass());
42-
43-
$extDefinition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension');
44-
$extDefinition->setArguments(array(
45-
new Reference('service_container'),
46-
array(),
47-
array(),
48-
array(),
49-
));
41+
$container = $this->createContainerBuilder();
5042

51-
$container->setDefinition('form.extension', $extDefinition);
43+
$container->setDefinition('form.extension', $this->createExtensionDefinition());
5244
$container->register('my.type1', __CLASS__.'_Type1')->addTag('form.type');
5345
$container->register('my.type2', __CLASS__.'_Type2')->addTag('form.type');
5446

5547
$container->compile();
5648

5749
$extDefinition = $container->getDefinition('form.extension');
5850

59-
$this->assertEquals(array(
60-
__CLASS__.'_Type1' => 'my.type1',
61-
__CLASS__.'_Type2' => 'my.type2',
62-
), $extDefinition->getArgument(1));
51+
$this->assertEquals(
52+
new ServiceLocatorArgument(array(
53+
__CLASS__.'_Type1' => new Reference('my.type1'),
54+
__CLASS__.'_Type2' => new Reference('my.type2'),
55+
)),
56+
$extDefinition->getArgument(0)
57+
);
6358
}
6459

6560
/**
6661
* @dataProvider addTaggedTypeExtensionsDataProvider
6762
*/
6863
public function testAddTaggedTypeExtensions(array $extensions, array $expectedRegisteredExtensions)
6964
{
70-
$container = new ContainerBuilder();
71-
$container->addCompilerPass(new FormPass());
65+
$container = $this->createContainerBuilder();
7266

73-
$extDefinition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension', array(
74-
new Reference('service_container'),
75-
array(),
76-
array(),
77-
array(),
78-
));
79-
80-
$container->setDefinition('form.extension', $extDefinition);
67+
$container->setDefinition('form.extension', $this->createExtensionDefinition());
8168

8269
foreach ($extensions as $serviceId => $tag) {
8370
$container->register($serviceId, 'stdClass')->addTag('form.type_extension', $tag);
@@ -86,7 +73,7 @@ public function testAddTaggedTypeExtensions(array $extensions, array $expectedRe
8673
$container->compile();
8774

8875
$extDefinition = $container->getDefinition('form.extension');
89-
$this->assertSame($expectedRegisteredExtensions, $extDefinition->getArgument(2));
76+
$this->assertEquals($expectedRegisteredExtensions, $extDefinition->getArgument(1));
9077
}
9178

9279
/**
@@ -102,8 +89,11 @@ public function addTaggedTypeExtensionsDataProvider()
10289
'my.type_extension3' => array('extended_type' => 'type2'),
10390
),
10491
array(
105-
'type1' => array('my.type_extension1', 'my.type_extension2'),
106-
'type2' => array('my.type_extension3'),
92+
'type1' => new IteratorArgument(array(
93+
new Reference('my.type_extension1'),
94+
new Reference('my.type_extension2'),
95+
)),
96+
'type2' => new IteratorArgument(array(new Reference('my.type_extension3'))),
10797
),
10898
),
10999
array(
@@ -116,8 +106,16 @@ public function addTaggedTypeExtensionsDataProvider()
116106
'my.type_extension6' => array('extended_type' => 'type2', 'priority' => 1),
117107
),
118108
array(
119-
'type1' => array('my.type_extension2', 'my.type_extension1', 'my.type_extension3'),
120-
'type2' => array('my.type_extension4', 'my.type_extension5', 'my.type_extension6'),
109+
'type1' => new IteratorArgument(array(
110+
new Reference('my.type_extension2'),
111+
new Reference('my.type_extension1'),
112+
new Reference('my.type_extension3'),
113+
)),
114+
'type2' => new IteratorArgument(array(
115+
new Reference('my.type_extension4'),
116+
new Reference('my.type_extension5'),
117+
new Reference('my.type_extension6'),
118+
)),
121119
),
122120
),
123121
);
@@ -129,17 +127,9 @@ public function addTaggedTypeExtensionsDataProvider()
129127
*/
130128
public function testAddTaggedFormTypeExtensionWithoutExtendedTypeAttribute()
131129
{
132-
$container = new ContainerBuilder();
133-
$container->addCompilerPass(new FormPass());
130+
$container = $this->createContainerBuilder();
134131

135-
$extDefinition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension', array(
136-
new Reference('service_container'),
137-
array(),
138-
array(),
139-
array(),
140-
));
141-
142-
$container->setDefinition('form.extension', $extDefinition);
132+
$container->setDefinition('form.extension', $this->createExtensionDefinition());
143133
$container->register('my.type_extension', 'stdClass')
144134
->addTag('form.type_extension');
145135

@@ -148,73 +138,71 @@ public function testAddTaggedFormTypeExtensionWithoutExtendedTypeAttribute()
148138

149139
public function testAddTaggedGuessers()
150140
{
151-
$container = new ContainerBuilder();
152-
$container->addCompilerPass(new FormPass());
153-
154-
$extDefinition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension');
155-
$extDefinition->setArguments(array(
156-
new Reference('service_container'),
157-
array(),
158-
array(),
159-
array(),
160-
));
141+
$container = $this->createContainerBuilder();
161142

162143
$definition1 = new Definition('stdClass');
163144
$definition1->addTag('form.type_guesser');
164145
$definition2 = new Definition('stdClass');
165146
$definition2->addTag('form.type_guesser');
166147

167-
$container->setDefinition('form.extension', $extDefinition);
148+
$container->setDefinition('form.extension', $this->createExtensionDefinition());
168149
$container->setDefinition('my.guesser1', $definition1);
169150
$container->setDefinition('my.guesser2', $definition2);
170151

171152
$container->compile();
172153

173154
$extDefinition = $container->getDefinition('form.extension');
174155

175-
$this->assertSame(array(
176-
'my.guesser1',
177-
'my.guesser2',
178-
), $extDefinition->getArgument(3));
156+
$this->assertEquals(
157+
new IteratorArgument(array(
158+
new Reference('my.guesser1'),
159+
new Reference('my.guesser2'),
160+
)),
161+
$extDefinition->getArgument(2)
162+
);
179163
}
180164

181165
/**
182166
* @dataProvider privateTaggedServicesProvider
183167
*/
184-
public function testPrivateTaggedServices($id, $tagName, $expectedExceptionMessage)
168+
public function testPrivateTaggedServices($id, $tagName, array $tagAttributes = array())
185169
{
186-
$container = new ContainerBuilder();
187-
$container->addCompilerPass(new FormPass());
188-
189-
$extDefinition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension');
190-
$extDefinition->setArguments(array(
191-
new Reference('service_container'),
192-
array(),
193-
array(),
194-
array(),
195-
));
196-
197-
$container->setDefinition('form.extension', $extDefinition);
198-
$container->register($id, 'stdClass')->setPublic(false)->addTag($tagName);
170+
$container = $this->createContainerBuilder();
199171

200-
if (method_exists($this, 'expectException')) {
201-
$this->expectException('InvalidArgumentException');
202-
$this->expectExceptionMessage($expectedExceptionMessage);
203-
} else {
204-
$this->setExpectedException('InvalidArgumentException', $expectedExceptionMessage);
205-
}
172+
$container->setDefinition('form.extension', $this->createExtensionDefinition());
173+
$container->register($id, 'stdClass')->setPublic(false)->addTag($tagName, $tagAttributes);
206174

207175
$container->compile();
208176
}
209177

210178
public function privateTaggedServicesProvider()
211179
{
212180
return array(
213-
array('my.type', 'form.type', 'The service "my.type" must be public as form types are lazy-loaded'),
214-
array('my.type_extension', 'form.type_extension', 'The service "my.type_extension" must be public as form type extensions are lazy-loaded'),
215-
array('my.guesser', 'form.type_guesser', 'The service "my.guesser" must be public as form type guessers are lazy-loaded'),
181+
array('my.type', 'form.type'),
182+
array('my.type_extension', 'form.type_extension', array('extended_type' => 'Symfony\Component\Form\Extension\Core\Type\FormType')),
183+
array('my.guesser', 'form.type_guesser'),
216184
);
217185
}
186+
187+
private function createContainerBuilder()
188+
{
189+
$container = new ContainerBuilder();
190+
$container->addCompilerPass(new FormPass());
191+
192+
return $container;
193+
}
194+
195+
private function createExtensionDefinition()
196+
{
197+
$definition = new Definition('Symfony\Component\Form\Extension\DependencyInjection\DependencyInjectionExtension');
198+
$definition->setArguments(array(
199+
new ServiceLocatorArgument(array()),
200+
array(),
201+
new IteratorArgument(array()),
202+
));
203+
204+
return $definition;
205+
}
218206
}
219207

220208
class FormPassTest_Type1 extends AbstractType

0 commit comments

Comments
 (0)