fix(ui): multiple logout requests being made in parallel (#13595)

Fixes https://github.com/payloadcms/payload/issues/13565

The logout operation was running twice and causing a race condition on
user updates. This change ensures the logout operation only runs 1 time.

Really this view should have 1 purpose and that is to show the
inactivity view. Currently it has 2 purposes which is why it needs the
useEffect — the root of this issue. Instead we should just call the
`logOut` function from the logout button instead of it linking to a
logout page.
This commit is contained in:
Jarrod Flesch
2025-08-26 13:54:57 -04:00
committed by GitHub
parent 344ad69572
commit cf37433667
2 changed files with 13 additions and 4 deletions

View File

@@ -15,6 +15,16 @@ import './index.scss'
const baseClass = 'logout'
/**
* This component should **just** be the inactivity route and do nothing with logging the user out.
*
* It currently handles too much, the auth provider should just log the user out and then
* we could remove the useEffect in this file. So instead of the logout button
* being an anchor link, it should be a button that calls `logOut` in the provider.
*
* This view is still useful if cookies attempt to refresh and fail, i.e. the user
* is logged out due to inactivity.
*/
export const LogoutClient: React.FC<{
adminRoute: string
inactivity?: boolean
@@ -47,11 +57,10 @@ export const LogoutClient: React.FC<{
const router = useRouter()
const handleLogOut = React.useCallback(async () => {
await logOut()
if (!inactivity && !navigatingToLoginRef.current) {
toast.success(t('authentication:loggedOutSuccessfully'))
navigatingToLoginRef.current = true
await logOut()
toast.success(t('authentication:loggedOutSuccessfully'))
startRouteTransition(() => router.push(loginRoute))
return
}

View File

@@ -193,13 +193,13 @@ export function AuthProvider({
const logOut = useCallback(async () => {
try {
if (user && user.collection) {
setNewUser(null)
await requests.post(`${serverURL}${apiRoute}/${user.collection}/logout`)
}
} catch (_) {
// fail silently and log the user out in state
}
setNewUser(null)
return true
}, [apiRoute, serverURL, setNewUser, user])