You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
feature #28738 [OptionsResolver] Passing Options argument to deprecation closure (yceruto)
This PR was squashed before being merged into the 4.2-dev branch (closes#28738).
Discussion
----------
[OptionsResolver] Passing Options argument to deprecation closure
| Q | A
| ------------- | ---
| Branch? | master
| Bug fix? | no
| New feature? | yes
| BC breaks? | no
| Deprecations? | no
| Tests pass? | yes
| Fixed tickets | #28721 (comment)
| License | MIT
| Doc PR | symfony/symfony-docs#10439
As spotted here #28721, we sometimes need more advanced cases, where the deprecation of the value depends on another option:
```php
$resolver->setDeprecated('date_format', function (Options $options, $dateFormat) {
if (null !== $options['date_format'] && 'single_text' === $options['widget']) {
return sprintf('Using the "date_format" option of the %s when the "widget" option is set to "single_text" is deprecated since Symfony 4.2.', self::class);
}
return '';
});
```
There is still a decision to make:
> We're in time to change the arguments position (Options $options, $value) to be consistent with other closure signatures.
WDYT?
Commits
-------
2936051 [OptionsResolver] Passing Options argument to deprecation closure
Copy file name to clipboardExpand all lines: src/Symfony/Component/OptionsResolver/OptionsResolver.php
+16-4Lines changed: 16 additions & 4 deletions
Original file line number
Diff line number
Diff line change
@@ -360,12 +360,12 @@ public function getDefinedOptions()
360
360
* Instead of passing the message, you may also pass a closure with the
361
361
* following signature:
362
362
*
363
-
* function ($value) {
363
+
* function (Options $options, $value): string {
364
364
* // ...
365
365
* }
366
366
*
367
367
* The closure receives the value as argument and should return a string.
368
-
* Returns an empty string to ignore the option deprecation.
368
+
* Return an empty string to ignore the option deprecation.
369
369
*
370
370
* The closure is invoked when {@link resolve()} is called. The parameter
371
371
* passed to the closure is the value of the option after validating it
@@ -860,8 +860,20 @@ public function offsetGet($option)
860
860
if (isset($this->deprecated[$option])) {
861
861
$deprecationMessage = $this->deprecated[$option];
862
862
863
-
if ($deprecationMessageinstanceof \Closure && !\is_string($deprecationMessage = $deprecationMessage($value))) {
864
-
thrownewInvalidOptionsException(sprintf('Invalid type for deprecation message, expected string but got "%s", returns an empty string to ignore.', \gettype($deprecationMessage)));
863
+
if ($deprecationMessageinstanceof \Closure) {
864
+
// If the closure is already being called, we have a cyclic dependency
865
+
if (isset($this->calling[$option])) {
866
+
thrownewOptionDefinitionException(sprintf('The options "%s" have a cyclic dependency.', implode('", "', array_keys($this->calling))));
867
+
}
868
+
869
+
$this->calling[$option] = true;
870
+
try {
871
+
if (!\is_string($deprecationMessage = $deprecationMessage($this, $value))) {
872
+
thrownewInvalidOptionsException(sprintf('Invalid type for deprecation message, expected string but got "%s", return an empty string to ignore.', \gettype($deprecationMessage)));
0 commit comments