openreader/src/lib/server/audiobook-scope.ts
Richard R 1f4794a706 feat(auth): implement session gatekeeping and architectural reorganization
- Introduce `USE_ANONYMOUS_AUTH_SESSIONS` to make guest access an opt-in feature.
- Transition root-level pages into `(app)` and `(public)` route groups for improved access control.
- Adopt Figtree as the primary typeface and implement a pre-render theme initialization script.
- Decouple audiobook chapter processing into a standalone API route and harden resource ownership logic.
- Replace the legacy footer with a unified layout and add skeleton loading states for document lists.
- Update environment documentation and test suites to align with the revised routing and auth flows.

BREAKING CHANGE: The audiobook generation API has been restructured, moving specific chapter logic to `/api/audiobook/chapter`.
2026-02-15 11:12:42 -07:00

25 lines
900 B
TypeScript

export function buildAllowedAudiobookUserIds(
authEnabled: boolean,
userId: string | null,
unclaimedUserId: string,
): { preferredUserId: string; allowedUserIds: string[] } {
if (!authEnabled) {
return { preferredUserId: unclaimedUserId, allowedUserIds: [unclaimedUserId] };
}
const preferredUserId = userId ?? unclaimedUserId;
const allowedUserIds = Array.from(new Set([preferredUserId, unclaimedUserId]));
return { preferredUserId, allowedUserIds };
}
export function pickAudiobookOwner(
existingUserIds: string[],
preferredUserId: string,
unclaimedUserId: string,
): string | null {
const existing = new Set(existingUserIds);
// Keep resumed writes on unclaimed scope when the book already exists there.
if (existing.has(unclaimedUserId)) return unclaimedUserId;
if (existing.has(preferredUserId)) return preferredUserId;
return existingUserIds[0] ?? null;
}