Skip to content

[DI] Updated the way inner services are referrer to in decoration #13545

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 20, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion reference/configuration/framework.rst
Original file line number Diff line number Diff line change
Expand Up @@ -2850,7 +2850,7 @@ Name of the lock you want to create.
lock.invoice.retry_till_save.store:
class: Symfony\Component\Lock\Store\RetryTillSaveStore
decorates: lock.invoice.store
arguments: ['@lock.invoice.retry_till_save.store.inner', 100, 50]
arguments: ['@.inner', 100, 50]

workflows
~~~~~~~~~
Expand Down
38 changes: 22 additions & 16 deletions service_container/service_decoration.rst
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ Most of the time, that's exactly what you want to do. But sometimes,
you might want to decorate the old one instead (i.e. apply the `Decorator pattern`_).
In this case, the old service should be kept around to be able to reference
it in the new one. This configuration replaces ``App\Mailer`` with a new one,
but keeps a reference of the old one as ``App\DecoratingMailer.inner``:
but keeps a reference of the old one as ``.inner``:

.. configuration-block::

Expand All @@ -70,7 +70,7 @@ but keeps a reference of the old one as ``App\DecoratingMailer.inner``:

App\DecoratingMailer:
# overrides the App\Mailer service
# but that service is still available as App\DecoratingMailer.inner
# but that service is still available as ".inner"
decorates: App\Mailer

.. code-block:: xml
Expand All @@ -84,6 +84,8 @@ but keeps a reference of the old one as ``App\DecoratingMailer.inner``:
<services>
<service id="App\Mailer"/>

<!-- overrides the App\Mailer service
but that service is still available as ".inner" -->
<service id="App\DecoratingMailer"
decorates="App\Mailer"
/>
Expand All @@ -106,7 +108,7 @@ but keeps a reference of the old one as ``App\DecoratingMailer.inner``:

$services->set(DecoratingMailer::class)
// overrides the App\Mailer service
// but that service is still available as App\DecoratingMailer.inner
// but that service is still available as ".inner"
->decorate(Mailer::class);
};

Expand All @@ -119,7 +121,7 @@ decorating service has one argument type-hinted with the decorated service class
If you are not using autowiring or the decorating service has more than one
constructor argument type-hinted with the decorated service class, you must
inject the decorated service explicitly (the ID of the decorated service is
automatically changed to ``decorating_service_id + '.inner'``):
automatically changed to ``'.inner'``):

.. configuration-block::

Expand All @@ -132,7 +134,7 @@ automatically changed to ``decorating_service_id + '.inner'``):
App\DecoratingMailer:
decorates: App\Mailer
# pass the old service as an argument
arguments: ['@App\DecoratingMailer.inner']
arguments: ['@.inner']

.. code-block:: xml

Expand All @@ -148,7 +150,7 @@ automatically changed to ``decorating_service_id + '.inner'``):
<service id="App\DecoratingMailer"
decorates="App\Mailer"
>
<argument type="service" id="App\DecoratingMailer.inner"/>
<argument type="service" id=".inner"/>
</service>

</services>
Expand All @@ -170,9 +172,13 @@ automatically changed to ``decorating_service_id + '.inner'``):
$services->set(DecoratingMailer::class)
->decorate(Mailer::class)
// pass the old service as an argument
->args([ref(DecoratingMailer::class.'.inner')]);
->args([ref('.inner')]);
};

.. versionadded:: 5.1

The special ``.inner`` value was introduced in Symfony 5.1. In previous
versions you needed to use: ``decorating_service_id + '.inner'``.

.. tip::

Expand Down Expand Up @@ -256,12 +262,12 @@ the ``decoration_priority`` option. Its value is an integer that defaults to
Bar:
decorates: Foo
decoration_priority: 5
arguments: ['@Bar.inner']
arguments: ['@.inner']

Baz:
decorates: Foo
decoration_priority: 1
arguments: ['@Baz.inner']
arguments: ['@.inner']

.. code-block:: xml

Expand All @@ -276,11 +282,11 @@ the ``decoration_priority`` option. Its value is an integer that defaults to
<service id="Foo"/>

<service id="Bar" decorates="Foo" decoration-priority="5">
<argument type="service" id="Bar.inner"/>
<argument type="service" id=".inner"/>
</service>

<service id="Baz" decorates="Foo" decoration-priority="1">
<argument type="service" id="Baz.inner"/>
<argument type="service" id=".inner"/>
</service>
</services>
</container>
Expand All @@ -297,11 +303,11 @@ the ``decoration_priority`` option. Its value is an integer that defaults to

$services->set(Bar::class)
->decorate(Foo::class, null, 5)
->args([ref(Bar::class.'.inner')]);
->args([ref('.inner')]);

$services->set(Baz::class)
->decorate(Foo::class, null, 1)
->args([ref(Baz::class.'.inner')]);
->args([ref('.inner')]);
};


Expand Down Expand Up @@ -331,7 +337,7 @@ Three different behaviors are available:
Bar:
decorates: Foo
decoration_on_invalid: ignore
arguments: ['@Bar.inner']
arguments: ['@.inner']

.. code-block:: xml

Expand All @@ -346,7 +352,7 @@ Three different behaviors are available:
<service id="Foo"/>

<service id="Bar" decorates="Foo" decoration-on-invalid="ignore">
<argument type="service" id="Bar.inner"/>
<argument type="service" id=".inner"/>
</service>
</services>
</container>
Expand All @@ -365,7 +371,7 @@ Three different behaviors are available:

$services->set(Bar::class)
->decorate(Foo::class, null, 0, ContainerInterface::IGNORE_ON_INVALID_REFERENCE)
->args([ref(Bar::class.'.inner')])
->args([ref('.inner')])
;
};

Expand Down