Open carvefx opened 3 months ago
Yes I tested and it's serious problem. Here’s a test that demonstrates the problem:
test('user token returns correct user profile', function () {
// Create and authenticate the first user
$userOne = User::factory()->create()->refresh();
$tokenOne = auth('User')->tokenById($userOne->id);
$responseOne = $this->getJson(route('users.profile'), [
'Authorization' => "Bearer {$tokenOne}",
]);
// Create and authenticate the second user
$userTwo = User::factory()->create()->refresh();
$tokenTwo = auth('User')->tokenById($userTwo->id);
$responseTwo = $this->getJson(route('users.profile'), [
'Authorization' => "Bearer {$tokenTwo}",
]);
// Extract user details from the responses
$userOneDetails = [
'name' => $userOne->name,
'token' => $tokenOne,
'profile' => $responseOne->json(),
];
$userTwoDetails = [
'name' => $userTwo->name,
'token' => $tokenTwo,
'profile' => $responseTwo->json(),
];
// Assert that profiles of different users are not equal
$this->assertNotEquals(
$userOneDetails['profile'],
$userTwoDetails['profile'],
'The profiles for different users should not be equal.'
);
});
The JWT use context to generate tokens, it's not a database token based. So if the state is the same, user will be the same.
setToken (and possibly setRequest) return the previously logged in user
JwtGuard::setToken and JwtGuard::setRequest, if used in a long-running environment (a la octane etc, or a websockets server in my case) will not reset the user, but simply overwrite the token.
This leads to a behaviour where if there exists a cached user, and you reset the token, and call
you will get the cached user, instead of the user represented by the new token.
Your environment:
Steps to reproduce
In a loop, log in a user via setting the token, and then do it again with a new token, the user() method will return the original user.
Expected behaviour
setting a token should invalidate the user cache
Actual behaviour
setting a token returns the "previous" / "cached" user