"use client" import { useState, useEffect } from "react" import { useForm } from "react-hook-form" import { zodResolver } from "@hookform/resolvers/zod" import * as z from "zod" import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter } from "@/components/ui/dialog" import { Button } from "@/components/ui/button" import { Form, FormControl, FormField, FormItem, FormLabel, FormMessage, FormDescription, } from "@/components/ui/form" import { Input } from "@/components/ui/input" import { Switch } from "@/components/ui/switch" import { Textarea } from "@/components/ui/textarea" import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs" // Assume these exist or need verify import { Setting } from "@/types/setting" import { settingService } from "@/services/settingService" import { toast } from "sonner" import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue, } from "@/components/ui/select" const formSchema = z.object({ title: z.string().min(2, "Başlık en az 2 karakter olmalı"), slogan: z.string().optional(), url: z.string().url("Geçerli bir URL giriniz").optional().or(z.literal("")), email: z.string().email("Geçerli bir e-posta giriniz").optional().or(z.literal("")), phone: z.string().optional(), address: z.string().optional(), copyright: z.string().optional(), map_embed: z.string().optional(), meta_title: z.string().optional(), meta_description: z.string().optional(), // Social facebook: z.string().url().optional().or(z.literal("")), x: z.string().url().optional().or(z.literal("")), instagram: z.string().url().optional().or(z.literal("")), whatsapp: z.string().optional(), // clean number usually linkedin: z.string().url().optional().or(z.literal("")), pinterest: z.string().url().optional().or(z.literal("")), // Config is_active: z.boolean().default(false), // Images W Logo w_logo: z.any().optional(), w_width: z.coerce.number().min(1).default(100), w_height: z.coerce.number().min(1).default(100), w_quality: z.coerce.number().min(1).max(100).default(85), w_format: z.string().default("avif"), // Images B Logo b_logo: z.any().optional(), b_width: z.coerce.number().min(1).default(100), b_height: z.coerce.number().min(1).default(100), b_quality: z.coerce.number().min(1).max(100).default(85), b_format: z.string().default("avif"), }) interface SettingDialogProps { open: boolean onOpenChange: (open: boolean) => void setting?: Setting | null onSuccess?: () => void } export function SettingDialog({ open, onOpenChange, setting, onSuccess }: SettingDialogProps) { const [loading, setLoading] = useState(false) const [wPreview, setWPreview] = useState(null) const [bPreview, setBPreview] = useState(null) const form = useForm>({ // eslint-disable-next-line @typescript-eslint/no-explicit-any resolver: zodResolver(formSchema) as any, defaultValues: { title: "", slogan: "", url: "", email: "", phone: "", address: "", copyright: "", map_embed: "", meta_title: "", meta_description: "", facebook: "", x: "", instagram: "", whatsapp: "", linkedin: "", pinterest: "", is_active: false, w_width: 100, w_height: 100, w_quality: 85, w_format: "avif", b_width: 100, b_height: 100, b_quality: 85, b_format: "avif", }, }) useEffect(() => { if (setting) { form.reset({ title: setting.title, slogan: setting.slogan || "", url: setting.url || "", email: setting.email || "", phone: setting.phone || "", address: setting.address || "", copyright: setting.copyright || "", map_embed: setting.map_embed || "", meta_title: setting.meta_title || "", meta_description: setting.meta_description || "", facebook: setting.facebook || "", x: setting.x || "", instagram: setting.instagram || "", whatsapp: setting.whatsapp || "", linkedin: setting.linkedin || "", pinterest: setting.pinterest || "", is_active: !!setting.is_active, w_width: setting.w_width || 100, w_height: setting.w_height || 100, w_quality: setting.w_quality || 85, w_format: setting.w_format || "avif", b_width: setting.b_width || 100, b_height: setting.b_height || 100, b_quality: setting.b_quality || 85, b_format: setting.b_format || "avif", }) // Set previews // Assuming backend serves images from a static path, need env URL const apiUrl = process.env.NEXT_PUBLIC_API_URL || "http://localhost:8080" if (setting.w_logo) { // Check if it's already a full URL or relative setWPreview(setting.w_logo.startsWith("http") ? setting.w_logo : `${apiUrl}${setting.w_logo}`) } if (setting.b_logo) { setBPreview(setting.b_logo.startsWith("http") ? setting.b_logo : `${apiUrl}${setting.b_logo}`) } } else { form.reset({ title: "", slogan: "", url: "", email: "", phone: "", address: "", copyright: "", map_embed: "", meta_title: "", meta_description: "", facebook: "", x: "", instagram: "", whatsapp: "", linkedin: "", pinterest: "", is_active: false, w_width: 100, w_height: 100, w_quality: 85, w_format: "avif", b_width: 100, b_height: 100, b_quality: 85, b_format: "avif", }) setWPreview(null) setBPreview(null) } }, [setting, form, open]) const handleImageChange = (e: React.ChangeEvent, fieldName: "w_logo" | "b_logo") => { const file = e.target.files?.[0] if (file) { form.setValue(fieldName, file) const reader = new FileReader() reader.onloadend = () => { if (fieldName === "w_logo") setWPreview(reader.result as string) else setBPreview(reader.result as string) } reader.readAsDataURL(file) } } const onSubmit = async (values: z.infer) => { setLoading(true) const formData = new FormData() // Append basic fields Object.entries(values).forEach(([key, value]) => { if (key !== "w_logo" && key !== "b_logo") { formData.append(key, String(value)) } }) // Append images if they are files if (values.w_logo instanceof File) { formData.append("w_logo", values.w_logo) } if (values.b_logo instanceof File) { formData.append("b_logo", values.b_logo) } try { if (setting) { await settingService.updateSetting(setting.ID, formData) toast.success("Ayar başarıyla güncellendi") } else { await settingService.createSetting(formData) toast.success("Ayar başarıyla oluşturuldu") } onOpenChange(false) if (onSuccess) onSuccess() } catch (error: unknown) { console.error("Setting save error:", error) toast.error((error as Error).message || "Bir hata oluştu") } finally { setLoading(false) } } return ( {setting ? "Ayar Düzenle" : "Yeni Ayar Ekle"}
Genel İletişim Sosyal Medya Görseller {/* GENERAL TAB */}
( Site Başlığı )} /> ( Slogan )} />
( Meta Başlığı )} /> ( Meta Açıklama )} />
(
Aktif Ayar Bu ayarı aktif yaparsanız, diğer tüm ayarlar otomatik olarak pasif duruma geçer.
)} />
{/* CONTACT TAB */}
( E-posta )} /> ( Telefon )} />
( Site URL )} /> ( Adres