Skip to content

Commit a6f969d

Browse files
committed
feature symfony#61718 [Config] Add argument $singular to NodeBuilder::arrayNode() to decouple plurals/singulars from XML (nicolas-grekas)
This PR was merged into the 7.4 branch. Discussion ---------- [Config] Add argument `$singular` to `NodeBuilder::arrayNode()` to decouple plurals/singulars from XML | Q | A | ------------- | --- | Branch? | 7.4 | Bug fix? | no | New feature? | yes | Deprecations? | no | Issues | - | License | MIT The capability of defining plural/singular variants for config node is used not only for XML but also for config builders generation. The current method to deal with this concern is named `fixXmlConfig()`. It's confusing to say the least. What's also confusing is that the call needs to happen on the parent node. This PR proposes to add a second argument to the `arrayNode()` method, so that things could be changed like this (example taken from the attached patch): ```diff $rootNode - ->fixXmlConfig('role', 'role_hierarchy') ->children() - ->arrayNode('role_hierarchy') + ->arrayNode('role_hierarchy', 'role') ``` I'm not deprecating the `fixXmlConfig()` method - it would be way too early. ~In a follow up PR, I'll try to require setting this second argument (or calling fixXmlConfig) when a prototype is defined. If possible.~ Commits ------- 5ac6e74 [Config] Add argument $singular to NodeBuilder::arrayNode() to decouple plurals/singulars from XML
2 parents 2471df3 + 5ac6e74 commit a6f969d

File tree

20 files changed

+191
-259
lines changed

20 files changed

+191
-259
lines changed

src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php

Lines changed: 86 additions & 178 deletions
Large diffs are not rendered by default.

src/Symfony/Bundle/FrameworkBundle/Tests/CacheWarmer/ConfigBuilderCacheWarmerTest.php

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -412,9 +412,8 @@ public function getConfigTreeBuilder(): TreeBuilder
412412
$rootNode = $treeBuilder->getRootNode();
413413

414414
$firewallNodeBuilder = $rootNode
415-
->fixXmlConfig('firewall')
416415
->children()
417-
->arrayNode('firewalls')
416+
->arrayNode('firewalls', 'firewall')
418417
->isRequired()
419418
->requiresAtLeastOneElement()
420419
->useAttributeAsKey('name')

src/Symfony/Bundle/FrameworkBundle/composer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
"composer-runtime-api": ">=2.1",
2121
"ext-xml": "*",
2222
"symfony/cache": "^6.4.12|^7.0|^8.0",
23-
"symfony/config": "^7.3|^8.0",
23+
"symfony/config": "^7.4|^8.0",
2424
"symfony/dependency-injection": "^7.2|^8.0",
2525
"symfony/deprecation-contracts": "^2.5|^3",
2626
"symfony/error-handler": "^7.3|^8.0",

src/Symfony/Bundle/SecurityBundle/DependencyInjection/MainConfiguration.php

