fix(sites-front) : refresh state apres switch/delete/401 + redirect logout
- logout.vue : navigateTo('/login') dans le finally, garanti meme si
auth.logout() rejette.
- auth.ts : systeme de callbacks onAuthSessionCleared appeles par
clearSession() (intercepteur 401 de useApi). Les composables modules
s'abonnent pour reset leur state sans que Shared n'importe depuis
modules/ (Option C validee par CLAUDE.md, module -> shared autorise).
- useCurrentSite.ts : enregistre un reset callback + apres un switch
reussi, rafraichit useSidebar().loadSidebar() + refreshNuxtData()
(sinon donnees de page obsoletes cote ancien site sous toast success).
- SiteSelector.vue : le court-circuit "tile deja active" est retire
pour permettre un PATCH de resync quand un autre onglet a bascule le
site entre temps. TODO cross-tab : ecouter un storage event dedie.
- sites.vue admin : auth.refreshUser() apres delete pour refleter le
ON DELETE SET NULL cote user.current_site_id.
- Specs vitest : stub useSidebar/refreshNuxtData, test "tile active"
retourne sur le nouveau contrat PATCH-toujours.
This commit is contained in:
@@ -29,6 +29,10 @@ vi.stubGlobal('useI18n', () => ({ t: (key: string) => key }))
|
||||
vi.stubGlobal('watchEffect', watchEffect)
|
||||
vi.stubGlobal('computed', computed)
|
||||
vi.stubGlobal('ref', ref)
|
||||
// useSidebar et refreshNuxtData sont consommes par useCurrentSite apres
|
||||
// un switch reussi — stubs minimaux pour eviter ReferenceError au mount.
|
||||
vi.stubGlobal('useSidebar', () => ({ loadSidebar: vi.fn() }))
|
||||
vi.stubGlobal('refreshNuxtData', vi.fn())
|
||||
|
||||
// Stub de MalioSiteSelector : on se contente de tracker les props recues
|
||||
// et de re-emettre `change` quand on le simule via `trigger`. Evite de
|
||||
@@ -144,13 +148,22 @@ describe('SiteSelector', () => {
|
||||
)
|
||||
})
|
||||
|
||||
it('clic sur le tile deja actif ne declenche aucun PATCH', async () => {
|
||||
it('clic sur le tile deja actif declenche un PATCH (resync cross-tab)', async () => {
|
||||
// Le court-circuit "si deja actif, ne rien faire" a ete supprime
|
||||
// pour couvrir le cas ou un autre onglet a modifie le site courant
|
||||
// cote serveur : un clic sur la tile localement "active" (etat
|
||||
// potentiellement stale) force une resync via PATCH. Le prix est un
|
||||
// PATCH superflu quand l'etat local est effectivement a jour.
|
||||
const wrapper = mountSelector()
|
||||
|
||||
await wrapper.find('[data-testid="tile-1"]').trigger('click')
|
||||
await flushPromises()
|
||||
|
||||
expect(mockPatch).not.toHaveBeenCalled()
|
||||
expect(mockPatch).toHaveBeenCalledWith(
|
||||
'/me/current-site',
|
||||
{ site: '/api/sites/1' },
|
||||
expect.anything(),
|
||||
)
|
||||
})
|
||||
|
||||
it('rollback visuel : sur erreur PATCH, data-active-id revient au site initial', async () => {
|
||||
|
||||
Reference in New Issue
Block a user