Files
threadcount-community/lib/csrf.ts
T
ThreadCount 8c86c988c1 ThreadCount Community edition
Uniform stock management for healthcare linen rooms: the coordinator app, the phone counter and the staff app, for your own server. Built from 2d04e45 on 2026-09-15. Licensed under the Functional Source License (FSL-1.1-ALv2).
2026-09-16 04:04:31 +10:00

16 lines
889 B
TypeScript

import type { NextRequest } from "next/server";
// State-changing routes only accept same-origin requests carrying JSON. Browsers send Sec-Fetch-Site on every
// request and Origin on cross-origin POSTs, so a cross-site <form> (even text/plain) can't reach them.
export function sameOriginJson(req: NextRequest, json = true): string | null {
const sfs = req.headers.get("sec-fetch-site");
if (sfs && sfs !== "same-origin" && sfs !== "none") return "Cross-site request refused";
const origin = req.headers.get("origin");
if (origin) {
const host = req.headers.get("x-forwarded-host") || req.headers.get("host") || "";
try { if (new URL(origin).host !== host) return "Cross-site request refused"; } catch { return "Bad origin"; }
}
if (json && !(req.headers.get("content-type") || "").toLowerCase().includes("application/json")) return "Expected JSON";
return null;
}