TypeScript 50.6%
JavaScript 46.1%
SQL 2.1%
Shell 0.6%
CSS 0.5%
1"use client";2import Link from "next/link";3import { useRouter } from "next/navigation";4import { useState } from "react";5export function ListingRowActions({ id, slug, status, listingType }: { id: string; slug: string; status: string; listingType: string }) {6 const router = useRouter(); const [busy, setBusy] = useState(false); const [msg, setMsg] = useState<string | null>(null);7 const act = async (a: string) => { setBusy(true); setMsg(null); const r = await fetch(`/api/listings/${id}/${a}`, { method: "POST" }); const d = await r.json(); setBusy(false); if (!r.ok) setMsg(d.problems ? d.problems.join(" · ") : d.error?.message ?? "Erreur"); else router.refresh(); };8 const del = async () => { if (!confirm("Supprimer ce brouillon ?")) return; await fetch(`/api/listings/${id}`, { method: "DELETE" }); router.refresh(); };9 return (10 <div className="flex flex-col gap-1 items-end text-xs shrink-0">11 <Link href={`/membre/annonces/${id}`} className="tv-btn tv-btn-ghost !py-1 !px-3">Modifier</Link>12 {status === "PUBLISHED" && <a href={`/annonce/${encodeURIComponent("toveli:" + slug)}`} className="underline text-ink-2" target="_blank" rel="noreferrer">Voir en ligne</a>}13 {["DRAFT", "PAUSED", "REJECTED"].includes(status) && <button type="button" disabled={busy} onClick={() => act(status === "PAUSED" ? "resume" : "publish")} className="underline text-brand-dark">{status === "PAUSED" ? "Réactiver" : "Publier"}</button>}14 {status === "PUBLISHED" && <button type="button" disabled={busy} onClick={() => act("pause")} className="underline text-ink-2">Mettre en pause</button>}15 {["PUBLISHED", "PAUSED"].includes(status) && <button type="button" disabled={busy} onClick={() => act(listingType === "RENT" ? "mark-rented" : "mark-sold")} className="underline text-ink-2">{listingType === "RENT" ? "Marquer louée" : "Marquer vendue"}</button>}16 {["SOLD", "RENTED", "ARCHIVED"].includes(status) && <button type="button" disabled={busy} onClick={() => act("reopen")} className="underline text-ink-2">Rouvrir</button>}17 {!["ARCHIVED", "DRAFT"].includes(status) && <button type="button" disabled={busy} onClick={() => act("archive")} className="underline text-ink-3">Retirer</button>}18 {status === "DRAFT" && <button type="button" onClick={del} className="underline text-ink-3">Supprimer</button>}19 {msg && <p className="text-warn max-w-[220px] text-right">{msg}</p>}20 </div>21 );22}23