Files
silo-server/web/src/hooks/useOverlayPrefs.ts
T
2933e0581f fix(web): make pre-merge frontend checks pass at HEAD (prettier drift + 15 stale tests) (#119)
* style(web): run prettier over drifted files

prettier --check was failing on 19 files at HEAD. The pinned prettier
version (3.8.1) has not changed since the initial migration, so the
drift came from unformatted commits, not a toolchain bump. Formatting
changes only, no behavior change.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

* test(web): sync stale test harnesses with current components

15 tests across 6 files were failing at HEAD; the components were
committed already out of sync with their tests in the initial
migration. All fixes are in test files only:

- SectionRow / SeriesContent: mock the watch playback controller
  required by ContinueWatchingCard and MediaItemMenu, mock the new
  useSimilarItems hook, add useOptionalAuth to the auth mock, and
  wrap renders in QueryClientProvider for MediaItemMenu query hooks
- SeriesContent: read rating from item.user_rating (the useRating
  hook no longer exists)
- ProfilesSettings: add useHouseholdSessions to the profiles mock
  for the new HouseholdStreamsPanel
- ImpersonationBanner: match the redesigned banner ("Viewing as",
  sticky full-width bar instead of sidebar offset)
- EpisodeRow: watched indicator uses the text-success token now
- profile-management: use a valid DiceBear preset ref; "adventurer"
  no longer resolves and round-trips to ""

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

---------

Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
2026-06-09 19:17:14 -04:00

55 lines
1.7 KiB
TypeScript

import { useMemo, useCallback } from "react";
import { useQuery } from "@tanstack/react-query";
import { api } from "@/api/client";
import { useSetting, useSetSetting } from "@/hooks/queries/settings";
import { settingsKeys } from "@/hooks/queries/keys";
import { parseOverlayPrefs, serializeOverlayPrefs, type CardOverlayPrefs } from "@/lib/overlays";
const SETTING_KEY = "card_overlays";
interface OverlayConfig {
enabled: boolean;
defaults?: string;
}
function useOverlayConfig() {
return useQuery({
queryKey: [...settingsKeys.all, "overlay-config"] as const,
queryFn: () => api<OverlayConfig>("/settings/overlay-config"),
staleTime: 60_000,
});
}
export function useOverlayPrefs() {
const { data: raw, isLoading: userLoading } = useSetting(SETTING_KEY);
const { data: config, isLoading: configLoading } = useOverlayConfig();
const setSetting = useSetSetting();
const prefs = useMemo(() => {
// User setting takes priority; fall back to admin defaults
const source = raw ?? config?.defaults ?? null;
return parseOverlayPrefs(source);
}, [raw, config?.defaults]);
// Admin kill switch: if disabled server-wide, return null prefs
const enabled = config?.enabled !== false;
const setPrefs = useCallback(
(next: CardOverlayPrefs) => {
const serialized = serializeOverlayPrefs(next);
// Avoid a network round-trip and downstream re-render cascade when
// the user toggles a control to its current value.
if (raw === serialized) return;
setSetting.mutate({ key: SETTING_KEY, value: serialized });
},
[raw, setSetting],
);
return {
prefs: enabled ? prefs : null,
setPrefs,
isLoading: userLoading || configLoading,
enabled,
};
}