Lines changed: 12 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -124,9 +124,8 @@ public function getConfigTreeBuilder(): TreeBuilder
124124
private function addRoleHierarchySection(ArrayNodeDefinition $rootNode): void
125125
{
126126
$rootNode
127-
->fixXmlConfig('role', 'role_hierarchy')
128127
->children()
129-
->arrayNode('role_hierarchy')
128+
->arrayNode('role_hierarchy', 'role')
130129
->useAttributeAsKey('id')
131130
->prototype('array')
132131
->performNoDeepMerging()
@@ -145,14 +144,10 @@ private function addRoleHierarchySection(ArrayNodeDefinition $rootNode): void
145144
private function addAccessControlSection(ArrayNodeDefinition $rootNode): void
146145
{
147146
$rootNode
148-
->fixXmlConfig('rule', 'access_control')
149147
->children()
150-
->arrayNode('access_control')
148+
->arrayNode('access_control', 'rule')
151149
->cannotBeOverwritten()
152150
->prototype('array')
153-
->fixXmlConfig('ip')
154-
->fixXmlConfig('method')
155-
->fixXmlConfig('attribute')
156151
->children()
157152
->scalarNode('request_matcher')->defaultNull()->end()
158153
->scalarNode('requires_channel')->defaultNull()->end()
@@ -163,24 +158,23 @@ private function addAccessControlSection(ArrayNodeDefinition $rootNode): void
163158
->end()
164159
->scalarNode('host')->defaultNull()->end()
165160
->integerNode('port')->defaultNull()->end()
166-
->arrayNode('ips')
161+
->arrayNode('ips', 'ip')
167162
->beforeNormalization()->ifString()->then(fn ($v) => [$v])->end()
168163
->prototype('scalar')->end()
169164
->end()
170-
->arrayNode('attributes')
165+
->arrayNode('attributes', 'attribute')
171166
->useAttributeAsKey('key')
172167
->prototype('scalar')->end()
173168
->end()
174169
->scalarNode('route')->defaultNull()->end()
175-
->arrayNode('methods')
170+
->arrayNode('methods', 'method')
176171
->beforeNormalization()->ifString()->then(fn ($v) => preg_split('/\s*,\s*/', $v))->end()
177172
->prototype('scalar')->end()
178173
->end()
179174
->scalarNode('allow_if')->defaultNull()->end()
180175
->end()
181-
->fixXmlConfig('role')
182176
->children()
183-
->arrayNode('roles')
177+
->arrayNode('roles', 'role')
184178
->beforeNormalization()->ifString()->then(fn ($v) => preg_split('/\s*,\s*/', $v))->end()
185179
->prototype('scalar')->end()
186180
->end()
@@ -197,15 +191,13 @@ private function addAccessControlSection(ArrayNodeDefinition $rootNode): void
197191
private function addFirewallsSection(ArrayNodeDefinition $rootNode, array $factories): void
198192
{
199193
$firewallNodeBuilder = $rootNode
200-
->fixXmlConfig('firewall')
201194
->children()
202-
->arrayNode('firewalls')
195+
->arrayNode('firewalls', 'firewall')
203196
->isRequired()
204197
->requiresAtLeastOneElement()
205198
->disallowNewKeysInSubsequentConfigs()
206199
->useAttributeAsKey('name')
207200
->prototype('array')
208-
->fixXmlConfig('required_badge')
209201
->children()
210202
;
211203

@@ -270,9 +262,8 @@ private function addFirewallsSection(ArrayNodeDefinition $rootNode, array $facto
270262
->end()
271263
->end()
272264
->end()
273-
->fixXmlConfig('delete_cookie')
274265
->children()
275-
->arrayNode('delete_cookies')
266+
->arrayNode('delete_cookies', 'delete_cookie')
276267
->normalizeKeys(false)
277268
->beforeNormalization()
278269
->ifTrue(fn ($v) => \is_array($v) && \is_int(key($v)))
@@ -300,7 +291,7 @@ private function addFirewallsSection(ArrayNodeDefinition $rootNode, array $facto
300291
->scalarNode('target_route')->defaultValue(null)->end()
301292
->end()
302293
->end()
303-
->arrayNode('required_badges')
294+
->arrayNode('required_badges', 'required_badge')
304295
->info('A list of badges that must be present on the authenticated passport.')
305296
->validate()
306297
->always()
@@ -364,9 +355,8 @@ private function addFirewallsSection(ArrayNodeDefinition $rootNode, array $facto
364355
private function addProvidersSection(ArrayNodeDefinition $rootNode): void
365356
{
366357
$providerNodeBuilder = $rootNode
367-
->fixXmlConfig('provider')
368358
->children()
369-
->arrayNode('providers')
359+
->arrayNode('providers', 'provider')
370360
->example([
371361
'my_memory_provider' => [
372362
'memory' => [
@@ -387,9 +377,8 @@ private function addProvidersSection(ArrayNodeDefinition $rootNode): void
387377
->children()
388378
->scalarNode('id')->end()
389379
->arrayNode('chain')
390-
->fixXmlConfig('provider')
391380
->children()
392-
->arrayNode('providers')
381+
->arrayNode('providers', 'provider')
393382
->beforeNormalization()
394383
->ifString()
395384
->then(fn ($v) => preg_split('/\s*,\s*/', $v))
@@ -423,9 +412,8 @@ private function addProvidersSection(ArrayNodeDefinition $rootNode): void
423412
private function addPasswordHashersSection(ArrayNodeDefinition $rootNode): void
424413
{
425414
$rootNode
426-
->fixXmlConfig('password_hasher')
427415
->children()
428-
->arrayNode('password_hashers')
416+
->arrayNode('password_hashers', 'password_hasher')
429417
->example([
430418
'App\Entity\User1' => 'auto',
431419
'App\Entity\User2' => [

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/AccessToken/OidcTokenHandlerFactory.php

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -90,8 +90,6 @@ public function addConfiguration(NodeBuilder $node): void
9090
{
9191
$node
9292
->arrayNode($this->getKey())
93-
->fixXmlConfig('issuer')
94-
->fixXmlConfig('algorithm')
9593
->validate()
9694
->ifTrue(static fn ($v) => !isset($v['algorithm']) && !isset($v['algorithms']))
9795
->thenInvalid('You must set either "algorithm" or "algorithms".')
@@ -151,7 +149,7 @@ public function addConfiguration(NodeBuilder $node): void
151149
->info('Audience set in the token, for validation purpose.')
152150
->isRequired()
153151
->end()
154-
->arrayNode('issuers')
152+
->arrayNode('issuers', 'issuer')
155153
->info('Issuers allowed to generate the token, for validation purpose.')
156154
->isRequired()
157155
->scalarPrototype()->end()
@@ -160,7 +158,7 @@ public function addConfiguration(NodeBuilder $node): void
160158
->info('Algorithm used to sign the token.')
161159
->setDeprecated('symfony/security-bundle', '7.1', 'The "%node%" option is deprecated and will be removed in 8.0. Use the "algorithms" option instead.')
162160
->end()
163-
->arrayNode('algorithms')
161+
->arrayNode('algorithms', 'algorithm')
164162
->info('Algorithms used to sign the token.')
165163
->isRequired()
166164
->scalarPrototype()->end()
@@ -173,14 +171,13 @@ public function addConfiguration(NodeBuilder $node): void
173171
->info('JSON-encoded JWKSet used to sign the token (must contain a list of valid public keys).')
174172
->end()
175173
->arrayNode('encryption')
176-
->fixXmlConfig('algorithm')
177174
->canBeEnabled()
178175
->children()
179176
->booleanNode('enforce')
180177
->info('When enabled, the token shall be encrypted.')
181178
->defaultFalse()
182179
->end()
183-
->arrayNode('algorithms')
180+
->arrayNode('algorithms', 'algorithm')
184181
->info('Algorithms used to decrypt the token.')
185182
->isRequired()
186183
->requiresAtLeastOneElement()

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/Factory/AccessTokenFactory.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,10 +43,10 @@ public function addConfiguration(NodeDefinition $node): void
4343
{
4444
parent::addConfiguration($node);
4545

46-
$builder = $node->fixXmlConfig('token_extractor')->children();
46+
$builder = $node->children();
4747
$builder
4848
->scalarNode('realm')->defaultNull()->end()
49-
->arrayNode('token_extractors')
49+
->arrayNode('token_extractors', 'token_extractor')
5050
->beforeNormalization()
5151
->ifString()
5252
->then(fn ($v) => [$v])

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/Factory/CustomAuthenticatorFactory.php

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -37,24 +37,24 @@ public function getKey(): string
3737
*/
3838
public function addConfiguration(NodeDefinition $builder): void
3939
{
40-
$builder
41-
->info('An array of service ids for all of your "authenticators".')
42-
->requiresAtLeastOneElement()
43-
->prototype('scalar')->end();
44-
4540
// get the parent array node builder ("firewalls") from inside the children builder
4641
$factoryRootNode = $builder->end()->end();
4742
$factoryRootNode
4843
->fixXmlConfig('custom_authenticator')
4944
->validate()
50-
->ifTrue(fn ($v) => isset($v['custom_authenticators']) && empty($v['custom_authenticators']))
45+
->ifTrue(fn ($v) => isset($v['custom_authenticators']) && !$v['custom_authenticators'])
5146
->then(function ($v) {
5247
unset($v['custom_authenticators']);
5348

5449
return $v;
5550
})
5651
->end()
5752
;
53+
54+
$builder
55+
->info('An array of service ids for all of your "authenticators".')
56+
->requiresAtLeastOneElement()
57+
->prototype('scalar')->end();
5858
}
5959

6060
public function createAuthenticator(ContainerBuilder $container, string $firewallName, array $config, string $userProviderId): array

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/Factory/LoginLinkFactory.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ class LoginLinkFactory extends AbstractFactory
3131
public function addConfiguration(NodeDefinition $node): void
3232
{
3333
/** @var NodeBuilder $builder */
34-
$builder = $node->fixXmlConfig('signature_property', 'signature_properties')->children();
34+
$builder = $node->children();
3535

3636
$builder
3737
->scalarNode('check_route')
@@ -42,7 +42,7 @@ public function addConfiguration(NodeDefinition $node): void
4242
->defaultFalse()
4343
->info('If true, only HTTP POST requests to "check_route" will be handled by the authenticator.')
4444
->end()
45-
->arrayNode('signature_properties')
45+
->arrayNode('signature_properties', 'signature_property')
4646
->isRequired()
4747
->prototype('scalar')->end()
4848
->requiresAtLeastOneElement()

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/Factory/RememberMeFactory.php

Lines changed: 3 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -125,26 +125,21 @@ public function getKey(): string
125125

126126
public function addConfiguration(NodeDefinition $node): void
127127
{
128-
$builder = $node
129-
->fixXmlConfig('signature_property', 'signature_properties')
130-
->fixXmlConfig('user_provider')
131-
->children()
132-
;
133-
128+
$builder = $node->children();
134129
$builder
135130
->scalarNode('secret')
136131
->cannotBeEmpty()
137132
->defaultValue('%kernel.secret%')
138133
->end()
139134
->scalarNode('service')->end()
140-
->arrayNode('user_providers')
135+
->arrayNode('user_providers', 'user_provider')
141136
->beforeNormalization()
142137
->ifString()->then(fn ($v) => [$v])
143138
->end()
144139
->prototype('scalar')->end()
145140
->end()
146141
->booleanNode('catch_exceptions')->defaultTrue()->end()
147-
->arrayNode('signature_properties')
142+
->arrayNode('signature_properties', 'signature_property')
148143
->prototype('scalar')->end()
149144
->requiresAtLeastOneElement()
150145
->info('An array of properties on your User that are used to sign the remember-me cookie. If any of these change, all existing cookies will become invalid.')

src/Symfony/Bundle/SecurityBundle/DependencyInjection/Security/UserProvider/InMemoryFactory.php

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,9 +45,8 @@ public function getKey(): string
4545
public function addConfiguration(NodeDefinition $node): void
4646
{
4747
$node
48-
->fixXmlConfig('user')
4948
->children()
50-
->arrayNode('users')
49+
->arrayNode('users', 'user')
5150
->useAttributeAsKey('identifier')
5251
->normalizeKeys(false)
5352
->prototype('array')

0 commit comments

Comments
 (0)