Skip to content

Commit d76f046

Browse files
committed
feature #4875 Added chapter about the locale based on the user entity (peterrehm)
This PR was merged into the 2.3 branch. Discussion ---------- Added chapter about the locale based on the user entity | Q | A | ------------- | --- | Doc fix? | no | New docs? | yes | Applies to | 2.3 | Fixed tickets | #4862 Commits ------- 1aaa491 Updated as per feedback. 0fc72a8 Updated as per feedback 6e986e1 Updated wording of the chapter as per discussion 66e21a9 Added chapter about the locale based on the user entity
2 parents 0d1e97e + 1aaa491 commit d76f046

File tree

1 file changed

+109
-0
lines changed

1 file changed

+109
-0
lines changed

Diff for: cookbook/session/locale_sticky_session.rst

+109
Original file line numberDiff line numberDiff line change
@@ -106,3 +106,112 @@ method::
106106
{
107107
$locale = $request->getLocale();
108108
}
109+
110+
Setting the Locale Based on the User's Preferences
111+
--------------------------------------------------
112+
113+
You might want to improve this technique even further and define the locale based on
114+
the user entity of the logged in user. However, since the ``LocaleListener`` is called
115+
before the ``FirewallListener``, which is responsible for handling authentication and
116+
is setting the user token into the ``TokenStorage``, you have no access to the user
117+
which is logged in.
118+
119+
Let's pretend you have defined a property "locale" in your user entity which you
120+
want to be used as the locale for the given user. In order to achieve the wanted locale
121+
configuration, you can set the locale which is defined for the user to the session right
122+
after the login. Fortunately, you can hook into the login process and update the user's
123+
session before the redirect to the first page. For this you need an event listener for the
124+
``security.interactive_login`` event:
125+
126+
.. code-block:: php
127+
128+
// src/AppBundle/EventListener/UserLocaleListener.php
129+
namespace AppBundle\EventListener;
130+
131+
use Symfony\Component\HttpFoundation\Session\Session;
132+
use Symfony\Component\Security\Http\Event\InteractiveLoginEvent;
133+
134+
/**
135+
* Stores the locale of the user in the session after the
136+
* login. This can be used by the LocaleListener afterwards.
137+
*/
138+
class UserLocaleListener
139+
{
140+
/**
141+
* @var Session
142+
*/
143+
private $session;
144+
145+
public function __construct(Session $session)
146+
{
147+
$this->session = $session;
148+
}
149+
150+
/**
151+
* @param InteractiveLoginEvent $event
152+
*/
153+
public function onInteractiveLogin(InteractiveLoginEvent $event)
154+
{
155+
$user = $event->getAuthenticationToken()->getUser();
156+
157+
if (null !== $user->getLocale()) {
158+
$this->session->set('_locale', $user->getLocale());
159+
}
160+
}
161+
}
162+
163+
Then register the listener:
164+
165+
.. configuration-block::
166+
167+
.. code-block:: yaml
168+
169+
# app/config/services.yml
170+
services:
171+
app.user_locale_listener:
172+
class: AppBundle\EventListener\UserLocaleListener
173+
arguments: [@session]
174+
tags:
175+
- { name: kernel.event_listener, event: security.interactive_login, method: onInteractiveLogin }
176+
177+
.. code-block:: xml
178+
179+
<!-- app/config/services.xml -->
180+
<?xml version="1.0" encoding="UTF-8" ?>
181+
<container xmlns="http://symfony.com/schema/dic/services"
182+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
183+
xsi:schemaLocation="http://symfony.com/schema/dic/services
184+
http://symfony.com/schema/dic/services/services-1.0.xsd">
185+
186+
<services>
187+
<service id="app.user_locale_listener"
188+
class="AppBundle\EventListener\UserLocaleListener">
189+
190+
<argument type="service" id="session"/>
191+
192+
<tag name="kernel.event_listener"
193+
event="security.interactive_login"
194+
method="onInteractiveLogin" />
195+
</service>
196+
</services>
197+
</container>
198+
199+
.. code-block:: php
200+
201+
// app/config/services.php
202+
$container
203+
->register('app.user_locale_listener', 'AppBundle\EventListener\UserLocaleListener')
204+
->addArgument('session')
205+
->addTag(
206+
'kernel.event_listener',
207+
array('event' => 'security.interactive_login', 'method' => 'onInteractiveLogin'
208+
);
209+
210+
.. caution::
211+
212+
With this configuration you are all set for having the locale based on the user's
213+
locale. If however the locale changes during the session, it would not be updated
214+
since with the current implementation the user locale will only be stored to the
215+
session on login. In order to update the language immediately after a user has
216+
changed their language, you need to update the session after an update to
217+
the user entity.

0 commit comments

Comments
 (0)