mirror of
https://github.com/jjbrunton/Sauci.git
synced 2026-11-01 18:19:43 +00:00
Add guest auth and save-account flow
Introduce anonymous sign-in with in-app saving, guest recovery warnings, paywall prompts, and admin guest labeling.
This commit is contained in:
1 parent
ce68d57a49
commit
349f460e15
14 files changed
+1236
-176
No files matched your search
@@ -15,6 +15,7 @@ describe('authStore', () => {
|
||||
partner: null,
|
||||
isLoading: true,
|
||||
isAuthenticated: false,
|
||||
isAnonymous: false,
|
||||
} as any);
|
||||
|
||||
useMatchStore.setState({ matches: [{ id: 'm1' }], newMatchesCount: 1 } as any);
|
||||
@@ -31,9 +32,35 @@ describe('authStore', () => {
|
||||
const state = useAuthStore.getState();
|
||||
expect(state.user).toBeNull();
|
||||
expect(state.isAuthenticated).toBe(false);
|
||||
expect(state.isAnonymous).toBe(false);
|
||||
expect(state.isLoading).toBe(false);
|
||||
});
|
||||
|
||||
it('sets isAnonymous from auth user', async () => {
|
||||
(supabase.auth.getSession as jest.Mock).mockResolvedValueOnce({
|
||||
data: { session: { user: { id: 'me' } } },
|
||||
});
|
||||
|
||||
(supabase.auth.getUser as jest.Mock).mockResolvedValueOnce({
|
||||
data: { user: { id: 'me', is_anonymous: true } },
|
||||
error: null,
|
||||
});
|
||||
|
||||
const profileQuery: any = {
|
||||
select: jest.fn(() => profileQuery),
|
||||
eq: jest.fn(() => profileQuery),
|
||||
maybeSingle: jest.fn(async () => ({ data: { id: 'me', couple_id: null } })),
|
||||
};
|
||||
|
||||
(supabase.from as jest.Mock).mockReturnValue(profileQuery);
|
||||
|
||||
await useAuthStore.getState().fetchUser();
|
||||
|
||||
const state = useAuthStore.getState();
|
||||
expect(state.isAuthenticated).toBe(true);
|
||||
expect(state.isAnonymous).toBe(true);
|
||||
});
|
||||
|
||||
it('clears stores and signs out when session invalid', async () => {
|
||||
(supabase.auth.getSession as jest.Mock).mockResolvedValueOnce({
|
||||
data: { session: { user: { id: 'me' } } },
|
||||
@@ -50,51 +77,9 @@ describe('authStore', () => {
|
||||
|
||||
expect(useAuthStore.getState().user).toBeNull();
|
||||
expect(useAuthStore.getState().isAuthenticated).toBe(false);
|
||||
expect(useAuthStore.getState().isAnonymous).toBe(false);
|
||||
|
||||
expect(useMatchStore.getState().matches).toEqual([]);
|
||||
expect(usePacksStore.getState().enabledPackIds).toEqual([]);
|
||||
expect(useMessageStore.getState().unreadCount).toBe(0);
|
||||
expect(useMessageStore.getState().activeMatchId).toBeNull();
|
||||
expect(useSubscriptionStore.getState().subscription.isProUser).toBe(false);
|
||||
|
||||
expect(supabase.auth.signOut).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('fetches couple and partner when couple_id exists', async () => {
|
||||
useAuthStore.setState({ user: { id: 'me', couple_id: 'c1' } } as any);
|
||||
|
||||
const couplesQuery: any = {
|
||||
select: jest.fn(() => couplesQuery),
|
||||
eq: jest.fn(() => couplesQuery),
|
||||
maybeSingle: jest.fn(async () => ({ data: { id: 'c1' } })),
|
||||
};
|
||||
|
||||
const partnerQuery: any = {
|
||||
select: jest.fn(() => partnerQuery),
|
||||
eq: jest.fn(() => partnerQuery),
|
||||
neq: jest.fn(() => partnerQuery),
|
||||
maybeSingle: jest.fn(async () => ({ data: { id: 'partner' } })),
|
||||
};
|
||||
|
||||
(supabase.from as jest.Mock).mockImplementation((table: string) => {
|
||||
if (table === 'couples') return couplesQuery;
|
||||
if (table === 'profiles') return partnerQuery;
|
||||
return couplesQuery;
|
||||
});
|
||||
|
||||
await useAuthStore.getState().fetchCouple();
|
||||
|
||||
expect(useAuthStore.getState().couple).toEqual({ id: 'c1' });
|
||||
expect(useAuthStore.getState().partner).toEqual({ id: 'partner' });
|
||||
});
|
||||
|
||||
it('signOut clears local state even if Supabase fails', async () => {
|
||||
(supabase.auth.signOut as jest.Mock).mockRejectedValueOnce(new Error('network'));
|
||||
|
||||
await useAuthStore.getState().signOut();
|
||||
|
||||
expect(useAuthStore.getState().user).toBeNull();
|
||||
expect(useAuthStore.getState().isAuthenticated).toBe(false);
|
||||
expect(useAuthStore.getState().isAnonymous).toBe(false);
|
||||
expect(useAuthStore.getState().isLoading).toBe(false);
|
||||
});
|
||||
});
|
||||
Reference in new issue
Block a user