134 lines
3.8 KiB
TypeScript
134 lines
3.8 KiB
TypeScript
"use client";
|
|
|
|
import { ArrowLeft } from "lucide-react";
|
|
import { useRouter } from "next/navigation";
|
|
import { useState } from "react";
|
|
import { Button } from "@/components/ui/button";
|
|
import { AdminItemForm, type ItemFormPayload } from "./AdminItemForm";
|
|
import { ItemAiAssistant, type ItemAiPrefill } from "./ItemAiAssistant";
|
|
|
|
interface AdminItemCreatePageProps {
|
|
locale: string;
|
|
categories: string[];
|
|
serverOptions: string[];
|
|
}
|
|
|
|
export function AdminItemCreatePage({
|
|
locale,
|
|
categories,
|
|
serverOptions,
|
|
}: AdminItemCreatePageProps) {
|
|
const router = useRouter();
|
|
const [submitting, setSubmitting] = useState(false);
|
|
const [error, setError] = useState<string | null>(null);
|
|
const [prefillData, setPrefillData] = useState<ItemAiPrefill | null>(null);
|
|
|
|
const goBackToList = () => {
|
|
router.push(`/${locale}/admin?tab=items`);
|
|
};
|
|
|
|
const handleSubmit = async (payload: ItemFormPayload) => {
|
|
setSubmitting(true);
|
|
setError(null);
|
|
|
|
try {
|
|
const body: Record<string, unknown> = {
|
|
name: payload.name,
|
|
category: payload.category,
|
|
rarity: payload.rarity,
|
|
imageUrl: payload.imageUrl,
|
|
imageLocalPath: payload.imageLocalPath,
|
|
level: payload.level,
|
|
weight: payload.weight,
|
|
slots: payload.slots,
|
|
skill: payload.skill,
|
|
description: payload.description,
|
|
servers: payload.servers,
|
|
tags: payload.tags,
|
|
metadata: payload.metadata,
|
|
fields: payload.fields,
|
|
server: payload.server ?? null,
|
|
};
|
|
|
|
const response = await fetch("/api/admin/items", {
|
|
method: "POST",
|
|
credentials: "include",
|
|
headers: { "Content-Type": "application/json" },
|
|
body: JSON.stringify(body),
|
|
});
|
|
|
|
if (!response.ok) {
|
|
const data = await response
|
|
.json()
|
|
.catch(() => ({ error: "Erro ao criar item" }));
|
|
throw new Error(data?.error || data?.message || "Falha ao criar item");
|
|
}
|
|
|
|
goBackToList();
|
|
} catch (err) {
|
|
console.error(err);
|
|
setError(
|
|
err instanceof Error
|
|
? err.message
|
|
: "Erro ao criar item. Tente novamente.",
|
|
);
|
|
} finally {
|
|
setSubmitting(false);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<div className="space-y-6">
|
|
<div className="flex flex-wrap items-center justify-between gap-3">
|
|
<div className="space-y-1">
|
|
<h1 className="text-3xl font-bold tracking-tight">Novo item</h1>
|
|
<p className="text-muted-foreground max-w-2xl">
|
|
Utilize a seção de IA abaixo para gerar automaticamente campos
|
|
sugeridos a partir de prints e descrições. Ajuste o que for
|
|
necessário antes de publicar.
|
|
</p>
|
|
</div>
|
|
<Button variant="outline" onClick={goBackToList} className="gap-2">
|
|
<ArrowLeft className="h-4 w-4" />
|
|
Voltar
|
|
</Button>
|
|
</div>
|
|
|
|
<ItemAiAssistant
|
|
locale={locale}
|
|
categories={categories}
|
|
serverOptions={serverOptions}
|
|
onGenerated={({ json, prefill }) => {
|
|
setPrefillData({
|
|
...prefill,
|
|
metadata: {
|
|
aiStructure: json ?? null,
|
|
...prefill.metadata,
|
|
},
|
|
});
|
|
}}
|
|
/>
|
|
|
|
{error && (
|
|
<div className="rounded-md border border-destructive/40 bg-destructive/10 px-4 py-3 text-sm text-destructive">
|
|
{error}
|
|
</div>
|
|
)}
|
|
|
|
<div className="rounded-lg border bg-card">
|
|
<AdminItemForm
|
|
mode="create"
|
|
categories={categories}
|
|
serverOptions={serverOptions}
|
|
onSubmit={handleSubmit}
|
|
submitting={submitting}
|
|
onCancel={goBackToList}
|
|
isActive
|
|
allowAiTools={false}
|
|
prefillData={prefillData}
|
|
/>
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|