1import{c as Ws,r as n,s as j,j as e,ar as ws,B as V,J as Js,O as Ks,Q as Qs,V as Xs,bM as Ps,bO as Ms,bP as Ys,b as v,L as q,ae as p,D as Ee,a as Ie,d as Le,e as ze,aj as es,f as Zs,a8 as Ue,am as bs,U as et,bN as st,ad as tt,bF as Oe,t as pe,y as ss,a5 as ke,ac as qe,bE as at,k as $s,S as Cs}from"./index-B8M9ps1T.js";import{C as J,c as oe,d as me,a as K,e as je}from"./card-DzCf0Wp_.js";import{T as Fs,a as Ts,b as ie,c as ce}from"./tabs-zzllh7vg.js";import{T as Es,a as Is,b as Be,c as te,d as Ls,e as ae}from"./table-CTVRo96p.js";import{A as Ss}from"./arrow-down-DYyOk26h.js";import{f as zs}from"./format-BTUpIa5v.js";import{I as b}from"./input-CerV3gOV.js";import{L as h}from"./label-DF1VlBtP.js";import{M as rt}from"./MyRewardsDashboard-e_QVmg2z.js";import{E as Ve}from"./eye-DwmRuwCq.js";import{R as rs}from"./refresh-cw-BgJzFfdP.js";import{T as fe}from"./textarea-DdRoT87k.js";import{S as ue}from"./switch-DlX2D2PP.js";import{S as Ne,a as ye,b as we,c as be,d as X}from"./select-B30Rlv9Z.js";import{S as it}from"./send-Cq96VOlB.js";import{U as nt}from"./user-plus-D5-c6eZm.js";import{P as He}from"./pencil-BXpbd9n1.js";import{C as lt}from"./cake-B1gNwt2h.js";import{L as dt}from"./lock-cMy7Y-lu.js";import{C as ct}from"./calculator-BNpuK-OZ.js";import{C as ts,m as ks,f as ot}from"./catalogMatchMode-DBoOjTrY.js";import{P as mt}from"./plus-D0Ml6N8h.js";import{T as ut}from"./trash-2-CY-Xk7Tz.js";import{E as Us}from"./external-link-BpJE8Y7I.js";import{S as ht}from"./search-e-4vjIwh.js";import{A as Ke,a as Qe,b as Xe}from"./alert-BdRdXLxS.js";import{C as xt}from"./circle-check-b9HLETk4.js";import{T as As}from"./triangle-alert-BeXbapDX.js";import{T as pt}from"./trophy-7o1zsS3T.js";import"./en-US-BOoww7nS.js";import"./progress-BgvGXmD4.js";import"./AccountHoldDisclaimer-DYGri-Wy.js";import"./circle-alert-DzIfzSNA.js";import"./PersonalVehiclesOnlyDisclaimer-Bb1swtmV.js";import"./RewardsTermsAcceptance-CQhmPNvw.js";import"./checkbox-BSnUNt5S.js";import"./index-CO7TY0pN.js";import"./RewardsTermsContent-NXqQkl-3.js";import"./arrow-right-BwLaIySX.js";import"./receipt-B-kL2XOF.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 as=Ws("Coins",[["circle",{cx:"8",cy:"8",r:"6",key:"3yglwk"}],["path",{d:"M18.09 10.37A6 6 0 1 1 10.34 18",key:"t5s6rm"}],["path",{d:"M7 6h1v4",key:"1obek4"}],["path",{d:"m16.71 13.88.7.71-2.82 2.82",key:"1rbuyh"}]]);function gt(){const[t,c]=n.useState([]),[_,S]=n.useState(!0),[i,g]=n.useState("date"),[N,y]=n.useState("desc");n.useEffect(()=>{j.from("reward_claims").select("*").order("created_at",{ascending:!1}).limit(200).then(({data:m})=>{const l=(m||[]).filter(w=>{if(w.status==="pending")return!1;const A=(w.customer_name||"").toLowerCase(),P=(w.invoice_number||"").toLowerCase();return!(A.includes("demo")||A.includes("test")||P.includes("demo")||P.includes("test"))});c(l),S(!1)})},[]);const s=n.useMemo(()=>{const m=[...t];return m.sort((l,w)=>{if(i==="points")return N==="asc"?l.points_awarded-w.points_awarded:w.points_awarded-l.points_awarded;const A=new Date(l.verified_at||l.created_at).getTime(),P=new Date(w.verified_at||w.created_at).getTime();return N==="asc"?A-P:P-A}),m},[t,i,N]),d=m=>{i===m?y(l=>l==="desc"?"asc":"desc"):(g(m),y("desc"))};return e.jsxs(J,{children:[e.jsx(oe,{children:e.jsx(me,{children:"All Claims"})}),e.jsx(K,{children:_?e.jsx("p",{className:"text-sm text-muted-foreground",children:"Loadingâ¦"}):s.length===0?e.jsx("p",{className:"text-sm text-muted-foreground",children:"No claims yet."}):e.jsx("div",{className:"overflow-x-auto",children:e.jsxs(Es,{children:[e.jsx(Is,{children:e.jsxs(Be,{children:[e.jsx(te,{children:"Invoice"}),e.jsx(te,{children:"Customer"}),e.jsx(te,{children:"Phone"}),e.jsx(te,{className:"text-right",children:"Amount"}),e.jsx(te,{className:"cursor-pointer select-none hover:text-foreground text-right",onClick:()=>d("points"),children:e.jsxs("span",{className:"flex items-center justify-end gap-1",children:["Points",i==="points"&&(N==="desc"?e.jsx(Ss,{className:"h-3.5 w-3.5"}):e.jsx(ws,{className:"h-3.5 w-3.5"}))]})}),e.jsx(te,{children:"Status"}),e.jsx(te,{className:"cursor-pointer select-none hover:text-foreground",onClick:()=>d("date"),children:e.jsxs("span",{className:"flex items-center gap-1",children:["Date",i==="date"&&(N==="desc"?e.jsx(Ss,{className:"h-3.5 w-3.5"}):e.jsx(ws,{className:"h-3.5 w-3.5"}))]})})]})}),e.jsx(Ls,{children:s.map(m=>e.jsxs(Be,{children:[e.jsx(ae,{className:"font-medium",children:m.invoice_number}),e.jsx(ae,{children:m.customer_name||"â"}),e.jsx(ae,{className:"text-sm text-muted-foreground",children:m.customer_phone||"â"}),e.jsxs(ae,{className:"text-right",children:["$",Number(m.invoice_amount).toFixed(2)]}),e.jsx(ae,{className:"text-right font-semibold",children:m.points_awarded}),e.jsx(ae,{children:e.jsx(V,{variant:m.status==="verified"?"default":m.status==="pending"?"secondary":"destructive",children:m.status})}),e.jsx(ae,{className:"text-sm text-muted-foreground",children:zs(new Date(m.verified_at||m.created_at),"MMM d, yyyy")})]},m.id))})]})})})]})}function ft({customerId:t,customerName:c,customerPhone:_,onClose:S}){const[i,g]=n.useState(!1),[N,y]=n.useState(null),s=async m=>{g(!0),y(null);try{const{data:l,error:w}=await j.functions.invoke("admin-preview-member-rewards",{body:{customer_id:m}});if(w)throw w;if(l!=null&&l.error)throw new Error(l.error);y(l)}catch(l){p.error(`Preview failed: ${(l==null?void 0:l.message)||"Unknown error"}`)}finally{g(!1)}};n.useEffect(()=>{t?s(t):y(null)},[t]);const d=!!t;return e.jsx(Js,{open:d,onOpenChange:m=>!m&&S(),children:e.jsxs(Ks,{side:"left",className:"w-full sm:max-w-md overflow-y-auto",children:[e.jsxs(Qs,{className:"space-y-2",children:[e.jsxs("div",{className:"flex items-center justify-between gap-2",children:[e.jsxs(Xs,{className:"flex items-center gap-2",children:[e.jsx(Ve,{className:"h-4 w-4 text-primary"}),"Member Preview"]}),e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx(V,{variant:"secondary",className:"text-xs",children:"Read-only"}),e.jsx(Ps,{className:"h-8 w-8 border border-muted bg-red-600 text-white",children:e.jsx(Ms,{className:"bg-red-600 text-white text-xs font-semibold",children:c?c.split(" ").map(m=>{var l;return(l=m[0])==null?void 0:l.toUpperCase()}).join("").slice(0,2):"U"})})]})]}),e.jsxs(Ys,{className:"text-xs",children:["Viewing as ",e.jsx("span",{className:"font-medium text-foreground",children:c||"â"}),_?e.jsxs(e.Fragment,{children:[" · ",_]}):null]}),e.jsx("div",{children:e.jsxs(v,{variant:"outline",size:"sm",onClick:()=>t&&s(t),disabled:i,children:[e.jsx(rs,{className:`h-3.5 w-3.5 mr-2 ${i?"animate-spin":""}`}),"Refresh"]})})]}),e.jsxs("div",{className:"mt-4",children:[i&&e.jsxs("div",{className:"flex items-center justify-center py-12 text-muted-foreground text-sm",children:[e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"})," Loading previewâ¦"]}),!i&&N&&e.jsx(rt,{result:N,onSignOut:S,previewMode:!0})]})]})})}function jt({open:t,onOpenChange:c,customerId:_,customerName:S}){const[i,g]=n.useState(""),[N,y]=n.useState(""),[s,d]=n.useState(""),[m,l]=n.useState("info"),[w,A]=n.useState(!1),[P,B]=n.useState(!0),[M,Y]=n.useState(!1),Q=()=>{g(""),y(""),d(""),l("info"),A(!1),B(!0)},ne=async()=>
6{if(_){if(!i.trim()){p.error("Title is required");return}Y(!0);try{const{data:o,error:R}=await j.functions.invoke("send-customer-message",{body:{customer_id:_,title:i.trim(),body:N.trim()||null,link:s.trim()||null,severity:m,pinned:w,send_push:P}});if(R||o!=null&&o.error)throw new Error((o==null?void 0:o.error)||(R==null?void 0:R.message)||"Failed to send");const F=o==null?void 0:o.push;p.success((F==null?void 0:F.sent)>0?`Message sent. Push delivered to ${F.sent} device${F.sent===1?"":"s"}.`:"Message saved to the member's Message Center."),Q(),c(!1)}catch(o){p.error((o==null?void 0:o.message)||"Failed to send message")}finally{Y(!1)}}};return e.jsx(Ee,{open:t,onOpenChange:o=>{M||c(o)},children:e.jsxs(Ie,{className:"max-w-lg",children:[e.jsxs(Le,{children:[e.jsxs(ze,{className:"flex items-center gap-2",children:[e.jsx(es,{className:"h-5 w-5 text-primary"}),"Send Message"]}),e.jsxs(Zs,{children:["Send a personal message to"," ",e.jsx("span",{className:"font-medium text-foreground",children:S||"this member"}),". It will appear in their Rewards Message Center."]})]}),e.jsxs("div",{className:"space-y-4 py-2",children:[e.jsxs("div",{className:"space-y-1.5",children:[e.jsx(h,{htmlFor:"msg-title",children:"Title"}),e.jsx(b,{id:"msg-title",value:i,onChange:o=>g(o.target.value),placeholder:"e.g. Your birthday gift is ready",maxLength:200})]}),e.jsxs("div",{className:"space-y-1.5",children:[e.jsx(h,{htmlFor:"msg-body",children:"Message (optional)"}),e.jsx(fe,{id:"msg-body",value:N,onChange:o=>y(o.target.value),placeholder:"Add details for the memberâ¦",rows:4,maxLength:2e3}),e.jsxs("p",{className:"text-[10px] text-muted-foreground text-right",children:[N.length,"/2000"]})]}),e.jsxs("div",{className:"grid grid-cols-2 gap-3",children:[e.jsxs("div",{className:"space-y-1.5",children:[e.jsx(h,{htmlFor:"msg-severity",children:"Type"}),e.jsxs(Ne,{value:m,onValueChange:o=>l(o),children:[e.jsx(ye,{id:"msg-severity",children:e.jsx(we,{})}),e.jsxs(be,{children:[e.jsx(X,{value:"info",children:"Info"}),e.jsx(X,{value:"success",children:"Success"}),e.jsx(X,{value:"warning",children:"Warning"}),e.jsx(X,{value:"error",children:"Urgent"})]})]})]}),e.jsxs("div",{className:"space-y-1.5",children:[e.jsx(h,{htmlFor:"msg-link",children:"Link (optional)"}),e.jsx(b,{id:"msg-link",value:s,onChange:o=>d(o.target.value),placeholder:"/my-rewards or https://â¦"})]})]}),e.jsxs("div",{className:"space-y-2 rounded-md border p-3 bg-muted/30",children:[e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsxs("div",{children:[e.jsx(h,{htmlFor:"msg-pinned",className:"text-sm",children:"Pin to top"}),e.jsx("p",{className:"text-[11px] text-muted-foreground",children:"Stays above other messages"})]}),e.jsx(ue,{id:"msg-pinned",checked:w,onCheckedChange:A})]}),e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsxs("div",{children:[e.jsx(h,{htmlFor:"msg-push",className:"text-sm",children:"Send push notification"}),e.jsx("p",{className:"text-[11px] text-muted-foreground",children:"Notifies devices that have the rewards app installed"})]}),e.jsx(ue,{id:"msg-push",checked:P,onCheckedChange:B})]})]})]}),e.jsxs(Ue,{children:[e.jsx(v,{variant:"outline",onClick:()=>c(!1),disabled:M,children:"Cancel"}),e.jsxs(v,{onClick:ne,disabled:M||!i.trim(),children:[M?e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"}):e.jsx(it,{className:"h-4 w-4 mr-2"}),"Send Message"]})]})]})})}function Ye(t){const c=t.replace(/\D/g,"").replace(/^1/,"").slice(0,10);return c.length===0?"":c.length<=3?`(${c}`:c.length<=6?`(${c.slice(0,3)}) ${c.slice(3)}`:`(${c.slice(0,3)}) ${c.slice(3,6)}-${c.slice(6)}`}function Rs(t){const c=t.replace(/\D/g,"").replace(/^1/,"").slice(0,10);return c.length===10?`+1${c}`:""}function _t(){const[t,c]=n.useState([]),[_,S]=n.useState(!0),[i,g]=n.useState(null),[N,y]=n.useState(""),[s,d]=n.useState(""),[m,l]=n.useState(""),[w,A]=n.useState(""),[P,B]=n.useState(null),[M,Y]=n.useState(null),[Q,ne]=n.useState(null),[o,R]=n.useState(!1),[F,L]=n.useState(!1),[z,H]=n.useState(""),[x,re]=n.useState(!1),E=n.useRef(null),[Z,_e]=n.useState(null),[r,u]=n.useState(null),[D,le]=n.useState(null),[G,de]=n.useState(!1),[U,Ae]=n.useState(!1),[is,ns]=n.useState(""),[Re,ls]=n.useState(""),[ds,cs]=n.useState(""),[os,ms]=n.useState("0"),[us,hs]=n.useState(!0),[ee,De]=n.useState(null),[xe,xs]=n.useState("add"),[Ge,We]=n.useState("0"),[ps,gs]=n.useState(""),[Pe,Je]=n.useState(!1),[Ce,Os]=n.useState(.1),[Se,fs]=n.useState(""),js=a=>{De(a),xs("add"),We("0"),gs(""),fs("")},qs=async()=>
6{if(!ee)return;const a=Math.floor(Number(Ge)||0);if(a<0||xe!=="set"&&a===0){p.error("Enter a positive amount");return}const f=ee.total_points||0;let C=f;xe==="add"?C=f+a:xe==="subtract"?C=Math.max(0,f-a):C=a,Je(!0);const{error:I}=await j.from("customers").update({total_points:C,updated_at:new Date().toISOString()}).eq("id",ee.id);if(I){Je(!1),p.error(`Adjust failed: ${I.message}`);return}try{await j.from("reward_redemption_audit").insert({customer_id:ee.id,action:`manual_${xe}`,points_delta:C-f,points_before:f,points_after:C,notes:ps||`Manual ${xe} by admin`})}catch{}Je(!1),p.success(`Points updated: ${f} â ${C}`),c($=>$.map(T=>T.id===ee.id?{...T,total_points:C}:T)),De(null)},Bs=async()=>{var se,he;const a=is.trim();if(!a){p.error("Name is required");return}const f=Re?Rs(Re):"";if(Re&&!f){p.error("Phone must be a valid 10-digit Canadian number");return}const C=ds.trim().toLowerCase();if(C&&!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(C)){p.error("Invalid email address");return}if(!C&&!f){p.error("Provide an email or phone");return}const I=Math.max(0,Math.floor(Number(os)||0));Ae(!0);let $=null;if(f){const{data:k}=await j.from("customers").select("id").eq("phone",f).maybeSingle();k!=null&&k.id&&($=k.id)}if(!$&&C){const{data:k}=await j.from("customers").select("id").eq("email",C).maybeSingle();k!=null&&k.id&&($=k.id)}let T=$;if($){const{error:k}=await j.from("customers").update({full_name:a,phone:f||null,email:C||null,total_points:I,active:!0}).eq("id",$);if(k){Ae(!1),p.error(`Update failed: ${k.message}`);return}p.success("Existing customer updated as rewards member")}else{const{data:k,error:W}=await j.from("customers").insert({full_name:a,phone:f||null,email:C||null,total_points:I,active:!0}).select("id").single();if(W||!(k!=null&&k.id)){Ae(!1),p.error(`Create failed: ${(W==null?void 0:W.message)||"unknown"}`);return}T=k.id,p.success("Rewards member created")}if(us&&T){const{data:k,error:W}=await j.functions.invoke("admin-send-rewards-login",{body:{customer_id:T}});if(W||k!=null&&k.error)p.error(`Login info not sent: ${(k==null?void 0:k.error)||(W==null?void 0:W.message)||"unknown"}`);else{const ge=[];(se=k==null?void 0:k.email)!=null&&se.success&&ge.push("email"),(he=k==null?void 0:k.sms)!=null&&he.success&&ge.push("SMS"),p.success(ge.length?`Login info sent via ${ge.join(" + ")}`:"Login info sent")}}Ae(!1),de(!1),ns(""),ls(""),cs(""),ms("0"),hs(!0),vs()},_s=async(a,f="email")=>{var T,se;if(f==="email"&&!a.email){p.error("This member has no email on file");return}if(f==="sms"&&!a.phone){p.error("This member has no phone on file");return}if(!a.email&&!a.phone){p.error("This member has no email or phone on file");return}le(a.id);const{data:C,error:I}=await j.functions.invoke("admin-send-rewards-login",{body:{customer_id:a.id,channel:f}});if(le(null),I||C!=null&&C.error){p.error(`Failed: ${(C==null?void 0:C.error)||(I==null?void 0:I.message)||"unknown"}`);return}const $=[];(T=C==null?void 0:C.email)!=null&&T.success&&$.push("email"),(se=C==null?void 0:C.sms)!=null&&se.success&&$.push("SMS"),p.success($.length?`Login info sent via ${$.join(" + ")}`:"Login info sent")},vs=async()=>{S(!0);const[{data:a},{data:f},{data:C}]=await Promise.all([j.from("reward_claims").select("customer_id").eq("status","verified").not("customer_id","is",null).limit(5e3),j.from("reward_redemptions").select("customer_id").not("customer_id","is",null).limit(5e3),j.from("customers").select("id, full_name, phone, email, total_points").gt("total_points",0).limit(5e3)]),I={};for(const O of a||[])O.customer_id&&(I[O.customer_id]=(I[O.customer_id]||0)+1);const $=Object.keys(I),T=Array.from(new Set((f||[]).map(O=>O.customer_id).filter(Boolean))),se=new Set([...(C||[]).map(O=>O.id),...$,...T]);let he=[...C||[]];const k=new Set(he.map(O=>O.id)),W=[...se].filter(O=>!k.has(O));if(W.length){const O=Array.from({length:Math.ceil(W.length/500)},(Me,ys)=>W.slice(ys*500,ys*500+500)),ve=await Promise.all(O.map(Me=>j.from("customers").select("id, full_name, phone, email, total_points").in("id",Me)));he=he.concat(ve.flatMap(({data:Me})=>Me||[]))}const ge=he.filter(O=>{const ve=(O.full_name||"").toLowerCase();return!ve.includes("demo")&&!ve.includes("test")});ge.sort((O,ve)=>(ve.total_points||0)-(O.total_points||0)),c(ge.map(O=>({...O,claim_count:I[O.id]||0}))),S(!1)};n.useEffect(()=>{vs(),j.rpc("get_public_reward_settings").then(({data:a})=>{const f=Array.isArray(a)?a[0]:a;f!=null&&f.points_per_dollar&&Os(Number(f.points_per_dollar))})},[]);const Ns=async a=>{if(g(a),y(a.full_name||""),d(Ye(a.phone||"")),l(a.email||""),A(a.birthday||""),B(null),Y(null),ne(null),H(""),a.phone){const{data:f}=await j.from("customer_profiles").select("user_id, phone_e164, birthday, avatar_url").eq("phone_e164",a.phone).maybeSingle();f&&(Y(f.user_id||null),ne(f.phone_e164||null),f.birthday&&A(f.birthday),B(f.avatar_url||null))}},Vs=async a=>{var C,I;const f=(C=a.target.files)==null?void 0:C[0];
6if(!(!f||!i)){if(!M){p.error("This member has no login account yet â send login info first.");return}if(f.size>5*1024*1024){p.error("File too large (max 5 MB)");return}L(!0);try{const $=((I=f.name.split(".").pop())==null?void 0:I.toLowerCase())||"jpg",T=`${M}/avatar-${Date.now()}.${$}`,{error:se}=await j.storage.from("customer-avatars").upload(T,f,{upsert:!0,cacheControl:"3600"});if(se)throw se;const{data:he}=j.storage.from("customer-avatars").getPublicUrl(T),k=he.publicUrl,{error:W}=await j.from("customer_profiles").update({avatar_url:k}).eq("user_id",M);if(W)throw W;B(k),p.success("Profile picture updated")}catch($){p.error(`Upload failed: ${$.message}`)}finally{L(!1),E.current&&(E.current.value="")}}},Hs=async()=>{if(!i)return;if(z.length<8){p.error("Password must be at least 8 characters");return}re(!0);const{data:a,error:f}=await j.functions.invoke("admin-set-customer-password",{body:{customer_id:i.id,new_password:z}});if(re(!1),f||a!=null&&a.error){p.error(`Failed: ${(a==null?void 0:a.error)||(f==null?void 0:f.message)||"unknown"}`);return}H(""),p.success("Password updated for member")},Gs=async()=>{if(!i)return;const a=N.trim();if(!a){p.error("Name is required");return}const f=s?Rs(s):"";if(s&&!f){p.error("Phone must be a valid 10-digit Canadian number");return}const C=m.trim();if(C&&!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(C)){p.error("Invalid email address");return}R(!0);const{error:I}=await j.from("customers").update({full_name:a,phone:f||null,email:C||null,birthday:w||null}).eq("id",i.id);if(I){R(!1),p.error(`Update failed: ${I.message}`);return}if(M||Q){const $={birthday:w||null};f&&($.phone_e164=f);const T=j.from("customer_profiles").update($),{error:se}=M?await T.eq("user_id",M):await T.eq("phone_e164",Q);if(se){R(!1),p.error(`Profile update failed: ${se.message}`);return}}R(!1),p.success("Member updated"),c($=>$.map(T=>T.id===i.id?{...T,full_name:a,phone:f,email:C||null}:T)),g(null)};return e.jsxs(J,{children:[e.jsxs(oe,{className:"flex flex-row items-center justify-between gap-2 space-y-0",children:[e.jsx(me,{children:"Rewards Members"}),e.jsxs(v,{size:"sm",onClick:()=>de(!0),children:[e.jsx(nt,{className:"h-4 w-4 mr-2"})," Add Member"]})]}),e.jsx(K,{children:_?e.jsx("p",{className:"text-sm text-muted-foreground",children:"Loadingâ¦"}):t.length===0?e.jsx("p",{className:"text-sm text-muted-foreground",children:"No members yet."}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"overflow-x-auto hidden lg:block",children:e.jsxs(Es,{children:[e.jsx(Is,{children:e.jsxs(Be,{children:[e.jsx(te,{children:"Name"}),e.jsx(te,{children:"Phone"}),e.jsx(te,{children:"Email"}),e.jsx(te,{className:"text-right",children:"Claims"}),e.jsx(te,{className:"text-right",children:"Points"}),e.jsx(te,{className:"text-right",children:"Actions"})]})}),e.jsx(Ls,{children:t.map(a=>e.jsxs(Be,{children:[e.jsx(ae,{className:"font-medium",children:a.full_name}),e.jsx(ae,{className:"text-sm",children:a.phone}),e.jsx(ae,{className:"text-sm text-muted-foreground",children:a.email||"â"}),e.jsx(ae,{className:"text-right",children:a.claim_count}),e.jsx(ae,{className:"text-right font-bold text-primary",children:a.total_points}),e.jsx(ae,{className:"text-right",children:e.jsxs("div",{className:"flex items-center justify-end gap-1",children:[e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>_e(a),"aria-label":"Preview as member",title:"Preview as member",children:e.jsx(Ve,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>u(a),"aria-label":"Send message",title:"Send message",children:e.jsx(es,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>_s(a,"email"),disabled:D===a.id,"aria-label":"Email login info",title:"Email login info",children:D===a.id?e.jsx(q,{className:"h-4 w-4 animate-spin"}):e.jsx(bs,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>js(a),"aria-label":"Adjust points",title:"Adjust points",children:e.jsx(as,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>Ns(a),"aria-label":"Edit member",title:"Edit member",children:e.jsx(He,{className:"h-4 w-4"})})]})})]},a.id))})]})}),e.jsx("div",{className:"lg:hidden space-y-3",children:t.map(a=>e.jsxs("div",{className:"rounded-lg border bg-card p-3 shadow-sm",children:[e.jsxs("div",{className:"flex items-start justify-between gap-2",children:[e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsx("p",{className:"font-semibold truncate",children:a.full_name}),e.jsx("p",{className:"text-xs text-muted-foreground truncate",children:a.phone}),a.email&&e.jsx("p",{className:"text-xs text-muted-foreground truncate",children:a.email})]}),e.jsxs("div",{className:"text-right shrink-0",children:[e.jsx("p",{className:"text-lg font-bold text-primary leading-none",children:a.total_points}),e.jsx("p",{className:"text-[10px] uppercase tracking-wide text-muted-foreground mt-0.5",children:"pts"}),e.jsxs("p",{className:"text-[10px] text-muted-foreground mt-1",children:[a.claim_count," claim",a.claim_count===1?"":"s"]})]})]}),e.jsxs("div",{className:"flex items-center justify-end gap-1 mt-2 pt-2 border-t",children:[e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>_e(a),"aria-label":"Preview as member",children:e.jsx(Ve,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>u(a),"aria-label":"Send message",children:e.jsx(es,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>_s(a,"email"),disabled:D===a.id,"aria-label":"Email login info",children:D===a.id?e.jsx(q,{className:"h-4 w-4 animate-spin"}):e.jsx(bs,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>js(a),"aria-label":"Adjust points",children:e.jsx(as,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"sm",onClick:()=>Ns(a),"aria-label":"Edit member",children:e.jsx(He,{className:"h-4 w-4"})})]})]},a.id))})]})}),e.jsx(Ee,{open:!!i,onOpenChange:a=>!a&&g(null),children:e.jsxs(Ie,{className:"max-h-[90vh] overflow-y-auto sm:max-w-lg",children:[e.jsx(Le,{children:e.jsxs(ze,{children:["Edit Member",i?` â ${i.full_name}`:""]})}),e.jsxs("div",{className:"space-y-6 py-2",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsxs(h,{className:"flex items-center gap-2",children:[e.jsx(et,{className:"h-4 w-4"})," Profile Picture"]}),e.jsxs("div",{className:"flex items-center gap-4",children:[e.jsxs(Ps,{className:"h-16 w-16",children:[P&&e.jsx(st,{src:P,alt:"Profile"}),e.jsx(Ms,{children:(N||(i==null?void 0:i.full_name)||"?").split(" ").map(a=>a[0]).slice(0,2).join("").toUpperCase()})]}),e.jsxs("div",{children:[e.jsx("input",{ref:E,type:"file",accept:"image/*",hidden:!0,onChange:Vs}),e.jsxs(v,{type:"button",variant:"outline",size:"sm",onClick:()=>{var a;return(a=E.current)==null?void 0:a.click()},disabled:F||!M,children:[F?e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"}):e.jsx(tt,{className:"h-4 w-4 mr-2"}),F?"Uploadingâ¦":"Upload"]}),!M&&e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:"Member has no login account yet â send login info first."})]})]})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"member-name",children:"Full name"}),e.jsx(b,{id:"member-name",value:N,onChange:a=>y(a.target.value),placeholder:"Jane Doe"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"member-phone",children:"Phone"}),e.jsx(b,{id:"member-phone",value:s,onChange:a=>d(Ye(a.target.value)),placeholder:"(780) 555-1234",inputMode:"tel"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"member-email",children:"Email"}),e.jsx(b,{id:"member-email",type:"email",value:m,onChange:a=>l(a.target.value),placeholder:"[email protected]"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsxs(h,{htmlFor:"member-bday",className:"flex items-center gap-2",children:[e.jsx(lt,{className:"h-4 w-4"})," Birthday"]}),e.jsx(b,{id:"member-bday",type:"date",value:w,onChange:a=>A(a.target.value)}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"Used to grant the member's birthday reward each year."})]}),e.jsxs("div",{className:"space-y-2 border-t pt-4",children:[e.jsxs(h,{htmlFor:"member-newpw",className:"flex items-center gap-2",children:[e.jsx(dt,{className:"h-4 w-4"})," Set new password"]}),e.jsxs("div",{className:"flex gap-2",children:[e.jsx(b,{id:"member-newpw",type:"password",value:z,onChange:a=>H(a.target.value),placeholder:"At least 8 characters",disabled:!M}),e.jsx(v,{type:"button",variant:"secondary",onClick:Hs,disabled:x||!M||z.length<8,children:x?e.jsx(q,{className:"h-4 w-4 animate-spin"}):"Update"})]}),!M&&e.jsx("p",{className:"text-xs text-muted-foreground",children:"Member has no login account yet â send login info first."})]})]}),e.jsxs(Ue,{children:[e.jsx(v,{variant:"outline",onClick:()=>g(null),disabled:o,children:"Cancel"}),e.jsx(v,{onClick:Gs,disabled:o,children:o?"Savingâ¦":"Save"})]})]})}),e.jsx(Ee,{open:G,onOpenChange:a=>!U&&de(a),children:e.jsxs(Ie,{children:[e.jsx(Le,{children:e.jsx(ze,{children:"Add Rewards Member"})}),e.jsxs("div",{className:"space-y-4 py-2",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"new-name",children:"Full name *"}),e.jsx(b,{id:"new-name",value:is,onChange:a=>ns(a.target.value),placeholder:"Jane Doe"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"new-phone",children:"Phone"}),e.jsx(b,{id:"new-phone",value:Re,onChange:a=>ls(Ye(a.target.value)),placeholder:"(780) 555-1234",inputMode:"tel"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"new-email",children:"Email"}),e.jsx(b,{id:"new-email",type:"email",value:ds,onChange:a=>cs(a.target.value),placeholder:"[email protected]"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"new-points",children:"Starting points"}),e.jsx(b,{id:"new-points",type:"number",min:0,value:os,onChange:a=>ms(a.target.value)}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"Give yourself enough points to test redemption (e.g. 500)."})]}),e.jsxs("label",{className:"flex items-center gap-2 text-sm",children:[e.jsx("input",{type:"checkbox",checked:us,onChange:a=>hs(a.target.checked),className:"h-4 w-4"}),"Send login info (email + SMS) after creating"]}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"If a customer already exists with the same phone or email, it will be updated instead of duplicated."})]}),e.jsxs(Ue,{children:[e.jsx(v,{variant:"outline",onClick:()=>de(!1),disabled:U,children:"Cancel"}),e.jsx(v,{onClick:Bs,disabled:U,children:U?e.jsxs(e.Fragment,{children:[e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"})," Creatingâ¦"]}):"Create member"})]})]})}),e.jsx(ft,{customerId:(Z==null?void 0:Z.id)||null,customerName:Z==null?void 0:Z.full_name,customerPhone:Z==null?void 0:Z.phone,onClose:()=>_e(null)}),e.jsx(jt,{open:!!r,onOpenChange:a=>!a&&u(null),customerId:(r==null?void 0:r.id)||null,customerName:r==null?void 0:r.full_name}),e.jsx(Ee,{open:!!ee,onOpenChange:a=>!Pe&&!a&&De(null),children:e.jsxs(Ie,{children:[e.jsx(Le,{children:e.jsxs(ze,{children:["Adjust Points",ee?` â ${ee.full_name}`:""]})}),e.jsxs("div",{className:"space-y-4 py-2",children:[e.jsxs("p",{className:"text-sm text-muted-foreground",children:["Current balance: ",e.jsx("span",{className:"font-semibold text-foreground",children:(ee==null?void 0:ee.total_points)??0})," points"]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Action"}),e.jsx("div",{className:"grid grid-cols-3 gap-2",children:["add","subtract","set"].map(a=>e.jsx(v,{type:"button",variant:xe===a?"default":"outline",size:"sm",onClick:()=>xs(a),children:a==="add"?"Add":a==="subtract"?"Subtract":"Set to"},a))})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"adjust-amount",children:"Points"}
6),e.jsx(b,{id:"adjust-amount",type:"number",min:0,value:Ge,onChange:a=>We(a.target.value)}),ee&&e.jsxs("p",{className:"text-xs text-muted-foreground",children:["New balance: ",(()=>{const a=Math.floor(Number(Ge)||0),f=ee.total_points||0;return xe==="add"?f+a:xe==="subtract"?Math.max(0,f-a):a})()]})]}),e.jsxs("div",{className:"rounded-lg bg-muted/40 border border-border p-3 space-y-2",children:[e.jsxs("div",{className:"flex items-center gap-1.5",children:[e.jsx(ct,{className:"h-3.5 w-3.5 text-muted-foreground"}),e.jsx("span",{className:"text-xs font-medium text-muted-foreground uppercase tracking-wide",children:"Quick Calculator"})]}),e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("span",{className:"text-sm text-muted-foreground",children:"$"}),e.jsx(b,{type:"number",min:0,step:"0.01",placeholder:"Dollars spent",value:Se,onChange:a=>fs(a.target.value),className:"h-8 flex-1"}),e.jsx("span",{className:"text-sm text-muted-foreground",children:"="}),e.jsxs("span",{className:"text-sm font-semibold text-primary min-w-[3rem] text-right",children:[Math.floor(Number(Se||0)*Ce)," pts"]}),e.jsx(v,{type:"button",size:"sm",variant:"outline",className:"h-8 px-2",disabled:!Se||Number(Se)<=0,onClick:()=>We(String(Math.floor(Number(Se||0)*Ce))),children:"Use"})]}),e.jsxs("p",{className:"text-xs text-muted-foreground",children:["Rate: ",Ce>=1?`${Ce} points per $1`:`1 point per $${(1/Ce).toFixed(0)} spent`]})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{htmlFor:"adjust-reason",children:"Reason (optional)"}),e.jsx(b,{id:"adjust-reason",value:ps,onChange:a=>gs(a.target.value),placeholder:"e.g. Goodwill bonus, manual correction"})]})]}),e.jsxs(Ue,{children:[e.jsx(v,{variant:"outline",onClick:()=>De(null),disabled:Pe,children:"Cancel"}),e.jsx(v,{onClick:qs,disabled:Pe,children:Pe?e.jsxs(e.Fragment,{children:[e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"})," Savingâ¦"]}):"Apply"})]})]})})]})}function vt(){var y;const[t,c]=n.useState(null),[_,S]=n.useState(!1),[i,g]=n.useState([]);n.useEffect(()=>{j.from("reward_settings").select("*").order("created_at",{ascending:!1}).limit(1).maybeSingle().then(({data:s})=>c(s)),j.from("reward_catalog").select("id, title, gift_card_amount, gift_card_currency, is_active, reward_type").eq("is_active",!0).in("reward_type",["gift_card","birthday_only"]).order("gift_card_amount",{ascending:!0}).then(({data:s})=>g(s||[]))},[]);const N=async()=>{var d,m;if(!t)return;S(!0);const{error:s}=await j.from("reward_settings").update({points_per_dollar:t.points_per_dollar,point_value_usd:t.point_value_usd,redemption_threshold:t.redemption_threshold,min_invoice_amount:t.min_invoice_amount,welcome_bonus:t.welcome_bonus,is_active:t.is_active,senior_bonus_enabled:t.senior_bonus_enabled,senior_bonus_code:((d=t.senior_bonus_code)==null?void 0:d.trim())||null,senior_points_multiplier:t.senior_points_multiplier,catalog_match_mode:t.catalog_match_mode,birthday_reward_enabled:t.birthday_reward_enabled,birthday_reward_catalog_id:t.birthday_reward_catalog_id,redemption_auth_code:((m=t.redemption_auth_code)==null?void 0:m.trim().toUpperCase())||null,tire_sales_eligible:t.tire_sales_eligible}).eq("id",t.id);S(!1),s?pe({title:"Could not save",description:s.message,variant:"destructive"}):pe({title:"Settings saved"})};return t?e.jsxs("div",{className:"space-y-5",children:[e.jsxs(J,{children:[e.jsxs(oe,{children:[e.jsx(me,{children:"Rewards Settings"}),e.jsx(je,{children:"Control how points are earned"})]}),e.jsxs(K,{className:"space-y-5",children:[e.jsxs("div",{className:"flex items-center justify-between rounded-lg border p-4",children:[e.jsxs("div",{children:[e.jsx(h,{className:"text-base",children:"Program Active"}),e.jsx("p",{className:"text-sm text-muted-foreground",children:"When off, customers can't claim points."})]}),e.jsx(ue,{checked:t.is_active,onCheckedChange:s=>c({...t,is_active:s})})]}),e.jsxs("div",{className:"flex items-center justify-between rounded-lg border p-4",children:[e.jsxs("div",{children:[e.jsx(h,{className:"text-base",children:"Tire Sales Earn Points"}),e.jsx("p",{className:"text-sm text-muted-foreground",children:"When off, invoices that contain tire line items are rejected from the rewards program."})]}),e.jsx(ue,{checked:t.tire_sales_eligible,onCheckedChange:s=>c({...t,tire_sales_eligible:s})})]}),e.jsxs("div",{className:"grid sm:grid-cols-2 gap-4",children:[e.jsxs("div",{children:[e.jsx(h,{htmlFor:"ppd",children:"Points per Dollar"}),e.jsx(b,{id:"ppd",type:"number",step:"0.01",value:t.points_per_dollar,onChange:s=>c({...t,points_per_dollar:Number(s.target.value)}),className:"mt-1.5"}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:t.points_per_dollar>0?t.points_per_dollar>=1?`Customers see: "${t.points_per_dollar} points per $1"`:`Customers see: "1 point per $${(1/t.points_per_dollar).toFixed(0)} spent"`:"e.g. 0.05 = 1 point per $20 spent"})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"min",children:"Minimum Invoice ($)"}),e.jsx(b,{id:"min",type:"number",step:"0.01",value:t.min_invoice_amount,onChange:s=>c({...t,min_invoice_amount:Number(s.target.value)}),className:"mt-1.5"})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"bonus",children:"Welcome Bonus (points)"}),e.jsx(b,{id:"bonus",type:"number",value:t.welcome_bonus,onChange:s=>c({...t,welcome_bonus:Number(s.target.value)}),className:"mt-1.5"}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:"First-time signups get this bonus."})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"pvalue",children:"Point Value ($)"}),e.jsx(b,{id:"pvalue",type:"number",step:"0.01",min:"0",value:t.point_value_usd,onChange:s=>c({...t,point_value_usd:Number(s.target.value)}),className:"mt-1.5"}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:t.point_value_usd>0?`Each point is worth $${Number(t.point_value_usd).toFixed(2)} when redeemed (${t.redemption_threshold||100} pts = $${((t.redemption_threshold||100)*t.point_value_usd).toFixed(2)}).`:"e.g. 0.20 = each point is worth 20¢"})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"threshold",children:"Redemption Threshold (points)"}),e.jsx(b,{id:"threshold",type:"number",step:"1",min:"1",value:t.redemption_threshold,onChange:s=>c({...t,redemption_threshold:Number(s.target.value)}),className:"mt-1.5"}),e.jsxs("p",{className:"text-xs text-muted-foreground mt-1",children:["Minimum points needed before a customer can redeem.",t.point_value_usd>0&&t.redemption_threshold>0&&e.jsxs(e.Fragment,{children:[" ",e.jsxs("span",{className:"font-medium text-foreground",children:[t.redemption_threshold.toLocaleStr
6ing()," pts = $",(t.redemption_threshold*t.point_value_usd).toFixed(2)]})]})]})]})]}),t.points_per_dollar>0&&t.point_value_usd>0&&e.jsxs("div",{className:"rounded-xl border border-primary/30 bg-primary/5 p-4",children:[e.jsxs("div",{className:"flex items-center justify-between mb-3 flex-wrap gap-2",children:[e.jsx("h4",{className:"text-sm font-semibold text-foreground",children:"Live Point Value Preview"}),e.jsxs("span",{className:"text-xs text-muted-foreground",children:[(t.points_per_dollar*t.point_value_usd*100).toFixed(1),"% effective return"]})]}),e.jsx("div",{className:"grid grid-cols-2 sm:grid-cols-4 gap-3",children:[50,100,250,500].map(s=>{const d=Math.floor(s*t.points_per_dollar),m=d*t.point_value_usd;return e.jsxs("div",{className:"rounded-lg bg-background border p-3 text-center",children:[e.jsx("div",{className:"text-xs text-muted-foreground",children:"Spend"}),e.jsxs("div",{className:"text-base font-bold text-foreground",children:["$",s]}),e.jsxs("div",{className:"text-xs text-primary mt-1",children:[d," pts"]}),e.jsxs("div",{className:"text-xs font-medium text-foreground mt-0.5",children:["= $",m.toFixed(2)]})]},s)})}),e.jsxs("p",{className:"text-xs text-muted-foreground mt-3",children:["Customers need ",e.jsxs("span",{className:"font-semibold text-foreground",children:[t.redemption_threshold," pts"]})," ","(= $",(t.redemption_threshold*t.point_value_usd).toFixed(2)," credit) to redeem."]})]})]})]}),e.jsxs(J,{children:[e.jsx(oe,{children:e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx(Oe,{className:"h-5 w-5 text-primary"}),e.jsxs("div",{children:[e.jsx(me,{children:"Senior Bonus"}),e.jsx(je,{children:"Reward seniors 65+ with extra points (verified in person by staff)"})]})]})}),e.jsxs(K,{className:"space-y-5",children:[e.jsxs("div",{className:"flex items-center justify-between rounded-lg border p-4",children:[e.jsxs("div",{children:[e.jsx(h,{className:"text-base",children:"Senior Bonus Enabled"}),e.jsx("p",{className:"text-sm text-muted-foreground",children:"Show senior checkbox on the claim form."})]}),e.jsx(ue,{checked:t.senior_bonus_enabled,onCheckedChange:s=>c({...t,senior_bonus_enabled:s})})]}),e.jsxs("div",{className:"grid sm:grid-cols-2 gap-4",children:[e.jsxs("div",{children:[e.jsx(h,{htmlFor:"senior-code",children:"Senior Bonus Code"}),e.jsx(b,{id:"senior-code",value:t.senior_bonus_code??"",onChange:s=>c({...t,senior_bonus_code:s.target.value}),placeholder:"SENIOR2026",className:"mt-1.5 font-mono uppercase",autoComplete:"off"}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:"Staff shares this code with senior customers in person."})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"senior-mult",children:"Points Multiplier"}),e.jsx(b,{id:"senior-mult",type:"number",step:"0.05",min:"1",value:t.senior_points_multiplier,onChange:s=>c({...t,senior_points_multiplier:Number(s.target.value)}),className:"mt-1.5"}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:"e.g. 1.5 = 50% bonus on top of normal points."})]})]})]})]}),e.jsxs(J,{children:[e.jsx(oe,{children:e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx(Oe,{className:"h-5 w-5 text-pink-600"}),e.jsxs("div",{children:[e.jsx(me,{children:"Birthday Reward"}),e.jsx(je,{children:"Give members a free reward they can redeem during their birthday month."})]})]})}),e.jsxs(K,{className:"space-y-5",children:[e.jsxs("div",{className:"flex items-center justify-between rounded-lg border p-4",children:[e.jsxs("div",{children:[e.jsx(h,{className:"text-base",children:"Birthday Reward Enabled"}),e.jsx("p",{className:"text-sm text-muted-foreground",children:"When on, the daily job issues the selected reward each member's birthday month."})]}),e.jsx(ue,{checked:!!t.birthday_reward_enabled,onCheckedChange:s=>c({...t,birthday_reward_enabled:s})})]}),e.jsxs("div",{children:[e.jsx(h,{htmlFor:"bday-reward",children:"Reward to Issue"}),e.jsxs(Ne,{value:t.birthday_reward_catalog_id||"none",onValueChange:s=>c({...t,birthday_reward_catalog_id:s==="none"?null:s}),children:[e.jsx(ye,{id:"bday-reward",className:"mt-1.5 max-w-md",children:e.jsx(we,{placeholder:"Choose a gift card rewardâ¦"})}),e.jsxs(be,{children:[e.jsx(X,{value:"none",children:"â None selected â"}),i.map(s=>e.jsxs(X,{value:s.id,children:[s.reward_type==="birthday_only"?"ð ":"",s.title,s.gift_card_amount?` ($${Number(s.gift_card_amount).toFixed(2)} ${s.gift_card_currency||"CAD"})`:""]},s.id))]})]}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:"Only active gift-card catalog items appear here. Members redeem this for free (0 points) once per year, during their birthday month. Unredeemed rewards expire at month-end."})]})]})]}),e.jsxs(J,{children:[e.jsxs(oe,{children:[e.jsx(me,{children:"Catalog â Monthly Draw Matching"}),e.jsx(je,{children:'How to decide whether a catalog reward and a monthly-draw prize are the "same" item.'})]}),e.jsxs(K,{className:"space-y-3",children:[e.jsx(h,{htmlFor:"match-mode",children:"Match logic"}),e.jsxs(Ne,{value:t.catalog_match_mode||"campaign_amount",onValueChange:s=>c({...t,catalog_match_mode:s}),children:[e.jsx(ye,{id:"match-mode",className:"max-w-md",children:e.jsx(we,{})}),e.jsx(be,{children:ts.map(s=>e.jsx(X,{value:s.value,children:s.label},s.value))})]}),e.jsx("p",{className:"text-xs text-muted-foreground",children:(y=ts.find(s=>s.value===(t.catalog_match_mode||"campaign_amount")))==null?void 0:y.description})]})]}),e.jsxs(J,{children:[e.jsx(oe,{children:e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx(Oe,{className:"h-5 w-5 text-amber-600"}),e.jsxs("div",{children:[e.jsx(me,{children:"Redemption Authorization Code"}),e.jsx(je,{children:"Staff-only code required at the counter to authorize a customer reward redemption after verifying the customer's AR (accounts receivable) status is clear."})]})]})}),e.jsxs(K,{className:"space-y-3",children:[e.jsx(h,{htmlFor:"auth-code",children:"Authorization Code"}),e.jsx(b,{id:"auth-code",value:t.redemption_auth_code??"",onChange:s=>c({...t,redemption_auth_code:s.target.value.toUpperCase()}),placeholder:"e.g. RA-CLEAR-2026",className:"mt-1.5 font-mono uppercase max-w-md",autoComplete:"off"}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"Share this code only with front-counter staff. They will enter it when releasing a reward redemption after confirming the customer has no outstanding AR balance. Change it any time staff turnover or you suspect the code has leaked. Not case-sensitive."})]})]}),e.jsxs(v,{onClick:N,disabled:_,children:[_&&e.jsx(q,{className:"mr-2 h-4 w-4 animate-spin"}),"Save Settings"]})]}):null}const Ds=(t,c)=>{if(t==null)return"";try{return new Intl.NumberFormat("en-CA",{style:"currency",currency:c}).format(Number(t))}catch{return`$${Number(t).toFixed(2)} ${c}`}},$e=t=>t.split(` 7`).map(c=>c.trim()).filter(c=>c.length>0),Fe=t=>Array.isArray(t)?t.join(` 8`):"",Te=(t=0)=>({title:"",description:"",image_url:"",points_cost:100,display_order:t,is_active:!0,reward_type:"physical",birthday_fulfillment:"tremendous",gift_card_amount:null,gift_card_currency:"CAD",gift_card_charge_currency:"USD",tremendous_campaign_id:null,redemption_steps:[],terms:[],expiry_days:null,points_expiry_note:null}),Nt=()=>{const[t,c]=n.useState([]),[_,S]=n.useState(!1),[i,g]=n.useState(Te()),[N,y]=n.useState(null),[s,d]=n.useState(null),[m,l]=n.useState(!1),[w,A]=n.useState(!1),[P,B]=n.useState(!1),[M,Y]=n.useState(null);n.useEffect(()=>{Q()},[]);const Q=async()=>{const{data:r,error:u}=await j.from("reward_catalog").select("*").order("display_order",{ascending:!0}).order("created_at",{ascending:!0});if(u){p.error("Failed to load rewards");return}c(r||[])},ne=async(r,u)=>{if(!r.title.trim()&&r.reward_type!=="gift_card"){p.error("Add a title first so AI knows what to draw");return}Y(u);try{const{data:D,error:le}=await j.functions.invoke("generate-prize-image",{body:{title:r.title,prize_type:r.reward_type,amount:r.gift_card_amount,currency:r.gift_card_currency||"CAD"}});if(le)throw le;if(D!=null&&D.error)throw new Error(D.error);const G=D==null?void 0:D.url;if(!G)throw new Error("No image URL returned");u==="new"?g(de=>({...de,image_url:G})):s&&d({...s,image_url:G}),p.success("AI image generated")}catch(D){p.error(D.message||"Failed to generate image")}finally{Y(null)}},o=()=>{g(Te(t.length)),A(!1),S(!0)},R=()=>{S(!1),g(Te())},F=r=>{const u=r.reward_type==="birthday_only"&&r.birthday_fulfillment==="in_house";
8if(r.reward_type!=="physical"&&!u){const D=Number(r.gift_card_amount);if(!Number.isFinite(D)||D<=0)return p.error("Gift card amount must be greater than 0"),!1}return!0},L=r=>!Number.isFinite(Number(r.points_cost))||Number(r.points_cost)<=0?(p.error("Points cost must be greater than 0"),!1):!0,z=async()=>{if(!i.title.trim()){p.error("Reward title is required");return}if(!L(i)||!F(i))return;l(!0);const r=i.reward_type==="birthday_only"&&i.birthday_fulfillment==="in_house",u=i.reward_type!=="physical"&&!r,{error:D}=await j.from("reward_catalog").insert({...i,description:i.description||null,image_url:i.image_url||null,birthday_fulfillment:i.reward_type==="birthday_only"?i.birthday_fulfillment:"tremendous",gift_card_amount:i.reward_type!=="physical"?i.gift_card_amount:null,gift_card_currency:u&&i.gift_card_currency||"CAD",gift_card_charge_currency:u&&i.gift_card_charge_currency||"USD",tremendous_campaign_id:u&&i.tremendous_campaign_id||null});if(l(!1),D){p.error("Failed to add reward");return}p.success("Reward added"),S(!1),g(Te()),Q()},H=r=>{y(r.id),d({...r,gift_card_currency:r.gift_card_currency||"CAD",gift_card_charge_currency:r.gift_card_charge_currency||"USD"}),B(!1)},x=()=>{y(null),d(null)},re=async()=>{if(!s)return;if(!s.title.trim()){p.error("Reward title is required");return}if(!L(s)||!F(s))return;l(!0);const r=s.reward_type==="birthday_only"&&s.birthday_fulfillment==="in_house",u=s.reward_type!=="physical"&&!r,{error:D}=await j.from("reward_catalog").update({title:s.title,description:s.description||null,image_url:s.image_url||null,points_cost:s.points_cost,display_order:s.display_order,is_active:s.is_active,reward_type:s.reward_type,birthday_fulfillment:s.reward_type==="birthday_only"?s.birthday_fulfillment:"tremendous",gift_card_amount:s.reward_type!=="physical"?s.gift_card_amount:null,gift_card_currency:u&&s.gift_card_currency||"CAD",gift_card_charge_currency:u&&s.gift_card_charge_currency||"USD",tremendous_campaign_id:u&&s.tremendous_campaign_id||null,redemption_steps:s.redemption_steps||[],terms:s.terms||[],expiry_days:s.expiry_days,points_expiry_note:s.points_expiry_note||null}).eq("id",s.id);if(l(!1),D){p.error("Failed to update reward");return}p.success("Reward updated"),x(),Q()},E=async r=>{if(!confirm("Delete this reward?"))return;const{error:u}=await j.from("reward_catalog").delete().eq("id",r);if(u){p.error("Failed to delete reward");return}p.success("Reward deleted"),Q()},Z=async(r,u)=>{c(le=>le.map(G=>G.id===r.id?{...G,is_active:u}:G));const{error:D}=await j.from("reward_catalog").update({is_active:u}).eq("id",r.id);if(D){c(le=>le.map(G=>G.id===r.id?{...G,is_active:!u}:G)),p.error("Failed to update reward");return}p.success(u?"Reward activated":"Reward hidden")},_e=(r,u,D,le)=>{const G=r.reward_type==="birthday_only"&&r.birthday_fulfillment==="in_house",de=r.reward_type!=="physical"&&!G;return e.jsxs("div",{className:"space-y-3 border rounded-md p-3 bg-background",children:[e.jsxs("div",{className:"grid grid-cols-2 gap-3",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Reward Type"}),e.jsxs(Ne,{value:r.reward_type,onValueChange:U=>u({reward_type:U}),children:[e.jsx(ye,{children:e.jsx(we,{})}),e.jsxs(be,{children:[e.jsx(X,{value:"physical",children:"Physical / In-shop"}),e.jsx(X,{value:"gift_card",children:"Gift Card (Tremendous)"}),e.jsx(X,{value:"birthday_only",children:"ð Birthday Only"})]})]}),r.reward_type==="birthday_only"&&e.jsx("p",{className:"text-xs text-pink-600",children:"Hidden from the regular catalog. Only redeemable via the birthday reward flow."})]}),r.reward_type==="birthday_only"&&e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Fulfillment"}),e.jsxs(Ne,{value:r.birthday_fulfillment,onValueChange:U=>u({birthday_fulfillment:U}),children:[e.jsx(ye,{children:e.jsx(we,{})}),e.jsxs(be,{children:[e.jsx(X,{value:"tremendous",children:"Tremendous (emailed gift card)"}),e.jsx(X,{value:"in_house",children:"In-house (redeem at shop)"})]})]}),e.jsx("p",{className:"text-xs text-muted-foreground",children:r.birthday_fulfillment==="in_house"?"Customer shows the redemption at the shop â no email gift card.":"Sent automatically by email via Tremendous."})]}),de&&e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Amount"}),e.jsxs("div",{className:"relative",children:[e.jsx("span",{className:"absolute left-3 top-1/2 -translate-y-1/2 text-sm text-muted-foreground",children:"CA$"}),e.jsx(b,{type:"number",min:1,step:"1",className:"pl-12 pr-14",value:r.gift_card_amount??"",onChange:U=>u({gift_card_amount:U.target.value===""?null:Number(U.target.value)}),placeholder:"50"}),e.jsx("span",{className:"absolute right-3 top-1/2 -translate-y-1/2 text-xs font-semibold text-muted-foreground",children:(r.gift_card_currency||"CAD").toUpperCase()})]})]}),G&&e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Display Value (optional)"}),e.jsxs("div",{className:"relative",children:[e.jsx("span",{className:"absolute left-3 top-1/2 -translate-y-1/2 text-sm text-muted-foreground",children:"CA$"}),e.jsx(b,{type:"number",min:0,step:"1",className:"pl-12",value:r.gift_card_amount??"",onChange:U=>u({gift_card_amount:U.target.value===""?null:Number(U.target.value)}),placeholder:"e.g. 25"})]}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"Shown to the customer. Leave blank to hide."})]})]}),de&&e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Charge Currency (what we order from Tremendous)"}),e.jsxs(Ne,{value:(r.gift_card_charge_currency||"USD").toUpperCase(),onValueChange:U=>u({gift_card_charge_currency:U}),children:[e.jsx(ye,{children:e.jsx(we,{})}),e.jsxs(be,{children:[e.jsx(X,{value:"USD",children:"USD â auto-converted from CAD using shop rate (predictable cost)"}),e.jsx(X,{value:"CAD",children:"CAD â Tremendous handles FX (campaign must include CAD products)"})]})]}),e.jsxs("p",{className:"text-xs text-muted-foreground",children:["Customer always sees ",Ds(r.gift_card_amount,r.gift_card_currency||"CAD"),". This setting only controls how the order is placed."]})]}),de&&e.jsxs("div",{className:"space-y-2",children:[e.jsxs("button",{type:"button",onClick:()=>le(!D),className:"text-xs text-muted-foreground hover:text-foreground transition-colors",children:[D?"â Hide":"+ Advanced"," (override currency / Tremendous campaign)"]}),D&&e.jsxs("div",{className:"grid grid-cols-2 gap-3 pt-1",children:[e.jsxs("div",{className:"space-y-1",children:[e.jsx(h,{className:"text-xs",children:"Currency"}),e.jsx(b,{value:r.gift_card_currency||"CAD",onChange:U=>u({gift_card_currency:U.target.value.toUpperCase().slice(0,3)}),placeholder:"CAD",maxLength:3})]}),e.jsxs("div",{className:"space-y-1",children:[e.jsx(h,{className:"text-xs",children:"Tremendous Campaign ID"}),e.jsx(b,{value:r.tremendous_campaign_id||"",onChange:U=>u({tremendous_campaign_id:U.target.value||null}),placeholder:"(use default)"})]})]})]})]})};return e.jsxs(J,{children:[e.jsxs(oe,{className:"flex flex-row items-start justify-between gap-4",children:[e.jsxs("div",{children:[e.jsxs(me,{className:"flex items-center gap-2",children:[e.jsx(Oe,{className:"h-5 w-5 text-red-600"}),"Rewards Catalog"]}),e.jsx(je,{children:"Add and manage the rewards customers can redeem with their points"})]}),!_&&e.jsxs(v,{onClick:o,size:"sm",className:"gap-1",children:[e.jsx(mt,{className:"h-4 w-4"})," Add Reward"]})]}),e.jsxs(K,{className:"space-y-4",children:[_&&e.jsxs("div",{className:"border rounded-lg p-4 space-y-3 bg-muted/30",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Title *"}),e.jsx(b,{value:i.title,onChange:r=>g({...i,title:r.target.value}),placeholder:"e.g. Free Oil Change or CA$50 Visa Gift Card"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Description"}),e.jsx(fe,{value:i.description||"",onChange:r=>g({...i,description:r.target.value}),rows:3,placeholder:"Describe the reward"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Image URL (optional)"}),e.jsxs("div",{className:"flex gap-2",children:[e.jsx(b,{value:i.image_url||"",onChange:r=>g({...i,image_url:r.target.value}),placeholder:"https://... or generate with AI"}),e.jsxs(v,{type:"button",variant:"outline",size:"default",onClick:()=>ne(i,"new"),disabled:M!==null,className:"shrink-0 gap-1",children:[M==="new"?e.jsx(q,{className:"h-4 w-4 animate-spin"}):e.jsx(ss,{className:"h-4 w-4"}),"AI"]})]}),i.image_url&&e.jsx("img",{src:i.image_url,alt:"Reward preview",className:"mt-1 w-32 h-32 object-cover rounded-md border",onError:r=>r.target.style.display="none"})]}),_e(i,r=>g({...i,...r}),w,A),e.jsxs("div",{className:"grid grid-cols-3 gap-3",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Points Cost *"}),e.jsx(b,{type:"number",min:1,value:i.points_cost,onChange:r=>g({...i,points_cost:Number(r.target.value)||0})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Display Order"}),e.jsx(b,{type:"number",value:i.display_order,onChange:r=>g({...i,display_order:Number(r.target.value)||0})})]}),e.jsxs("div",{className:"flex items-end justify-between gap-2",children:[e.jsx(h,{htmlFor:"new-active",children:"Active"}),e.jsx(ue,{id:"new-active",checked:i.is_active,onCheckedChange:r=>g({...i,is_active:r})})]})]}),e.jsxs("div",{className:"border-t pt-3 space-y-3",children:[e.jsx("p",{className:"text-sm font-medium text-foreground",children:"Details modal content"}),e.jsxs("div",{className:"grid grid-cols-2 gap-3",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Reward expiry (days)"}),e.jsx(b,{type:"number",min:1,placeholder:"e.g. 90",value:i.expiry_days??"",onChange:r=>g({...i,expiry_days:r.target.value===""?null:Number(r.target.value)})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Points expiry note"}),e.jsx(b,{placeholder:"e.g. Valid 24 months from last invoice",value:i.points_expiry_note??"",onChange:r=>g({...i,points_expiry_note:r.target.value})})]})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Redemption steps (one per line)"}),e.jsx(fe,{rows:4,placeholder:`Verify your phone on My Rewards 9Confirm your points balance 10Choose this reward and submit`,value:Fe(i.redemption_steps),onChange:r=>g({...i,redemption_steps:$e(r.target.value)})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Terms & conditions (one per line)"}),e.jsx(fe,{rows:4,placeholder:`One redemption per transaction
11Not exchangeable for cash 12Issuer terms apply once redeemed`,value:Fe(i.terms),onChange:r=>g({...i,terms:$e(r.target.value)})})]})]}),e.jsxs("div",{className:"flex gap-2 justify-end",children:[e.jsxs(v,{variant:"outline",size:"sm",onClick:R,children:[e.jsx(ke,{className:"h-4 w-4 mr-1"})," Cancel"]}),e.jsxs(v,{size:"sm",onClick:z,disabled:m,children:[e.jsx(qe,{className:"h-4 w-4 mr-1"})," ",m?"Saving...":"Save Reward"]})]})]}),t.length===0&&!_?e.jsx("p",{className:"text-muted-foreground text-sm",children:"No rewards added yet."}):e.jsx("div",{className:"space-y-3",children:t.map(r=>N===r.id&&s?e.jsxs("div",{className:"border rounded-lg p-4 space-y-3 bg-muted/30",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Title *"}),e.jsx(b,{value:s.title,onChange:u=>d({...s,title:u.target.value})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Description"}),e.jsx(fe,{value:s.description||"",onChange:u=>d({...s,description:u.target.value}),rows:3})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Image URL"}),e.jsxs("div",{className:"flex gap-2",children:[e.jsx(b,{value:s.image_url||"",onChange:u=>d({...s,image_url:u.target.value})}),e.jsxs(v,{type:"button",variant:"outline",size:"default",onClick:()=>ne(s,"edit"),disabled:M!==null,className:"shrink-0 gap-1",children:[M==="edit"?e.jsx(q,{className:"h-4 w-4 animate-spin"}):e.jsx(ss,{className:"h-4 w-4"}),"AI"]})]}),s.image_url&&e.jsx("img",{src:s.image_url,alt:"Reward preview",className:"mt-1 w-32 h-32 object-cover rounded-md border",onError:u=>u.target.style.display="none"})]}),_e(s,u=>d({...s,...u}),P,B),e.jsxs("div",{className:"grid grid-cols-3 gap-3",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Points Cost *"}),e.jsx(b,{type:"number",min:1,value:s.points_cost,onChange:u=>d({...s,points_cost:Number(u.target.value)||0})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Display Order"}),e.jsx(b,{type:"number",value:s.display_order,onChange:u=>d({...s,display_order:Number(u.target.value)||0})})]}),e.jsxs("div",{className:"flex items-end justify-between gap-2",children:[e.jsx(h,{htmlFor:`edit-active-${r.id}`,children:"Active"}),e.jsx(ue,{id:`edit-active-${r.id}`,checked:s.is_active,onCheckedChange:u=>d({...s,is_active:u})})]})]}),e.jsxs("div",{className:"border-t pt-3 space-y-3",children:[e.jsx("p",{className:"text-sm font-medium text-foreground",children:"Details modal content"}),e.jsxs("div",{className:"grid grid-cols-2 gap-3",children:[e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Reward expiry (days)"}),e.jsx(b,{type:"number",min:1,placeholder:"e.g. 90",value:s.expiry_days??"",onChange:u=>d({...s,expiry_days:u.target.value===""?null:Number(u.target.value)})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Points expiry note"}),e.jsx(b,{placeholder:"e.g. Valid 24 months from last invoice",value:s.points_expiry_note??"",onChange:u=>d({...s,points_expiry_note:u.target.value})})]})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Redemption steps (one per line)"}),e.jsx(fe,{rows:4,value:Fe(s.redemption_steps),onChange:u=>d({...s,redemption_steps:$e(u.target.value)})})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsx(h,{children:"Terms & conditions (one per line)"}),e.jsx(fe,{rows:4,value:Fe(s.terms),onChange:u=>d({...s,terms:$e(u.target.value)})})]})]}),e.jsxs("div",{className:"flex gap-2 justify-end",children:[e.jsxs(v,{variant:"outline",size:"sm",onClick:x,children:[e.jsx(ke,{className:"h-4 w-4 mr-1"})," Cancel"]}),e.jsxs(v,{size:"sm",onClick:re,disabled:m,children:[e.jsx(qe,{className:"h-4 w-4 mr-1"})," ",m?"Saving...":"Save"]})]})]},r.id):e.jsxs("div",{className:"border rounded-lg p-4 flex items-start gap-4 hover:bg-muted/30 transition-colors",children:[r.image_url&&e.jsx("img",{src:r.image_url,alt:r.title,className:"w-20 h-20 object-cover rounded-md border shrink-0",onError:u=>u.target.style.display="none"}),e.jsxs("div",{className:"flex-1 min-w-0",children:[e.jsxs("div",{className:"flex items-center gap-2 flex-wrap",children:[e.jsx("h4",{className:"font-semibold",children:r.title}),e.jsxs(V,{className:"bg-primary hover:bg-primary gap-1",children:[e.jsx(as,{className:"h-3 w-3"}
12),r.points_cost.toLocaleString()," pts"]}),r.reward_type!=="physical"&&e.jsxs(V,{className:"bg-emerald-600 hover:bg-emerald-600 gap-1",children:[e.jsx(at,{className:"h-3 w-3"}),Ds(r.gift_card_amount,r.gift_card_currency||"CAD")]}),r.reward_type==="birthday_only"&&e.jsx(V,{className:"bg-pink-600 hover:bg-pink-600 gap-1",children:"ð Birthday Only"}),!r.is_active&&e.jsx("span",{className:"text-xs px-2 py-0.5 rounded bg-muted text-muted-foreground",children:"Hidden"}),e.jsxs("span",{className:"text-xs text-muted-foreground",children:["#",r.display_order]})]}),r.description&&e.jsx("p",{className:"text-sm text-muted-foreground mt-1 whitespace-pre-wrap",children:r.description})]}),e.jsxs("div",{className:"flex items-center gap-2 shrink-0",children:[e.jsxs("div",{className:"flex flex-col items-center gap-0.5 px-2 border-r pr-3 mr-1",children:[e.jsx(ue,{checked:r.is_active,onCheckedChange:u=>Z(r,u),"aria-label":r.is_active?"Hide reward":"Show reward"}),e.jsx("span",{className:"text-[10px] text-muted-foreground",children:r.is_active?"Active":"Hidden"})]}),e.jsx(v,{variant:"ghost",size:"icon",onClick:()=>H(r),children:e.jsx(He,{className:"h-4 w-4"})}),e.jsx(v,{variant:"ghost",size:"icon",onClick:()=>E(r.id),children:e.jsx(ut,{className:"h-4 w-4 text-destructive"})})]})]},r.id))}),e.jsxs("p",{className:"text-xs text-muted-foreground",children:["Public link:"," ",e.jsx("a",{href:"/rewards",target:"_blank",rel:"noopener noreferrer",className:"text-primary underline",children:"/rewards"})]})]})]})};function yt(){const[t,c]=n.useState([]),[_,S]=n.useState(""),[i,g]=n.useState(""),N=async()=>{const{data:d}=await j.from("ineligible_invoices").select("*").order("created_at",{ascending:!1});c(d||[])};n.useEffect(()=>{N()},[]);const y=async()=>{if(!_.trim())return;const{error:d}=await j.from("ineligible_invoices").insert({invoice_number:_.trim(),reason:i.trim()||null});if(d){pe({title:"Could not add",description:d.message,variant:"destructive"});return}S(""),g(""),N()},s=async d=>{await j.from("ineligible_invoices").delete().eq("id",d),N()};return e.jsxs(J,{children:[e.jsxs(oe,{children:[e.jsx(me,{children:"Ineligible Invoices"}),e.jsx(je,{children:"Block specific invoice numbers from earning rewards."})]}),e.jsxs(K,{className:"space-y-4",children:[e.jsxs("div",{className:"flex flex-col sm:flex-row gap-2",children:[e.jsx(b,{placeholder:"Invoice number",value:_,onChange:d=>S(d.target.value)}),e.jsx(b,{placeholder:"Reason (optional)",value:i,onChange:d=>g(d.target.value)}),e.jsx(v,{onClick:y,children:"Add"})]}),e.jsx("div",{className:"space-y-2",children:t.length===0?e.jsx("p",{className:"text-sm text-muted-foreground",children:"No blocked invoices."}):t.map(d=>e.jsxs("div",{className:"flex items-center justify-between rounded-md border p-2.5",children:[e.jsxs("div",{children:[e.jsx("p",{className:"font-medium",children:d.invoice_number}),d.reason&&e.jsx("p",{className:"text-xs text-muted-foreground",children:d.reason})]}),e.jsx(v,{variant:"ghost",size:"icon",onClick:()=>s(d.id),children:e.jsx(ke,{className:"h-4 w-4"})})]},d.id))})]})]})}const wt=t=>{switch(t){case"sent":return"default";case"pending":return"secondary";case"failed":return"destructive";default:return"outline"}};function bt(){const[t,c]=n.useState([]),[_,S]=n.useState(!0),[i,g]=n.useState(!1),N=async()=>{const{data:s}=await j.from("reward_redemptions").select("*, customers(full_name, phone)").order("created_at",{ascending:!1}).limit(100);c(s||[]),S(!1)};n.useEffect(()=>{N()},[]);const y=async()=>{g(!0);try{const{data:s,error:d}=await j.functions.invoke("sync-tremendous-redemptions",{body:{}});if(d)throw d;p.success(`Synced ${(s==null?void 0:s.updated)??0} redemption${(s==null?void 0:s.updated)===1?"":"s"}`),await N()}catch(s){p.error((s==null?void 0:s.message)||"Sync failed")}finally{g(!1)}};return _?e.jsx(J,{children:e.jsxs(K,{className:"p-6 flex items-center justify-center text-muted-foreground",children:[e.jsx(q,{className:"h-4 w-4 animate-spin mr-2"})," Loading redemptionsâ¦"]})}):e.jsxs("div",{className:"space-y-3",children:[e.jsx("div",{className:"flex justify-end",children:e.jsxs(v,{variant:"outline",size:"sm",onClick:y,disabled:i,children:[i?e.jsx(q,{className:"h-4 w-4 animate-spin mr-2"}):e.jsx(rs,{className:"h-4 w-4 mr-2"}
12),"Refresh gift card brands"]})}),t.length===0?e.jsx(J,{children:e.jsx(K,{className:"p-8 text-center text-muted-foreground",children:"No redemptions yet."})}):e.jsx(J,{children:e.jsx(K,{className:"p-0 overflow-x-auto",children:e.jsxs("table",{className:"w-full text-sm",children:[e.jsx("thead",{className:"bg-muted/50 text-left",children:e.jsxs("tr",{children:[e.jsx("th",{className:"p-3 font-medium",children:"Date"}),e.jsx("th",{className:"p-3 font-medium",children:"Customer"}),e.jsx("th",{className:"p-3 font-medium",children:"Email"}),e.jsx("th",{className:"p-3 font-medium",children:"Reward"}),e.jsx("th",{className:"p-3 font-medium",children:"Brand chosen"}),e.jsx("th",{className:"p-3 font-medium",children:"Points"}),e.jsx("th",{className:"p-3 font-medium",children:"Amount"}),e.jsx("th",{className:"p-3 font-medium",children:"Status"}),e.jsx("th",{className:"p-3 font-medium",children:"Order"})]})}),e.jsx("tbody",{children:t.map(s=>{var m,l,w;const d=((m=s.catalog_snapshot)==null?void 0:m.title)||"â";return e.jsxs("tr",{className:"border-t",children:[e.jsx("td",{className:"p-3 whitespace-nowrap",children:new Date(s.created_at).toLocaleDateString()}),e.jsxs("td",{className:"p-3",children:[e.jsx("div",{className:"font-medium",children:((l=s.customers)==null?void 0:l.full_name)||"â"}),e.jsx("div",{className:"text-xs text-muted-foreground",children:((w=s.customers)==null?void 0:w.phone)||""})]}),e.jsx("td",{className:"p-3",children:s.recipient_email}),e.jsx("td",{className:"p-3",children:d}),e.jsx("td",{className:"p-3",children:e.jsx(Ct,{id:s.id,value:s.redeemed_brand,onSaved:A=>c(P=>P.map(B=>B.id===s.id?{...B,redeemed_brand:A}:B))})}),e.jsx("td",{className:"p-3",children:s.points_redeemed}),e.jsxs("td",{className:"p-3 font-medium",children:["$",Number(s.dollar_amount).toFixed(2)]}),e.jsxs("td",{className:"p-3",children:[e.jsx(V,{variant:wt(s.status),className:"capitalize",children:s.status}),s.error_message&&e.jsx("div",{className:"text-xs text-destructive mt-1 max-w-[220px] truncate",title:s.error_message,children:s.error_message})]}),e.jsx("td",{className:"p-3",children:s.delivery_url?e.jsx(v,{asChild:!0,variant:"ghost",size:"sm",children:e.jsxs("a",{href:s.delivery_url,target:"_blank",rel:"noopener noreferrer",children:["View ",e.jsx(Us,{className:"ml-1 h-3 w-3"})]})}):e.jsx("span",{className:"text-xs text-muted-foreground",children:"â"})})]},s.id)})})]})})})]})}function Ct({id:t,value:c,onSaved:_}){const[S,i]=n.useState(!1),[g,N]=n.useState(c||""),[y,s]=n.useState(!1),d=async()=>{const m=g.trim();if(!m)return;s(!0);const{error:l}=await j.from("reward_redemptions").update({redeemed_brand:m}).eq("id",t);if(s(!1),l){p.error(l.message);return}_(m),i(!1),p.success("Brand saved")};return S?e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsx(b,{autoFocus:!0,value:g,onChange:m=>N(m.target.value),onKeyDown:m=>{m.key==="Enter"&&d(),m.key==="Escape"&&i(!1)},placeholder:"e.g. Boston Pizza",className:"h-7 text-sm w-40"}),e.jsx(v,{size:"icon",variant:"ghost",className:"h-7 w-7",onClick:d,disabled:y,children:e.jsx(qe,{className:"h-3.5 w-3.5"})}),e.jsx(v,{size:"icon",variant:"ghost",className:"h-7 w-7",onClick:()=>{i(!1),N(c||"")},children:e.jsx(ke,{className:"h-3.5 w-3.5"})})]}):e.jsxs("button",{type:"button",onClick:()=>i(!0),className:"group inline-flex items-center gap-1.5 text-left hover:text-foreground",children:[c?e.jsx("span",{className:"font-medium",children:c}):e.jsx("span",{className:"text-xs text-muted-foreground",children:"Set brandâ¦"}),e.jsx(He,{className:"h-3 w-3 opacity-0 group-hover:opacity-60"})]})}const St={succeeded:"default",refunded:"destructive",failed:"destructive"},kt={ok:"default",error:"destructive",not_configured:"destructive"},At={sent:"default",skipped:"secondary",failed:"destructive"};function Rt(){const[t,c]=n.useState([]),[_,S]=n.useState(!0),[i,g]=n.useState(""),N=async()=>{S(!0);const{data:s,error:d}=await j.from("reward_redemption_audit").select("*").order("created_at",{ascending:!1}).limit(200);d||c(s||[]),S(!1)};n.useEffect(()=>{N()},[]);const y=t.filter(s=>{var m,l,w,A,P,B,M;if(!i.trim())return!0;const d=i.toLowerCase();return((m=s.recipient_email)==null?void 0:m.toLowerCase().includes(d))||((w=(l=s.customer_snapshot)==null?void 0:l.full_name)==null?void 0:w.toLowerCase().includes(d))||((P=(A=s.catalog_snapshot)==null?void 0:A.title)==null?void 0:P.toLowerCase().includes(d))||((B=s.tremendous_order_id)==null?void 0:B.toLowerCase().includes(d))||((M=s.outcome)==null?void 0:M.toLowerCase().includes(d))});return e.jsx(J,{children:e.jsxs(K,{className:"p-4 space-y-4",children:[e.jsxs("div",{className:"flex items-center justify-between gap-3 flex-wrap",children:[e.jsxs("div",{children:[e.jsx("h3",{className:"font-semibold",children:"Redemption Audit Log"}),e.jsx("p",{className:"text-xs text-muted-foreground",children:"Every reward redemption attempt â successful and failed â with full traceability."})]}),e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsxs("div",{className:"relative",children:[e.jsx(ht,{className:"h-4 w-4 absolute left-2.5 top-1/2 -translate-y-1/2 text-muted-foreground"}),e.jsx(b,{placeholder:"Search email, name, itemâ¦",value:i,onChange:s=>g(s.target.value),className:"pl-8 w-64"})]}),e.jsx(v,{variant:"outline",size:"icon",onClick:N,disabled:_,children:_?e.jsx(q,{className:"h-4 w-4 animate-spin"}):e.jsx(rs,{className:"h-4 w-4"})})]})]}),_?e.jsxs("div",{className:"flex items-center justify-center py-12 text-muted-foreground",children:[e.jsx(q,{className:"h-5 w-5 animate-spin mr-2"})," Loading audit logâ¦"]}):y.length===0?e.jsx("div",{className:"text-center py-12 text-muted-foreground text-sm",children:t.length===0?"N
12o redemption attempts logged yet.":"No entries match your search."}):e.jsx("div",{className:"overflow-x-auto",children:e.jsxs("table",{className:"w-full text-sm",children:[e.jsx("thead",{className:"text-left text-xs text-muted-foreground border-b",children:e.jsxs("tr",{children:[e.jsx("th",{className:"py-2 pr-4 font-medium",children:"When"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Customer"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Reward"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Points"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Outcome"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Tremendous"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Receipt"}),e.jsx("th",{className:"py-2 pr-4 font-medium",children:"Order"})]})}),e.jsx("tbody",{children:y.map(s=>{var d,m;return e.jsxs("tr",{className:"border-b last:border-0 align-top",children:[e.jsx("td",{className:"py-3 pr-4 whitespace-nowrap text-xs text-muted-foreground",children:zs(new Date(s.created_at),"MMM d, HH:mm")}),e.jsxs("td",{className:"py-3 pr-4",children:[e.jsx("div",{className:"font-medium",children:((d=s.customer_snapshot)==null?void 0:d.full_name)||"â"}),e.jsx("div",{className:"text-xs text-muted-foreground",children:s.recipient_email})]}),e.jsxs("td",{className:"py-3 pr-4",children:[e.jsx("div",{className:"font-medium",children:((m=s.catalog_snapshot)==null?void 0:m.title)||"â"}),e.jsxs("div",{className:"text-xs text-muted-foreground",children:[s.gift_card_currency," $",Number(s.dollar_amount).toFixed(2)]})]}),e.jsxs("td",{className:"py-3 pr-4 whitespace-nowrap",children:[e.jsx("div",{className:"font-semibold",children:s.points_charged.toLocaleString()}),e.jsxs("div",{className:"text-xs text-muted-foreground",children:["@ $",Number(s.point_value_usd).toFixed(2),"/pt"]})]}),e.jsxs("td",{className:"py-3 pr-4",children:[e.jsx(V,{variant:St[s.outcome]||"outline",children:s.outcome}),s.error_message&&e.jsx("div",{className:"text-xs text-destructive mt-1 max-w-[200px] truncate",title:s.error_message,children:s.error_message})]}),e.jsx("td",{className:"py-3 pr-4",children:s.tremendous_status?e.jsx(V,{variant:kt[s.tremendous_status]||"outline",children:s.tremendous_status}):e.jsx("span",{className:"text-xs text-muted-foreground",children:"â"})}),e.jsx("td",{className:"py-3 pr-4",children:s.email_status?e.jsx(V,{variant:At[s.email_status]||"outline",children:s.email_status}):e.jsx("span",{className:"text-xs text-muted-foreground",children:"â"})}),e.jsxs("td",{className:"py-3 pr-4",children:[s.tremendous_order_id?e.jsxs("div",{className:"text-xs font-mono",children:[s.tremendous_order_id.slice(0,10),"â¦"]}):e.jsx("span",{className:"text-xs text-muted-foreground",children:"â"}),s.delivery_url&&e.jsxs("a",{href:s.delivery_url,target:"_blank",rel:"noopener noreferrer",className:"text-xs text-primary hover:underline inline-flex items-center gap-1 mt-1",children:["Open ",e.jsx(Us,{className:"h-3 w-3"})]})]})]},s.id)})})]})})]})})}function Dt(){const[t,c]=n.useState("pending"),[_,S]=n.useState([]),[i,g]=n.useState(!1),[N,y]=n.useState(null),s=async()=>{g(!0);const{data:l,error:w}=await j.functions.invoke("referrals-admin",{body:{action:"list",status:t}});if(g(!1),w){pe({title:"Failed to load",description:w.message,variant:"destructive"});return}S((l==null?void 0:l.rows)||[])};n.useEffect(()=>{s()},[t]);const d=async l=>{y(l);const{error:w}=await j.functions.invoke("referrals-admin",{body:{action:"approve",referral_id:l}});if(y(null),w){pe({title:"Could not approve",description:w.message,variant:"destructive"});return}pe({title:"Referral approved â points awarded to both customers."}),s()},m=async l=>{const w=window.prompt("Reason for rejection (optional):")||null;y(l);const{error:A}=await j.functions.invoke("referrals-admin",{body:{action:"reject",referral_id:l,reason:w}});if(y(null),A){pe({title:"Could not reject",description:A.message,variant:"destructive"});return}pe({title:"Referral rejected"}),s()};return e.jsx(J,{children:e.jsxs(K,{className:"p-4 md:p-6 space-y-4",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx($s,{className:"h-5 w-5 text-primary"}),e.jsx("h2",{className:"text-lg font-semibold",children:"Referrals"})]}),e.jsxs(Fs,{value:t,onValueChange:l=>c(l),children:[e.jsxs(Ts,{children:[e.jsx(ie,{value:"pending",children:"Pending"}),e.jsx(ie,{value:"approved",children:"Approved"}),e.jsx(ie,{value:"rejected",children:"Rejected"})]}),e.jsx(ce,{value:t,className:"mt-4",children:i?e.jsxs("div",{className:"py-10 flex items-center justify-center text-muted-foreground",children:[e.jsx(q,{className:"h-4 w-4 animate-spin mr-2"})," Loadingâ¦"]}):_.length===0?e.jsx("p",{className:"py-8 text-center text-sm text-muted-foreground",children:"No referrals in this state."}):e.jsx("div",{className:"space-y-3",children:_.map(l=>{var w,A,P;return e.jsxs("div",{className:"border rounded-lg p-4 grid grid-cols-1 md:grid-cols-12 gap-3 items-start",children:[e.jsxs("div",{className:"md:col-span-4",children:[e.jsx("p",{className:"text-xs text-muted-foreground",children:"Referrer"}),e.jsx("p",{className:"font-semibold",children:((w=l.referrer)==null?void 0:w.full_name)||"â"}),e.jsx("p",{className:"text-xs text-muted-foreground",children:(A=l.referrer)==null?void 0:A.phone}),e.jsx(V,{variant:"outline",className:"mt-1 font-mono text-[10px]",children:l.referrer_code})]}),e.jsxs("div",{className:"md:col-span-4",children:[e.jsx("p",{className:"text-xs text-muted-foreground",children:"New Customer"}),e.jsx("p",{className:"font-semibold",children:l.referred_name||((P=l.referred)==null?void 0:P.full_name)||"â"}),e.jsx("p",{className:"text-xs text-muted-foreground",children:l.referred_phone}),l.invoice_number&&e.jsxs("p",{className:"text-xs mt-1",children:["Invoice: ",e.jsx("span",{className:"font-mono",children:l.invoice_number})]})]}),e.jsx("div",{className:"md:col-span-4 flex flex-col gap-2 items-stretch md:items-end",children:l.status==="pending"?e.jsxs(e.Fragment,{children:[e.jsxs(v,{size:"sm",onClick:()=>d(l.id),disabled:N===l.id,className:"bg-emerald-600 hover:bg-emerald-700",children:[N===l.id?e.jsx(q,{className:"h-3 w-3 mr-1 animate-spin"}):e.jsx(qe,{className:"h-3 w-3 mr-1"}),"Approve & Award Points"]}),e.jsxs(v,{size:"sm",variant:"outline",onClick:()=>m(l.id),disabled:N===l.id,children:[e.jsx(ke,{className:"h-3 w-3 mr-1"})," Reject"]})]}):l.status==="approved"?e.jsxs("div",{className:"text-right text-xs",children:[e.jsx(V,{className:"bg-emerald-600",children:"Approved"}),e.jsxs("p",{className:"text-muted-foreground mt-1",children:["+",l.referrer_points_awarded," pts to referrer"]}),e.jsxs("p",{className:"text-muted-foreground",children:["+",l.referred_bonus_points_awarded," pts to new customer"]})]}):e.jsxs("div",{className:"text-right text-xs",children:[e.jsx(V,{variant:"destructive",children:"Rejected"}),l.rejected_reason&&e.jsx("p",{className:"text-muted-foreground mt-1",children:l.rejected_reason})]})})]},l.id)})})})]})]})})}const Pt=()=>{const[t,c]=n.useState(!1),[_,S]=n.useState(!1),[i,g]=n.useState(null),[N,y]=n.useState([]),[s,d]=n.useState(null),[m,l]=n.useState(null),[w,A]=n.useState(null),P=async()=>{const[{data:o,error:R},{data:F,error:L},z]=await Promise.all([j.from("monthly_draw_prizes").select("id,title,gift_card_amount,gift_card_currency,tremendous_campaign_id,is_active,prize_type"),j.from("reward_catalog").select("id,title,gift_card_amount,gift_card_currency,tremendous_campaign_id,is_active,reward_type"),ot()]);if(R)throw R;if(L)throw L;return{giftDraws:(o||[]).filter(H=>(H.prize_type??"gift_card")==="gift_card"&&H.is_active),giftCatalog:(F||[]).filter(H=>(H.reward_type??"gift_card")==="gift_card"&&H.is_active),mode:z}},B=async()=>{S(!0),d(null);try{const{giftDraws:o,giftCatalog:R,mode:F}=await P();l(F);const L=[];for(const z of o){if(!z.tremendous_campaign_id)continue;const H=R.filter(x=>ks({tremendous_campaign_id:x.tremendous_campaign_id,gift_card_amount:x.gift_card_amount},{tremendous_campaign_id:z.tremendous_campaign_id,gift_card_amount:z.gift_card_amount},F));L.push({draw:{id:z.id,title:z.title,amount:z.gift_card_amount,campaignId:z.tremendous_campaign_id},catalog:H.map(x=>({id:x.id,title:x.title,amount:x.gift_card_amount,is_active:x.is_active}))})}d(L)}catch(o){g([{severity:"error",scope:"cross",label:"Preview failed",detail
12:o.message||String(o)}])}finally{S(!1)}},M=async()=>{c(!0),g(null);try{const{giftDraws:o,giftCatalog:R,mode:F}=await P();l(F);const L=[],z=[];for(const x of o)z.push({source:"draw",id:x.id,title:x.title,amount:x.gift_card_amount,currency:x.gift_card_currency,campaignId:x.tremendous_campaign_id,active:x.is_active}),x.tremendous_campaign_id||L.push({severity:"error",scope:"draw",id:x.id,label:x.title,detail:"Active monthly-draw prize is missing a Tremendous campaign ID."}),(!x.gift_card_amount||!x.gift_card_currency)&&L.push({severity:"warning",scope:"draw",id:x.id,label:x.title,detail:"Missing gift card amount or currency."});for(const x of R)z.push({source:"catalog",id:x.id,title:x.title,amount:x.gift_card_amount,currency:x.gift_card_currency,campaignId:x.tremendous_campaign_id,active:x.is_active}),x.tremendous_campaign_id||L.push({severity:"error",scope:"catalog",id:x.id,label:x.title,detail:"Active catalog reward is missing a Tremendous campaign ID."});for(const x of o){if(!x.tremendous_campaign_id)continue;const re=R.filter(E=>ks({tremendous_campaign_id:E.tremendous_campaign_id,gift_card_amount:E.gift_card_amount},{tremendous_campaign_id:x.tremendous_campaign_id,gift_card_amount:x.gift_card_amount},F));if(re.length===0){L.push({severity:"error",scope:"cross",id:x.id,label:x.title,detail:F==="campaign_amount"?`Draw prize uses campaign ${x.tremendous_campaign_id} @ $${x.gift_card_amount} but no catalog reward matches campaign + amount.`:`Draw prize uses campaign ${x.tremendous_campaign_id} but no catalog reward maps to it.`});continue}for(const E of re)(E.gift_card_currency||"").toUpperCase()!==(x.gift_card_currency||"").toUpperCase()&&L.push({severity:"error",scope:"cross",id:E.id,label:E.title,detail:`Catalog currency (${E.gift_card_currency}) â draw currency (${x.gift_card_currency}) for campaign ${x.tremendous_campaign_id}.`}),F==="campaign_only"&&Number(E.gift_card_amount)!==Number(x.gift_card_amount)&&L.push({severity:"warning",scope:"cross",id:E.id,label:E.title,detail:`Loose match: catalog amount ${E.gift_card_amount} â draw amount ${x.gift_card_amount} (campaign ${x.tremendous_campaign_id}).`})}const H=new Map;for(const x of R){if(!x.tremendous_campaign_id)continue;const re=H.get(x.tremendous_campaign_id)||[];re.push(x),H.set(x.tremendous_campaign_id,re)}for(const[x,re]of H){const E=new Set(re.map(Z=>Number(Z.gift_card_amount)));E.size>1&&F==="campaign_only"&&L.push({severity:"warning",scope:"catalog",label:x,detail:`Multiple catalog rows share campaign ${x} with different amounts: ${[...E].join(", ")}. Loose mode will treat them all as the same item.`})}y(z),g(L),A(new Date)}catch(o){g([{severity:"error",scope:"cross",label:"Check failed",detail:o.message||String(o)}])}finally{c(!1)}},Y=(i==null?void 0:i.filter(o=>o.severity==="error"))||[],Q=(i==null?void 0:i.filter(o=>o.severity==="warning"))||[],ne=m?ts.find(o=>o.value===m):null;return e.jsxs(J,{children:[e.jsxs(oe,{className:"flex flex-row items-center justify-between gap-4 flex-wrap",children:[e.jsxs("div",{children:[e.jsxs(me,{className:"flex items-center gap-2",children:[e.jsx(Cs,{className:"h-5 w-5"}),"Campaign Mapping Verification"]}),e.jsx("p",{className:"text-sm text-muted-foreground mt-1",children:"Cross-checks that monthly-draw prizes and reward catalog rows reference the same Tremendous campaigns. Match logic is configured in Settings."})]}),e.jsxs("div",{className:"flex gap-2",children:[e.jsxs(v,{variant:"outline",onClick:B,disabled:_||t,children:[_?e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"}):e.jsx(Ve,{className:"h-4 w-4 mr-2"}),"Preview Matches"]}),e.jsxs(v,{onClick:M,disabled:t||_,children:[t?e.jsx(q,{className:"h-4 w-4 mr-2 animate-spin"}):e.jsx(Cs,{className:"h-4 w-4 mr-2"}),"Run Check"]})]})]}),e.jsxs(K,{className:"space-y-4",children:[ne&&e.jsxs("div",{className:"rounded-md border p-3 bg-muted/40 text-sm",children:[e.jsxs("div",{className:"flex items-center gap-2 flex-wrap",children:[e.jsx("span",{className:"font-medium",children:"Active match logic:"}),e.jsx(V,{children:ne.label})]}),e.jsx("p",{className:"text-xs text-muted-foreground mt-1",children:ne.description})]}),w&&e.jsxs("p",{className:"text-xs text-muted-foreground",children:["Last run: ",w.toLocaleStr
12ing()]}),s&&e.jsxs("div",{className:"space-y-2",children:[e.jsx("h3",{className:"text-sm font-semibold",children:"Preview â what would be linked right now"}),s.length===0?e.jsx("p",{className:"text-sm text-muted-foreground",children:"No active gift-card draw prizes with a campaign ID."}):e.jsx("div",{className:"border rounded-md overflow-x-auto",children:e.jsxs("table",{className:"w-full text-sm",children:[e.jsx("thead",{className:"bg-muted",children:e.jsxs("tr",{children:[e.jsx("th",{className:"text-left p-2",children:"Draw Prize"}),e.jsx("th",{className:"text-left p-2",children:"Campaign"}),e.jsx("th",{className:"text-left p-2",children:"Matched Catalog Rows"})]})}),e.jsx("tbody",{children:s.map(o=>e.jsxs("tr",{className:"border-t align-top",children:[e.jsxs("td",{className:"p-2",children:[e.jsx("div",{className:"font-medium",children:o.draw.title}),e.jsxs("div",{className:"text-xs text-muted-foreground",children:["$",o.draw.amount??"â"]})]}),e.jsx("td",{className:"p-2 font-mono text-xs",children:o.draw.campaignId}),e.jsx("td",{className:"p-2",children:o.catalog.length===0?e.jsx("span",{className:"text-destructive text-xs",children:"No matches"}):e.jsx("ul",{className:"space-y-1",children:o.catalog.map(R=>e.jsxs("li",{className:"flex items-center gap-2",children:[e.jsx(V,{variant:R.is_active?"default":"secondary",children:R.is_active?"active":"hidden"}),e.jsx("span",{children:R.title}),e.jsxs("span",{className:"text-xs text-muted-foreground",children:["$",R.amount??"â"]})]},R.id))})})]},o.draw.id))})]})})]}),i&&i.length===0&&e.jsxs(Ke,{children:[e.jsx(xt,{className:"h-4 w-4"}),e.jsx(Qe,{children:"All mappings look good"}),e.jsx(Xe,{children:"Every active monthly-draw prize has a matching catalog reward under the active match logic."})]}),Y.length>0&&e.jsxs(Ke,{variant:"destructive",children:[e.jsx(As,{className:"h-4 w-4"}),e.jsxs(Qe,{children:[Y.length," error",Y.length===1?"":"s"]}),e.jsx(Xe,{children:e.jsx("ul",{className:"list-disc pl-5 mt-2 space-y-1 text-sm",children:Y.map((o,R)=>e.jsxs("li",{children:[e.jsx(V,{variant:"outline",className:"mr-2",children:o.scope}),e.jsxs("span",{className:"font-medium",children:[o.label,":"]})," ",o.detail]},R))})})]}),Q.length>0&&e.jsxs(Ke,{children:[e.jsx(As,{className:"h-4 w-4"}),e.jsxs(Qe,{children:[Q.length," warning",Q.length===1?"":"s"]}),e.jsx(Xe,{children:e.jsx("ul",{className:"list-disc pl-5 mt-2 space-y-1 text-sm",children:Q.map((o,R)=>e.jsxs("li",{children:[e.jsx(V,{variant:"outline",className:"mr-2",children:o.scope}),e.jsxs("span",{className:"font-medium",children:[o.label,":"]})," ",o.detail]},R))})})]}),N.length>0&&e.jsx("div",{className:"border rounded-md overflow-x-auto",children:e.jsxs("table",{className:"w-full text-sm",children:[e.jsx("thead",{className:"bg-muted",children:e.jsxs("tr",{children:[e.jsx("th",{className:"text-left p-2",children:"Source"}),e.jsx("th",{className:"text-left p-2",children:"Title"}),e.jsx("th",{className:"text-left p-2",children:"Amount"}),e.jsx("th",{className:"text-left p-2",children:"Currency"}),e.jsx("th",{className:"text-left p-2",children:"Campaign ID"})]})}),e.jsx("tbody",{children:N.map(o=>e.jsxs("tr",{className:"border-t",children:[e.jsx("td",{className:"p-2",children:e.jsx(V,{variant:o.source==="draw"?"default":"secondary",children:o.source})}),e.jsx("td",{className:"p-2",children:o.title}),e.jsx("td",{className:"p-2",children:o.amount??"â"}),e.jsx("td",{className:"p-2",children:o.currency??"â"}),e.jsx("td",{className:"p-2 font-mono text-xs",children:o.campaignId||e.jsx("span",{className:"text-destructive",children:"missing"})})]},`${o.source}-${o.id}`))})]})})]})]})},ja=()=>{const[t,c]=n.useState({members:0,totalPoints:0,claimsThisMonth:0}),[_,S]=n.useState(null),[i,g]=n.useState(!1);n.useEffect(()=>{(async()=>{const y=new Date;y.setDate(1),y.setHours(0,0,0,0);const[{count:s},{data:d},{count:m},{data:l}]=await Promise.all([j.from("customers").select("id",{count:"exact",head:!0}).gt("total_points",0),j.from("customers").select("total_points").gt("total_points",0),j.from("reward_claims").select("id",{count:"exact",head:!0}).eq("status","verified").gte("verified_at",y.toISOString()),j.from("reward_settings").select("is_active").limit(1).maybeSingle()]),w=(d||[]).reduce((A,P)=>A+Number(P.total_points||0),0);c({members:s||0,totalPoints:w,claimsThisMonth:m||0}),S((l==null?void 0:l.is_active)??!1)})()},[]);const N=async y=>{const s=_;S(y),g(!0);const{data:d}=await j.from("reward_settings").select("id").limit(1).maybeSingle();if(!(d!=null&&d.id)){S(s),g(!1),p.error("Reward settings not initialized");return}const{error:m}=await j.from("reward_settings").update({is_active:y}).eq("id",d.id);if(g(!1),m){S(s),p.error("Failed to update program status");return}p.success(y?"Rewards program enabled":"Rewards program paused")};return e.jsxs("div",{className:"container mx-auto p-4 md:p-6 space-y-6",children:[e.jsxs("div",{className:"flex flex-col md:flex-row md:items-center md:justify-between gap-4",children:[e.jsxs("div",{children:[e.jsx("h1",{className:"text-2xl md:text-3xl font-bold",children:"Recovery Rewards"}),e.jsx("p",{className:"text-muted-foreground",children:"Manage the points program, claims, and members."})]}),e.jsxs("div",{className:"flex items-center gap-3 rounded-lg border bg-card px-4 py-3 shadow-sm",children:[e.jsxs("div",{className:"flex flex-col",children:[e.jsx(h,{htmlFor:"program-active-toggle",className:"text-sm font-semibold cursor-pointer",children:"Program Active"}),e.jsx("span",{className:"text-xs text-muted-foreground",children:_===null?"Loadingâ¦":_?"Customers can earn & redeem points":"Earning & redemptions are paused"})]}),_!==null&&e.jsx(V,{variant:_?"default":"secondary",className:_?"bg-emerald-600 hover:bg-emerald-600":"",children:_?"ON":"OFF"}),e.jsx(ue,{id:"program-active-toggle",checked:!!_,disabled:_===null||i,onCheckedChange:N})]})]}),e.jsxs("div",{className:"grid grid-cols-1 sm:grid-cols-3 gap-4",children:[e.jsx(Ze,{icon:e.jsx($s,{className:"h-5 w-5"}),label:"Members",value:t.members}),e.jsx(Ze,{icon:e.jsx(ss,{className:"h-5 w-5"}),label:"Total Points Issued",value:t.totalPoints}),e.jsx(Ze,{icon:e.jsx(pt,{className:"h-5 w-5"}),label:"Claims This Month",value:t.claimsThisMonth})]}),e.jsxs(Fs,{defaultValue:"claims",children:[e.jsxs(Ts,{children:[e.jsx(ie,{value:"claims",children:"Claims"}),e.jsx(ie,{value:"redemptions",children:"Redemptions"}),e.jsx(ie,{value:"audit",children:"Audit Log"}),e.jsx(ie,{value:"catalog",children:"Catalog"}),e.jsx(ie,{value:"verify",children:"Verify"}),e.jsx(ie,{value:"members",children:"Members"}),e.jsx(ie,{value:"referrals",children:"Referrals"}),e.jsx(ie,{value:"settings",children:"Settings"}),e.jsx(ie,{value:"blocklist",children:"Blocklist"})]}),e.jsx(ce,{value:"claims",className:"mt-4",children:e.jsx(gt,{})}),e.jsx(ce,{value:"redemptions",className:"mt-4",children:e.jsx(bt,{})}),e.jsx(ce,{value:"audit",className:"mt-4",children:e.jsx(Rt,{})}),e.jsx(ce,{value:"catalog",className:"mt-4",children:e.jsx(Nt,{})}),e.jsx(ce,{value:"verify",className:"mt-4",children:e.jsx(Pt,{})}),e.jsx(ce,{value:"members",className:"mt-4",children:e.jsx(_t,{})}),e.jsx(ce,{value:"referrals",className:"mt-4",children:e.jsx(Dt,{})}),e.jsx(ce,{value:"settings",className:"mt-4",children:e.jsx(vt,{})}),e.jsx(ce,{value:"blocklist",className:"mt-4",children:e.jsx(yt,{})})]})]})};function Ze({icon:t,label:c,value:_}){return e.jsx(J,{children:e.jsxs(K,{className:"p-5 flex items-center gap-4",children:[e.jsx("div",{className:"bg-primary/10 text-primary p-3 rounded-full",children:t}),e.jsxs("div",{children:[e.jsx("p",{className:"text-sm text-muted-foreground",children:c}),e.jsx("p",{className:"text-2xl font-bold",children:_.toLocaleStr
12ing()})]})]})})}export{ja 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.