feat: Add API to save session snapshots and initialize the corresponding database table.

This commit is contained in:
Michael committed 2026-02-22 13:35:34 +01:00
1 parent 77fb61ef79
commit 3b3021d85f
2 files changed
+65 -3

No files matched your search

+25
View File
@@ -0,0 +1,25 @@
"use server";
import { db } from "@/db";
import { sql } from "drizzle-orm";
export async function initSnapshotTable() {
try {
await db.execute(sql`
CREATE TABLE IF NOT EXISTS session_snapshots (
id SERIAL PRIMARY KEY,
code_fournisseur VARCHAR(20) NOT NULL,
nom_fournisseur VARCHAR(255),
magasin VARCHAR(20) NOT NULL,
changes JSONB NOT NULL,
summary_json JSONB,
label TEXT,
created_at TIMESTAMP DEFAULT NOW()
);
`);
return { success: true };
} catch (err) {
console.error("Init DB error:", err);
return { success: false, error: err instanceof Error ? err.message : String(err) };
}
}
+40 -3
View File
@@ -3,6 +3,7 @@
import { db } from "@/db"; import { db } from "@/db";
import { sessionSnapshots } from "@/db/schema"; import { sessionSnapshots } from "@/db/schema";
import { z } from "zod"; import { z } from "zod";
import { sql } from "drizzle-orm";
const SaveSnapshotSchema = z.object({ const SaveSnapshotSchema = z.object({
codeFournisseur: z.string(), codeFournisseur: z.string(),
@@ -44,8 +45,44 @@ export async function saveSnapshot(raw: unknown) {
.returning({ id: sessionSnapshots.id }); .returning({ id: sessionSnapshots.id });
return { success: true, snapshotId: created?.id }; return { success: true, snapshotId: created?.id };
} catch (err) { } catch (err: any) {
console.error("Snapshot DB insertion error:", err); console.error("Snapshot DB error, attempting auto-repair:", err);
return { success: false, error: "Database error during insertion" };
// Si la table n'existe pas, on tente de la créer
if (err.message?.includes("relation") && err.message?.includes("does not exist")) {
try {
await db.execute(sql`
CREATE TABLE IF NOT EXISTS session_snapshots (
id SERIAL PRIMARY KEY,
code_fournisseur VARCHAR(20) NOT NULL,
nom_fournisseur VARCHAR(255),
magasin VARCHAR(20) NOT NULL,
changes JSONB NOT NULL,
summary_json JSONB,
label TEXT,
created_at TIMESTAMP DEFAULT NOW()
);
`);
// On ré-essaie l'insertion une seule fois
const [created] = await db
.insert(sessionSnapshots)
.values({
codeFournisseur,
nomFournisseur: nomFournisseur ?? null,
magasin,
label: label ?? `Snapshot — ${new Date().toLocaleDateString("fr-FR")}`,
changes,
summaryJson: summary ?? null,
})
.returning({ id: sessionSnapshots.id });
return { success: true, snapshotId: created?.id };
} catch (repairErr: any) {
console.error("Auto-repair failed:", repairErr);
return { success: false, error: `Repair failed: ${repairErr.message}` };
}
}
const errorMessage = err instanceof Error ? err.message : String(err);
return { success: false, error: `DB Error: ${errorMessage}` };
} }
} }