1import{g as O,r as o,j as e,N as z,L as D,s as i,h as c}from"./index-Be_2bHJP.js";import{F as R}from"./Footer-DydoStv_.js";import{P as U}from"./plus-IV4fWgEX.js";import{L as q}from"./loader-circle-BezEXFER.js";import{P as A,T as M}from"./trash-2-dik4pVU8.js";/** 2 * @license lucide-react v0.462.0 - ISC 3 * 4 * This source code is licensed under the ISC license. 5 * See the LICENSE file in the root directory of this source tree. 6 */const V=O("GripVertical",[["circle",{cx:"9",cy:"12",r:"1",key:"1vctgf"}],["circle",{cx:"9",cy:"5",r:"1",key:"hp0tcf"}],["circle",{cx:"9",cy:"19",r:"1",key:"fkjjf6"}],["circle",{cx:"15",cy:"12",r:"1",key:"1tmaij"}],["circle",{cx:"15",cy:"5",r:"1",key:"19l28e"}],["circle",{cx:"15",cy:"19",r:"1",key:"f4zoj3"}]]),k=["now","next","later","done"],C=["Nova Web","Nova Voice","Nova Messaging","Nova Companion","Novaco Insights","Platform"],S={title:"",product:C[0],status:"next",progress:0,sort_order:0},K=()=>{const[u,_]=o.useState([]),[T,I]=o.useState(!0),[l,f]=o.useState(null),[h,x]=o.useState(!1),[s,n]=o.useState(S),[b,j]=o.useState(!1),[N,v]=o.useState(!1),p=async()=>{const{data:t}=await i.from("roadmap_items").select("*").order("sort_order",{ascending:!0});_(t||[]),I(!1)};o.useEffect(()=>{p()},[]);const g=()=>{n(S),f(null),x(!1)},P=t=>{n({title:t.title,product:t.product,status:t.status,progress:t.progress,sort_order:t.sort_order}),f(t.id),x(!0)},E=async t=>{confirm("Delete this roadmap item?")&&(await i.from("roadmap_items").delete().eq("id",t),c.success("Item deleted"),p())},y=async(t,r)=>{v(!0);try{const{data:a,error:d}=await i.functions.invoke("translate-roadmap",{body:{title:t,itemId:r}});if(d)throw d;return(a==null?void 0:a.translations)||null}catch(a){return console.error("Translation error:",a),c.error("Translation failed â item saved without translations"),null}finally{v(!1)}},F=async t=>{if(t.preventDefault(),!s.title||!s.product){c.error("Title and product are required");return}j(!0);try{if(l){const r=u.find(m=>m.id===l),a=(r==null?void 0:r.title)!==s.title,d={title:s.title,product:s.product,status:s.status,progress:s.progress,sort_order:s.sort_order};if(a){const m=await y(s.title,l);m&&(d.translations=m)}const{error:w}=await i.from("roadmap_items").update(d).eq("id",l);if(w)throw w;c.success("Item updated")}else{const r=await y(s.title),{error:a}=await i.from("roadmap_items").insert({title:s.title,product:s.product,status:s.status,progress:s.progress,sort_order:s.sort_order,translations:r||{}});if(a)throw a;c.success("Item created")}g(),p()}catch(r){c.error(r.message||"Something went wrong")}j(!1)},L=k.map(t=>({status:t,items:u.filter(r=>r.status===t)})).filter(t=>t.items.length>0);return e.jsxs("div",{className:"min-h-screen",children:[e.jsx(z,{}),e.jsx("section",{className:"pt-32 pb-24 px-6",children:e.jsxs("div",{className:"container mx-auto max-w-4xl",children:[e.jsxs("div",{className:"flex items-center justify-between mb-8",children:[e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-center gap-3 mb-2",children:[e.jsx("p",{className:"text-sm font-semibold uppercase tracking-widest text-accent",children:"Novaco Insights"}),e.jsx(D,{to:"/admin/demos",className:"text-xs text-muted-foreground hover:text-foreground transition-colors",children:"Demo Pages â"})]}),e.jsx("h1",{className:"font-display text-3xl font-bold",children:"Roadmap"}),e.jsx("p",{className:"text-muted-foreground mt-1 text-sm",children:"Manage roadmap items. Titles are entered in English and automatically translated."})]}),!h&&e.jsxs("button",{onClick:()=>{g(),x(!0)},className:"btn-accent-glass inline-flex items-center gap-2 rounded-xl px-5 py-2.5 text-sm font-semibold text-accent-foreground",children:[e.jsx(U,{size:16})," New item"]})]}),h&&e.jsxs("form",{onSubmit:F,className:"glass-card rounded-2xl p-8 mb-8 space-y-5",children:[e.jsx("h2",{className:"font-display text-lg font-bold",children:l?"Edit item":"New roadmap item"}),e.jsxs("div",{children:[e.jsx("label",{className:"text-xs font-medium text-muted-foreground mb-1 block",children:"Title (English) *"}),e.jsx("input",{value:s.title,onChange:t=>n({...s,title:t.target.value}),className:"w-full rounded-lg border border-border/50 bg-background px-4 py-2.5 text-sm outline-none focus:border-accent transition-colors",placeholder:"e.g. Multi-language support for chat widget"})]}),e.jsxs("div",{className:"grid sm:grid-cols-2 gap-4",children:[e.jsxs("div",{children:[e.jsx("label",{className:"text-xs font-medium text-muted-foreground mb-1 block",children:"Product *"}),e.jsx("select",{value:s.product,onChange:t=>n({...s,product:t.target.value}),className:"w-full rounded-lg border border-border/50 bg-background px-4 py-2.5 text-sm outline-none focus:border-accent transition-colors",children:C.map(t=>e.jsx("option",{value:t,children:t},t))})]}),e.jsxs("div",{children:[e.jsx("label",{className:"text-xs font-medium text-muted-foreground mb-1 block",children:"Status *"}),e.jsx("select",{value:s.status,onChange:t=>n({...s,status:t.target.value}),className:"w-full rounded-lg border border-border/50 bg-background px-4 py-2.5 text-sm outline-none focus:border-accent transition-colors",children:k.map(t=>e.jsx("option",{value:t,children:t.charAt(0).toUpperCase()+t.slice(1)},t))})]})]}),e.jsxs("div",{className:"grid sm:grid-cols-2 gap-4",children:[e.jsxs("div",{children:[e.jsx("label",{className:"text-xs font-medium text-muted-foreground mb-1 block",children:"Progress (%)"}),e.jsx("input",{type:"number",min:0,max:100,value:s.progress,onChange:t=>n({...s,progress:parseInt(t.target.value)||0}),className:"w-full rounded-lg border border-border/50 bg-background px-4 py-2.5 text-sm outline-none focus:border-accent transition-colors"})]}),e.jsxs("div",{children:[e.jsx("label",{className:"text-xs font-medium text-muted-foreground mb-1 block",children:"Sort order"}),e.jsx("input",{type:"number",value:s.sort_order,onChange:t=>n({...s,sort_order:parseInt(t.target.value)||0}),className:"w-full rounded-lg border border-border/50 bg-background px-4 py-2.5 text-sm outline-none focus:border-accent transition-colors"})]})]}),e.jsxs("div",{className:"flex gap-3 pt-2",children:[e.jsx("button",{type:"submit",disabled:b||N,className:"btn-accent-glass inline-flex items-center gap-2 rounded-xl px-6 py-2.5 text-sm font-semibold text-accent-foreground disabled:opacity-50",children:N?e.jsxs(e.Fragment,{children:[e.jsx(q,{size:14,className:"animate-spin"})," Translatingâ¦"]}):b?"Savingâ¦":l?"Update":"Create"}),e.jsx("button",{type:"button",onClick:g,className:"glass-card rounded-xl px-6 py-2.5 text-sm font-semibold text-foreground",children:"Cancel"})]})]}),T?e.jsx("div",{className:"text-muted-foreground text-center py-12",children:"Loadingâ¦"}):u.length===0?e.jsx("div",{className:"glass-card rounded-2xl p-12 text-center",children:e.jsx("p",{className:"text-muted-foreground",children:"No roadmap items yet."})}):e.jsx("div",{className:"space-y-8",children:L.map(t=>e.jsxs("div",{children:[e.jsxs("h3",{className:"text-sm font-semibold uppercase tracking-widest text-muted-foreground mb-3",children:[t.status," (",t.items.length,")"]}),e.jsx("div",{className:"space-y-2",children:t.items.map(r=>e.jsxs("div",{className:"glass-card rounded-xl p-4 flex items-center gap-3",children:[e.jsx(V,{size:14,className:"text-muted-foreground
6/40 flex-shrink-0"}),e.jsxs("div",{className:"flex-1 min-w-0",children:[e.jsx("p",{className:"font-medium text-sm truncate",children:r.title}),e.jsxs("div",{className:"flex items-center gap-2 mt-0.5",children:[e.jsx("span",{className:"text-xs text-muted-foreground",children:r.product}),r.progress>0&&r.progress<100&&e.jsxs("span",{className:"text-xs text-accent",children:[r.progress,"%"]}),r.translations&&Object.keys(r.translations).length>0&&e.jsxs("span",{className:"text-[10px] bg-accent/10 text-accent px-1.5 py-0.5 rounded",children:[Object.keys(r.translations).length," translations"]})]})]}),e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsx("button",{onClick:()=>P(r),className:"p-2 rounded-lg hover:bg-accent/10 transition-colors text-muted-foreground hover:text-accent",children:e.jsx(A,{size:14})}),e.jsx("button",{onClick:()=>E(r.id),className:"p-2 rounded-lg hover:bg-red-500/10 transition-colors text-muted-foreground hover:text-red-500",children:e.jsx(M,{size:14})})]})]},r.id))})]},t.status))})]})}),e.jsx(R,{})]})};export{K as default};
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.