From cd526dced4e0602cc84e02346c895a90b15d28fd Mon Sep 17 00:00:00 2001 From: makearmy Date: Wed, 1 Oct 2025 19:17:37 -0400 Subject: [PATCH] co2 galvo owner test --- app/settings/co2-galvo/[id]/co2-galvo.tsx | 75 +++++++++++++++-------- 1 file changed, 51 insertions(+), 24 deletions(-) diff --git a/app/settings/co2-galvo/[id]/co2-galvo.tsx b/app/settings/co2-galvo/[id]/co2-galvo.tsx index 825c45ef..ab4f6518 100644 --- a/app/settings/co2-galvo/[id]/co2-galvo.tsx +++ b/app/settings/co2-galvo/[id]/co2-galvo.tsx @@ -5,12 +5,26 @@ import { useParams } from "next/navigation"; import Image from "next/image"; import Markdown from "react-markdown"; +function getMaToken(): string | null { + if (typeof window === "undefined") return null; + // cookie first + const c = document.cookie + .split("; ") + .find((x) => x.startsWith("ma_at=")) + ?.split("=")[1]; + if (c) return decodeURIComponent(c); + // localStorage fallback (if you ever store it there) + try { + const ls = window.localStorage.getItem("ma_at"); + if (ls) return ls; + } catch {} + return null; +} + export default function CO2GalvoSettingDetailPage() { - const { id } = useParams(); + const { id } = useParams<{ id: string }>(); const [setting, setSetting] = useState(null); const [loading, setLoading] = useState(true); - - // claim UI state const [claimBusy, setClaimBusy] = useState(false); const [claimMsg, setClaimMsg] = useState(null); const [claimErr, setClaimErr] = useState(null); @@ -18,17 +32,13 @@ export default function CO2GalvoSettingDetailPage() { useEffect(() => { if (!id) return; - const url = - `${process.env.NEXT_PUBLIC_API_BASE_URL}/items/settings_co2gal/${id}` + - `?fields=` + - [ + const fields = [ "submission_id", "setting_title", "uploader", - // ── Owner (expand username) ─────────────────────────── + // need username explicitly for M2O "owner.id", "owner.username", - // ───────────────────────────────────────────────────── "setting_notes", "photo.filename_disk", "photo.title", @@ -47,7 +57,7 @@ export default function CO2GalvoSettingDetailPage() { "lens_apt.name", "lens_exp.name", "focus", - // laser software can be string or relation + // laser_soft may be string OR relation "laser_soft", "laser_soft.name", "repeat_all", @@ -56,26 +66,47 @@ export default function CO2GalvoSettingDetailPage() { "raster_settings", ].join(","); - fetch(url, { cache: "no-store" }) - .then((res) => { - if (!res.ok) throw new Error("Failed to load"); + const url = + `${process.env.NEXT_PUBLIC_API_BASE_URL}/items/settings_co2gal/` + + encodeURIComponent(String(id)) + + `?fields=${encodeURIComponent(fields)}`; + + const token = getMaToken(); + setLoading(true); + + fetch(url, { + method: "GET", + headers: token ? { Authorization: `Bearer ${token}` } : {}, + cache: "no-store", + // do NOT rely on cross-site cookies; we send the bearer explicitly + credentials: "omit", + }) + .then(async (res) => { + if (!res.ok) { + const j = await res.json().catch(() => ({})); + throw new Error(j?.errors?.[0]?.message || `HTTP ${res.status}`); + } return res.json(); }) - .then((data) => setSetting(data.data)) - .catch(() => setSetting(null)) + .then((json) => setSetting(json?.data ?? null)) + .catch((e) => { + console.error("co2-galvo fetch failed:", e); + setSetting(null); + }) .finally(() => setLoading(false)); }, [id]); if (loading) return

Loading setting...

; if (!setting) return

Setting not found.

; - // Owner display: prefer username if relation is expanded; otherwise show raw value/id + // ----- presentation helpers ----- const ownerDisplay: string = typeof setting?.owner === "object" ? (setting.owner?.username ?? setting.owner?.id ?? "—") - : (typeof setting?.owner === "string" ? setting.owner : "—"); + : typeof setting?.owner === "string" + ? setting.owner + : "—"; - // laser_soft may be string or relation const softwareLabel: string = typeof setting?.laser_soft === "object" ? (setting.laser_soft?.name ?? "—") @@ -160,12 +191,8 @@ export default function CO2GalvoSettingDetailPage() {

{setting.setting_title}

-

- Owner: {ownerDisplay} -

-

- Uploader: {setting.uploader || "—"} -

+

Owner: {ownerDisplay}

+

Uploader: {setting.uploader || "—"}

{ownerDisplay === "—" && (