feat: add CSRF protection for admin API routes
Double-submit cookie pattern: login sets bh-csrf-token cookie, proxy.ts validates X-CSRF-Token header on POST/PUT/DELETE to /api/admin/*. New adminFetch() helper in src/lib/csrf.ts auto-includes the header. All admin pages migrated from fetch() to adminFetch(). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
import { useState, useEffect, useRef, useCallback } from "react";
|
||||
import { Loader2, Check, AlertCircle } from "lucide-react";
|
||||
import { adminFetch } from "@/lib/csrf";
|
||||
|
||||
interface SectionEditorProps<T> {
|
||||
sectionKey: string;
|
||||
@@ -24,7 +25,7 @@ export function SectionEditor<T>({
|
||||
const initialLoadRef = useRef(true);
|
||||
|
||||
useEffect(() => {
|
||||
fetch(`/api/admin/sections/${sectionKey}`)
|
||||
adminFetch(`/api/admin/sections/${sectionKey}`)
|
||||
.then((r) => {
|
||||
if (!r.ok) throw new Error("Failed to load");
|
||||
return r.json();
|
||||
@@ -39,7 +40,7 @@ export function SectionEditor<T>({
|
||||
setError("");
|
||||
|
||||
try {
|
||||
const res = await fetch(`/api/admin/sections/${sectionKey}`, {
|
||||
const res = await adminFetch(`/api/admin/sections/${sectionKey}`, {
|
||||
method: "PUT",
|
||||
headers: { "Content-Type": "application/json" },
|
||||
body: JSON.stringify(dataToSave),
|
||||
|
||||
Reference in New Issue
Block a user