Files
av-planner/src/state/authStore.ts
T
aarbitandClaude Sonnet 5 6cdfde822d Add site-wide announcements, account migration, and profile self-service
Announcements: a Super Admin (or an Admin individually flagged via
profiles.can_post_announcements) can post/retire a site-wide banner.
Account migration: a Super Admin can move a locked-out user's diagrams,
private catalog entries, and submissions to another account, with a
migration-history log; ProfileModal adds the self-service half (link a new
Google identity via Supabase manual linking, then unlink the old one,
while signed in as the account being migrated). Also reworks the top bar's
flat button row into grouped dropdown menus (Diagram / Admin / Account) now
that there are enough entries to need it.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017DUU6CnxECCDeqDNYJgr5x
2026-09-28 10:05:11 -05:00

54 lines
1.6 KiB
TypeScript

import { create } from 'zustand'
import type { UserRole } from '../data/AdminUserRepository'
import { supabase } from '../data/supabaseClient'
export type { UserRole }
interface AuthStoreState {
userId: string | null
username: string | null
role: UserRole | null
/** Lets a specific Admin post/retire site-wide announcements without the
* whole Admin role gaining that ability — a Super Admin can always post
* regardless of this flag (see can_manage_announcements() in the DB). */
canPostAnnouncements: boolean
isLoaded: boolean
/** One-time fetch of your own profile — nothing else in the app changes
* your own username while you're signed in, and your own role changing
* (a Super-Admin-only action on someone else's account, see
* organized-ideas.md §6) isn't something you'd do to yourself, so
* there's no need to keep this live. */
load: () => Promise<void>
}
export const useAuthStore = create<AuthStoreState>((set) => ({
userId: null,
username: null,
role: null,
canPostAnnouncements: false,
isLoaded: false,
load: async () => {
const {
data: { user },
} = await supabase.auth.getUser()
if (!user) {
set({ isLoaded: true })
return
}
const { data } = await supabase
.from('profiles')
.select('username, role, can_post_announcements')
.eq('id', user.id)
.single()
set({
userId: user.id,
username: data?.username ?? null,
role: (data?.role as UserRole | undefined) ?? null,
canPostAnnouncements: data?.can_post_announcements ?? false,
isLoaded: true,
})
},
}))