Repository: PrestaShop/PrestaShop (PHP)

Issue:
Invalid token when changing email address in profile page
### Prerequisites

- [X] I understand and accept the project's [code of conduct](https://github.com/PrestaShop/PrestaShop/blob/develop/CODE_OF_CONDUCT.md).
- [X] I have already [searched in existing issues](https://github.com/PrestaShop/PrestaShop/issues?q=is%3Aissue+label%3ABug) and found no previous report of this bug.

### Describe the bug and add attachments

Invalid token when changing email address in profile page

![Capture d’écran de 2023-05-29 10-07-17](https://github.com/PrestaShop/PrestaShop/assets/24647495/a6f8c6b4-bc73-42ae-91d6-aa82d8dc2b07)


### Expected behavior

A validation message should be displayed

![Capture d’écran de 2023-05-29 10-08-53](https://github.com/PrestaShop/PrestaShop/assets/24647495/d969c25e-dc0d-45a7-be4f-0c13820b6f01)


### Steps to reproduce

1- Go to Advanced parameters > Team page
2- Go to the first employee page
3- Update email and save
4- See the error => Invalid token: direct access to this link may lead to a potential security breach.

### PrestaShop version(s) where the bug happened

9.0

### PHP version(s) where the bug happened

8.1

### If your bug is related to a module, specify its name and its version

_No response_

### Your company or customer's name goes here (if applicable).

_No response_


Discussion: The problem is caused when you change the email address of the account you're connected with. At some point in a redirection, the token of the BO access is regenerated. But it is regenerated using the old email address. The new address should be already saved into db but when the regeneration process fetches the user it gives an old version of the user.
To fix the problem,  ensure the user retrieved is with the right email address, then force the token regeneration.



Fix (patch):
diff --git a/src/PrestaShopBundle/Controller/Admin/Configure/AdvancedParameters/EmployeeController.php b/src/PrestaShopBundle/Controller/Admin/Configure/AdvancedParameters/EmployeeController.php
index a3cf08f0b96ef..59271cb72e340 100644
--- a/src/PrestaShopBundle/Controller/Admin/Configure/AdvancedParameters/EmployeeController.php
+++ b/src/PrestaShopBundle/Controller/Admin/Configure/AdvancedParameters/EmployeeController.php
@@ -373,9 +373,18 @@ public function editAction($employeeId, Request $request)
             if ($result->isSubmitted() && $result->isValid()) {
                 $this->addFlash('success', $this->trans('Successful update', 'Admin.Notifications.Success'));
 
-                return $this->redirectToRoute('admin_employees_edit', [
-                    'employeeId' => $result->getIdentifiableObjectId(),
-                ]);
+                // If we are editing our own profile, we must set a new token before redirect to avoid compromised page
+                // todo: to be improved when UserProvider is also improved.
+                // @see https://github.com/PrestaShop/PrestaShop/pull/32861
+                $redirectParameters = ['employeeId' => $result->getIdentifiableObjectId()];
+                if ($contextEmployeeProvider->getId() === $result->getIdentifiableObjectId()) {
+                    $newToken = $this->get('security.csrf.token_manager')
+                        ->getToken($employeeForm->get('email')->getData())
+                        ->getValue();
+                    $redirectParameters['_token'] = $newToken;
+                }
+
+                return $this->redirectToRoute('admin_employees_edit', $redirectParameters);
             }
         } catch (Exception $e) {
             $this->addFlash('error', $this->getErrorMessageForException($e, $this->getErrorMessages($e)));
diff --git a/src/PrestaShopBundle/Service/Routing/Router.php b/src/PrestaShopBundle/Service/Routing/Router.php
index 44d93026e6d8c..ab8a97787d14a 100644
--- a/src/PrestaShopBundle/Service/Routing/Router.php
+++ b/src/PrestaShopBundle/Service/Routing/Router.php
@@ -60,7 +60,10 @@ public function generate($name, $parameters = [], $referenceType = self::ABSOLUT
     {
         $url = parent::generate($name, $parameters, $referenceType);
 
-        if (TokenInUrls::isDisabled()) {
+        // For now, if we generate a _token and pass it in parameters, we must use it instead of use TokenManager.
+        // todo: to be improved when UserProvider is also improved.
+        // @see https://github.com/PrestaShop/PrestaShop/pull/32861
+        if (TokenInUrls::isDisabled() || isset($parameters['_token'])) {
             return $url;
         }