fix: trigger login tracking on session restore

This commit is contained in:
2026-05-08 14:36:56 +08:00
parent 91d993dc6b
commit e694c6605a
5 changed files with 28 additions and 8 deletions

View File

@@ -13,6 +13,7 @@ const authMocks = vi.hoisted(() => ({
authEntry: vi.fn(),
changePassword: vi.fn(),
ensureStoredAccessToken: vi.fn(),
refreshStoredAccessToken: vi.fn(),
getAuthLoginOptions: vi.fn(),
getCurrentAuthUser: vi.fn(),
loginWithPhoneCode: vi.fn(),
@@ -28,6 +29,7 @@ const authMocks = vi.hoisted(() => ({
vi.mock('../../services/apiClient', () => ({
AUTH_STATE_EVENT: 'genarrative-auth-state-changed',
ensureStoredAccessToken: authMocks.ensureStoredAccessToken,
refreshStoredAccessToken: authMocks.refreshStoredAccessToken,
}));
vi.mock('../../services/authService', () => ({
@@ -94,6 +96,7 @@ beforeEach(() => {
window.history.replaceState(null, '', '/');
authMocks.consumeAuthCallbackResult.mockReturnValue(null);
authMocks.ensureStoredAccessToken.mockResolvedValue('jwt-existing-token');
authMocks.refreshStoredAccessToken.mockResolvedValue('jwt-refreshed-token');
authMocks.getCurrentAuthUser.mockResolvedValue({
user: null,
availableLoginMethods: ['phone'],
@@ -204,12 +207,12 @@ test('auth gate keeps platform content visible when phone login is available', a
expect(screen.queryByText('先登录账号,再同步你的冒险进度。')).toBeNull();
});
test('auth gate waits for access token refresh before exposing restored user content', async () => {
test('auth gate waits for refresh cookie rotation before exposing restored user content', async () => {
let resolveToken!: (token: string) => void;
const tokenPromise = new Promise<string>((resolve) => {
resolveToken = resolve;
});
authMocks.ensureStoredAccessToken.mockReturnValue(tokenPromise);
authMocks.refreshStoredAccessToken.mockReturnValue(tokenPromise);
authMocks.getCurrentAuthUser.mockResolvedValue({
user: mockUser,
availableLoginMethods: ['phone'],
@@ -224,10 +227,11 @@ test('auth gate waits for access token refresh before exposing restored user con
expect(screen.getByText('正在校验登录状态...')).toBeTruthy();
expect(authMocks.getCurrentAuthUser).not.toHaveBeenCalled();
resolveToken('jwt-restored-token');
resolveToken('jwt-refreshed-token');
expect(await screen.findByText('应用内容')).toBeTruthy();
expect(authMocks.ensureStoredAccessToken).toHaveBeenCalledTimes(1);
expect(authMocks.refreshStoredAccessToken).toHaveBeenCalledTimes(1);
expect(authMocks.ensureStoredAccessToken).not.toHaveBeenCalled();
expect(authMocks.getCurrentAuthUser).toHaveBeenCalledTimes(1);
});
@@ -440,7 +444,7 @@ test('auth state refresh keeps mounted platform content and local tab state', as
const tokenPromise = new Promise<string>((resolve) => {
resolveToken = resolve;
});
authMocks.ensureStoredAccessToken.mockReturnValueOnce(tokenPromise);
authMocks.refreshStoredAccessToken.mockReturnValueOnce(tokenPromise);
act(() => {
window.dispatchEvent(new Event('genarrative-auth-state-changed'));