import { createFileRoute } from "@tanstack/react-router"; import { z } from "zod"; const schema = z.object({ id: z.string().min(1).max(50), data: z.string().min(1).max(20), avversario: z.string().min(1).max(80), casa: z.boolean(), setNostri: z.number().int().min(0), setLoro: z.number().int().min(0), parziali: z.array(z.tuple([z.number().int(), z.number().int()])), mvp: z.string().max(80), azioni: z.array( z.object({ id: z.string(), tipo: z.enum(["attacco", "ace", "muro", "errore", "punto_avv", "errore_avv"]), giocatoreId: z.string().optional(), set: z.number().int(), ts: z.number(), }), ), }); /** * Proxy verso Strapi per il risultato finale di una partita scoutata: additivo, il localStorage * del device resta la fonte usata da useRosa/giocatoriConScout. Best-effort: nessun retry, nessun * upsert (un doppio invio crea al più una entry doppia in Strapi, da cancellare a mano). */ export const Route = createFileRoute("/api/public/scout-finale")({ server: { handlers: { POST: async ({ request }) => { const parsed = schema.safeParse(await request.json()); if (!parsed.success) return new Response("Dati non validi", { status: 400 }); const strapiUrl = process.env["VITE_STRAPI_URL"]; const token = process.env["STRAPI_WRITE_TOKEN"]; if (!strapiUrl || !token) { console.error("scout-finale: STRAPI_URL o STRAPI_WRITE_TOKEN mancanti"); return new Response("CMS non configurato", { status: 503 }); } const m = parsed.data; const res = await fetch(`${strapiUrl}/api/scout-match-finales`, { method: "POST", headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, body: JSON.stringify({ data: { match_id: m.id, data: m.data, avversario: m.avversario, casa: m.casa, set_nostri: m.setNostri, set_loro: m.setLoro, parziali: m.parziali, mvp: m.mvp, azioni: m.azioni, }, }), }); if (!res.ok) { console.error("scout-finale: Strapi ha risposto", res.status, await res.text()); return new Response("Salvataggio su CMS non riuscito", { status: 502 }); } return Response.json({ ok: true }); }, }, }, });