Files
Epicnabbo-Catalogus-Updated…/src/lib/services/site-settings.ts
T
2026-07-01 15:06:52 +02:00

57 lines
1.8 KiB
TypeScript

import { prisma } from "@/lib/prisma";
// Fallback values used when a setting row is missing OR the DB is unreachable,
// so the app still renders (e.g. local dev without a DATABASE_URL).
const DEFAULTS: Record<string, string> = {
hotel_name: "Atom",
habbo_imaging_url: "https://epicnabbo.nl/imaging/",
logo_url: "",
nitro_client_url: "",
};
/**
* DB-driven CMS config, mirroring AtomCMS's `setting()` / habbo-next's
* `siteSettings`. Loads the whole website_settings table into a key→value map,
* cached in-process, with graceful fallback to DEFAULTS. Booleans are stored as
* the strings '1' / '0'.
*/
class SiteSettings {
private cache: Map<string, string> | null = null;
private async load(): Promise<Map<string, string>> {
if (this.cache === null) {
try {
const rows = await prisma.websiteSetting.findMany({
select: { key: true, value: true },
});
this.cache = new Map(rows.map((r) => [r.key, r.value]));
} catch {
// DB unavailable — serve defaults without caching so we retry later.
return new Map(Object.entries(DEFAULTS));
}
}
return this.cache;
}
async get(key: string, fallback: string | null = null): Promise<string | null> {
const map = await this.load();
if (map.has(key)) return map.get(key) as string;
if (key in DEFAULTS) return DEFAULTS[key] as string;
return fallback;
}
async getBool(key: string, fallback = false): Promise<boolean> {
const v = await this.get(key, null);
if (v === null) return fallback;
const s = v.toLowerCase();
return s === "1" || s === "true";
}
/** Invalidate the in-process cache after a settings write. */
reload(): void {
this.cache = null;
}
}
export const siteSettings = new SiteSettings();