SPB Git forge

spb/spinza

Public
8commits 1branches 0releases
1.6 MBsize
maindefault branch
16 days agolast push
TypeScript 97.6% SQL 1.4% JavaScript 0.5%
2.3 KB · 52 lines typescript
Raw Blame History
1import { db, eq, featureFlags, platformSettings } from "@spinza/database";2import { DAILY_REWARDS, RESCUE_CREDITS_AMOUNT, RESCUE_CREDITS_COOLDOWN_HOURS } from "@spinza/shared";34/** In-process cache of flags & settings, refreshed every 10 s. */5let flags = new Map<string, boolean>();6let settings = new Map<string, unknown>();7let loadedAt = 0;8const TTL = 10_000;910export async function refreshSettings(force = false): Promise<void> {11  if (!force && Date.now() - loadedAt < TTL) return;12  const [f, s] = await Promise.all([db.select().from(featureFlags), db.select().from(platformSettings)]);13  flags = new Map(f.map((x) => [x.key, x.enabled]));14  settings = new Map(s.map((x) => [x.key, x.value]));15  loadedAt = Date.now();16}1718export function flag(key: string, def = true): boolean {19  return flags.has(key) ? (flags.get(key) as boolean) : def;20}2122export function setting<T>(key: string, def: T): T {23  return settings.has(key) ? (settings.get(key) as T) : def;24}2526export interface MaintenanceSetting {27  enabled: boolean;28  message: string;29}30export const maintenance = () => setting<MaintenanceSetting>("maintenance", { enabled: false, message: "Spinza is getting an upgrade. Your credits and progress are safe." });31export const rescueConfig = () => setting("rescue", { amount: RESCUE_CREDITS_AMOUNT, cooldownHours: RESCUE_CREDITS_COOLDOWN_HOURS, threshold: 0 });32export const dailySchedule = () => setting("dailyRewards", { schedule: DAILY_REWARDS as readonly number[] }).schedule;33export const profanityWords = () => setting("profanity", { words: [] as string[] }).words;3435export async function setFlag(key: string, enabled: boolean): Promise<void> {36  await db.insert(featureFlags).values({ key, enabled }).onConflictDoUpdate({ target: featureFlags.key, set: { enabled, updatedAt: new Date() } });37  await refreshSettings(true);38}3940export async function setSetting(key: string, value: unknown): Promise<void> {41  await db.insert(platformSettings).values({ key, value }).onConflictDoUpdate({ target: platformSettings.key, set: { value, updatedAt: new Date() } });42  await refreshSettings(true);43}4445export function allFlags(): Record<string, boolean> {46  return Object.fromEntries(flags);47}48export function allSettings(): Record<string, unknown> {49  return Object.fromEntries(settings);50}51export { eq };52