"use server"; import { revalidatePath } from "next/cache"; import { z } from "zod"; import { getCurrentUser } from "@/data/auth"; import { countPemakaianSatuanBarang, deleteSatuanBarang, insertSatuanBarang, updateSatuanBarang, type SatuanBarangInput, } from "@/data/satuan-barang"; export type SimpanSatuanBarangState = { ok: boolean; error?: string; fieldErrors?: { namaSatuanBarang?: string[] }; values?: { namaSatuanBarang?: string }; idSatuanBarang?: number; }; export type HapusSatuanBarangState = { ok: boolean; error?: string }; const satuanBarangSchema = z.object({ namaSatuanBarang: z .string() .trim() .min(1, "Nama satuan wajib diisi") .max(30, "Maksimal 30 karakter"), }); export async function simpanSatuanBarang( _prevState: SimpanSatuanBarangState, formData: FormData, ): Promise { const user = await getCurrentUser(); const values = { namaSatuanBarang: String(formData.get("namaSatuanBarang") ?? ""), }; const parsed = satuanBarangSchema.safeParse(values); if (!parsed.success) { return { ok: false, fieldErrors: z.flattenError(parsed.error).fieldErrors, values, }; } const input: SatuanBarangInput = parsed.data; const idRaw = String(formData.get("idSatuanBarang") ?? ""); const id = idRaw ? Number.parseInt(idRaw, 10) : null; if (id !== null && (!Number.isSafeInteger(id) || id <= 0)) { return { ok: false, error: "ID satuan tidak valid", values }; } try { if (id !== null) { const updated = await updateSatuanBarang(id, input); if (!updated) { return { ok: false, error: "Satuan tidak ditemukan", values }; } revalidatePath("/master/satuan-barang"); return { ok: true, idSatuanBarang: id }; } const idBaru = await insertSatuanBarang(input); revalidatePath("/master/satuan-barang"); return { ok: true, idSatuanBarang: idBaru }; } catch (error) { console.error( "[simpanSatuanBarang] gagal", { userId: user.id, idSatuanBarang: id ?? "(baru)", nama: input.namaSatuanBarang, }, error, ); return { ok: false, error: "Gagal menyimpan satuan, coba simpan ulang", values, }; } } export async function hapusSatuanBarang( _prevState: HapusSatuanBarangState, formData: FormData, ): Promise { const user = await getCurrentUser(); const id = Number.parseInt(String(formData.get("idSatuanBarang") ?? ""), 10); if (!Number.isSafeInteger(id) || id <= 0) { return { ok: false, error: "ID satuan tidak ada" }; } try { const dipakai = await countPemakaianSatuanBarang(id); if (dipakai > 0) { return { ok: false, error: `Satuan masih dipakai ${dipakai} barang, tidak bisa dihapus`, }; } const deleted = await deleteSatuanBarang(id); if (!deleted) { return { ok: false, error: "Satuan tidak ditemukan" }; } revalidatePath("/master/satuan-barang"); return { ok: true }; } catch (error) { console.error("[hapusSatuanBarang] gagal", { userId: user.id, id }, error); return { ok: false, error: "Gagal menghapus satuan, coba hapus ulang", }; } }