--- import { getBlueskyAgent } from "@fujocoded/authproto/helpers"; import Combobox from "./Combobox.astro"; import AtprotoIcon from "./icons/AtprotoIcon.astro"; import { getAtmosphereCommunityDid } from "../../lib/community/atmosphere"; import { getMembership } from "../../lib/opensocial/membership"; const PROFILE_TTL_MS = 60_000; type CachedProfile = { expiresAt: number; avatar?: string; displayName?: string; // Admin of this site's own (Atmosphere) community. The dropdown is global, so // "admin" here means admin of atmosphere.community, not of any community. isAdmin: boolean; }; const profileCache: Map = (globalThis as any).__authMenuProfileCache ?? ((globalThis as any).__authMenuProfileCache = new Map()); async function loadAdminStatus(did: string): Promise { try { const communityDid = await getAtmosphereCommunityDid(); const membership = await getMembership({ communityDid, userDid: did }); return membership.isAdmin; } catch (err) { // A degraded appview shouldn't break the header; just hide the badge. console.warn("[AuthMenu] failed to load admin status", did, err); return false; } } async function loadProfile(did: string): Promise { const now = Date.now(); const cached = profileCache.get(did); if (cached && cached.expiresAt > now) return cached; try { const agent = await getBlueskyAgent(); const [profile, isAdmin] = await Promise.all([ agent?.app.bsky.actor.getProfile({ actor: did }), loadAdminStatus(did), ]); const entry: CachedProfile = { expiresAt: now + PROFILE_TTL_MS, avatar: profile?.data.avatar, displayName: profile?.data.displayName, isAdmin, }; profileCache.set(did, entry); return entry; } catch (err) { // Don't poison the cache on transient failures, but surface it server-side // so a degraded appview doesn't disappear silently behind "no avatar". console.warn("[AuthMenu] failed to load profile", did, err); return cached ?? null; } } const loggedInUser = Astro.locals.loggedInUser; const authError = Astro.locals.authproto?.errorDescription ?? Astro.locals.authproto?.errorCode; const profile = loggedInUser ? await loadProfile(loggedInUser.did) : null; const displayName = profile?.displayName?.trim() || loggedInUser?.handle || ""; const avatarUrl = profile?.avatar; const isAdmin = profile?.isAdmin ?? false; const avatarInitial = (displayName || "@").charAt(0).toUpperCase(); ---
{ loggedInUser ? ( <> {avatarUrl ? ( ) : ( )} {displayName}

Signed in as @{loggedInUser.handle} {isAdmin && Admin}

) : ( <>

Sign in to the Atmosphere

Your{" "} Atmosphere account {" "} lets you access dozens of websites—including this one!

{authError && ( )}
) }