"use server"; import { revalidatePath } from "next/cache"; import { z } from "zod"; import { actionOk, authAction } from "@/lib/foundation/action"; import { DatabaseError } from "@/lib/foundation/errors"; import { prisma } from "@/lib/prisma"; import { rcon } from "@/lib/services/rcon"; const MOTTO_MAX = 127; const mottoSchema = z.object({ motto: z .string() .max(MOTTO_MAX, `Motto must be at most ${MOTTO_MAX} characters`), }); const updateMottoAction = authAction({ schema: mottoSchema }, async (ctx) => { try { await prisma.user.update({ where: { id: ctx.session.user.id }, data: { motto: ctx.data.motto }, }); } catch { throw new DatabaseError("Failed to update motto"); } try { await rcon.setMotto(ctx.session.user.id, ctx.data.motto); } catch { // RCON is best-effort; the change is already persisted. } revalidatePath("/settings"); return actionOk(); }); export async function updateMotto(formData: FormData): Promise { const motto = String(formData.get("motto") ?? "") .normalize("NFC") .slice(0, MOTTO_MAX); await updateMottoAction({ motto }); } export { updateMottoAction };