Skip to content

Commit 414b1ba

Browse files
committed
Merge branch '2.8' into 3.4
* 2.8: Avoiding authentication on every request with Guard [Filesystem] Improved the code of an example Removed another usage of mt_rand() Transition from mt_rand to random_int remove not existent label_attr options from buttons
2 parents 52a2239 + 6c17837 commit 414b1ba

File tree

6 files changed

+102
-11
lines changed

6 files changed

+102
-11
lines changed

components/filesystem.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ endpoint for filesystem operations::
2929
$fileSystem = new Filesystem();
3030

3131
try {
32-
$fileSystem->mkdir('/tmp/random/dir/'.mt_rand());
32+
$fileSystem->mkdir(sys_get_temp_dir().'/'.random_int(0, 1000));
3333
} catch (IOExceptionInterface $exception) {
3434
echo "An error occurred while creating your directory at ".$exception->getPath();
3535
}

controller.rst

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ This renders a page that prints a lucky (random) number::
2626
*/
2727
public function numberAction()
2828
{
29-
$number = mt_rand(0, 100);
29+
$number = random_int(0, 100);
3030

3131
return new Response(
3232
'<html><body>Lucky number: '.$number.'</body></html>'
@@ -68,7 +68,7 @@ class::
6868
*/
6969
public function numberAction($max)
7070
{
71-
$number = mt_rand(0, $max);
71+
$number = random_int(0, $max);
7272

7373
return new Response(
7474
'<html><body>Lucky number: '.$number.'</body></html>'

page_creation.rst

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ random) number and prints it. To do that, create a "Controller class" and a
5858
*/
5959
public function numberAction()
6060
{
61-
$number = mt_rand(0, 100);
61+
$number = random_int(0, 100);
6262

6363
return new Response(
6464
'<html><body>Lucky number: '.$number.'</body></html>'
@@ -128,7 +128,7 @@ variable so we can render that::
128128
*/
129129
public function numberAction()
130130
{
131-
$number = mt_rand(0, 100);
131+
$number = random_int(0, 100);
132132

133133
return $this->render('lucky/number.html.twig', array(
134134
'number' => $number,

reference/forms/types/reset.rst

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@ A button that resets all fields to their original values.
1212
| Inherited | - `attr`_ |
1313
| options | - `disabled`_ |
1414
| | - `label`_ |
15-
| | - `label_attr`_ |
1615
| | - `translation_domain`_ |
1716
+----------------------+---------------------------------------------------------------------+
1817
| Parent type | :doc:`ButtonType </reference/forms/types/button>` |
@@ -43,6 +42,4 @@ as a key. This can be useful when you need to set a custom class for the button:
4342

4443
.. include:: /reference/forms/types/options/button_label.rst.inc
4544

46-
.. include:: /reference/forms/types/options/label_attr.rst.inc
47-
4845
.. include:: /reference/forms/types/options/button_translation_domain.rst.inc

reference/forms/types/submit.rst

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@ A submit button.
1212
| Inherited | - `attr`_ |
1313
| options | - `disabled`_ |
1414
| | - `label`_ |
15-
| | - `label_attr`_ |
1615
| | - `label_format`_ |
1716
| | - `translation_domain`_ |
1817
| | - `validation_groups`_ |
@@ -54,8 +53,6 @@ as a key. This can be useful when you need to set a custom class for the button:
5453

5554
.. include:: /reference/forms/types/options/button_label.rst.inc
5655

57-
.. include:: /reference/forms/types/options/label_attr.rst.inc
58-
5956
.. include:: /reference/forms/types/options/label_format.rst.inc
6057

6158
.. include:: /reference/forms/types/options/button_translation_domain.rst.inc

security/guard_authentication.rst

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -536,6 +536,103 @@ and add the following logic::
536536
// ...
537537
}
538538

539+
Avoid Authenticating the Browser on Every Request
540+
-------------------------------------------------
541+
542+
If you create a Guard login system that's used by a browser and you're experiencing
543+
problems with your session or CSRF tokens, the cause could be bad behavior by your
544+
authenticator. When a Guard authenticator is meant to be used by a browser, you
545+
should *not* authenticate the user on *every* request. In other words, you need to
546+
make sure the ``getCredentials()`` method *only* returns a non-null value when
547+
you actually *need* to authenticate the user. Why? Because, when ``getCredentials()``
548+
returns a non-null value, for security purposes, the user's session is "migrated"
549+
to a new session id.
550+
551+
This is an edge-case, and unless you're having session or CSRF token issues, you
552+
can ignore this. Here is an example of good and bad behavior::
553+
554+
public function getCredentials(Request $request)
555+
{
556+
// GOOD behavior: only authenticate on a specific route
557+
if ($request->attributes->get('_route') !== 'login_route' || !$request->isMethod('POST')) {
558+
return null;
559+
}
560+
561+
// e.g. your login system authenticates by the user's IP address
562+
// BAD behavior: authentication will now execute on every request
563+
// even if the user is already authenticated (due to the session)
564+
return array('ip' => $request->getClientIp());
565+
}
566+
567+
The problem occurs when your browser-based authenticator tries to authenticate
568+
the user on *every* request - like in the IP address-based example above. There
569+
are two possible fixes:
570+
571+
1) If you do *not* need authentication to be stored in the session, set ``stateless: true``
572+
under your firewall.
573+
574+
2) Update your authenticator to avoid authentication if the user is already authenticated:
575+
576+
.. code-block:: diff
577+
578+
// src/Security/MyIpAuthenticator.php
579+
// ...
580+
581+
+ use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface;
582+
583+
class MyIpAuthenticator
584+
{
585+
+ private $tokenStorage;
586+
587+
+ public function __construct(TokenStorageInterface $tokenStorage)
588+
+ {
589+
+ $this->tokenStorage = $tokenStorage;
590+
+ }
591+
592+
public function getCredentials(Request $request)
593+
{
594+
+ // if there is already an authenticated user (likely due to the session)
595+
+ // then return null and skip authentication: there is no need.
596+
+ $user = $this->tokenStorage->getToken() ? $this->tokenStorage->getToken()->getUser() : null;
597+
+ if (is_object($user)) {
598+
+ return null;
599+
+ }
600+
601+
return array('ip' => $request->getClientIp());
602+
}
603+
}
604+
605+
You'll also need to update your service configuration to pass the token storage:
606+
607+
.. configuration-block::
608+
609+
.. code-block:: yaml
610+
611+
# app/config/services.yml
612+
services:
613+
app.token_authenticator:
614+
class: AppBundle\Security\TokenAuthenticator
615+
arguments: ['@security.token_storage']
616+
617+
.. code-block:: xml
618+
619+
<!-- app/config/services.xml -->
620+
<services>
621+
<service id="app.token_authenticator" class="AppBundle\Security\TokenAuthenticator">
622+
<argument type="service" id="security.token_storage" />
623+
</service>
624+
</services>
625+
626+
.. code-block:: php
627+
628+
// app/config/services.php
629+
use AppBundle\Security\TokenAuthenticator;
630+
use Symfony\Component\DependencyInjection\Definition;
631+
use Symfony\Component\DependencyInjection\Reference;
632+
633+
$container->register('app.token_authenticator', TokenAuthenticator::class)
634+
->addArgument(new Reference('security.token_storage'));
635+
539636
Frequently Asked Questions
540637
--------------------------
541638

0 commit comments

Comments
 (0)