@cedros/pay-react 1.1.30 → 1.1.31
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +53 -30
- package/dist/{AISettingsSection-C0zqPbd6.js → AISettingsSection-B12x5sV5.js} +2 -2
- package/dist/{AISettingsSection-BMh3hAb5.mjs → AISettingsSection-DXWDF4Cf.mjs} +4 -4
- package/dist/AutosaveIndicator-CJdkhZis.js +1 -0
- package/dist/{AutosaveIndicator-3ctAnz8Y.mjs → AutosaveIndicator-D966vOrP.mjs} +1 -1
- package/dist/CedrosContext-3Dz7_9Ct.js +3 -0
- package/dist/{CedrosContext-5Gjveoba.mjs → CedrosContext-DQc_k5PG.mjs} +430 -314
- package/dist/ChatLogsSection-CH37u0nX.js +1 -0
- package/dist/{ChatLogsSection-BtJixYAp.mjs → ChatLogsSection-DR7mpuQS.mjs} +2 -2
- package/dist/{ComplianceSection-BMnb1p4w.mjs → ComplianceSection-C61_Hf-X.mjs} +3 -3
- package/dist/ComplianceSection-DS4e2IBp.js +1 -0
- package/dist/CryptoButton-BQceZhbn.js +1 -0
- package/dist/{CryptoButton-Cl2kZbOP.mjs → CryptoButton-BuO_RZLj.mjs} +4 -5
- package/dist/CustomersSection-Bzs9Qon3.js +1 -0
- package/dist/{CustomersSection-dmwoBhcf.mjs → CustomersSection-CWWvusxs.mjs} +2 -2
- package/dist/DisputesSection-ClcYIHga.js +1 -0
- package/dist/{DisputesSection-CHyLne76.mjs → DisputesSection-D8rcS5Vs.mjs} +2 -2
- package/dist/{Dropdown-BRSZlhik.mjs → Dropdown-0y3S40Xf.mjs} +1 -1
- package/dist/Dropdown-BuKiVR_L.js +1 -0
- package/dist/{ErrorBanner-lZJhCmDX.mjs → ErrorBanner-DAjYj6Dx.mjs} +1 -1
- package/dist/ErrorBanner-DxrRVqwe.js +1 -0
- package/dist/FAQSection-0UnN2BZs.js +1 -0
- package/dist/{FAQSection-Di2xE9Sm.mjs → FAQSection-Dck0NM-A.mjs} +3 -3
- package/dist/{ImagesSection-D63PEjR6.mjs → ImagesSection-Bn9GrRRa.mjs} +2 -2
- package/dist/ImagesSection-CSwBHvNl.js +1 -0
- package/dist/{InventorySection-Dp5Yu4TA.mjs → InventorySection-Dytfmtn8.mjs} +2 -2
- package/dist/InventorySection-ymxaMcIg.js +1 -0
- package/dist/{MessagingSection-BLCnCpEv.mjs → MessagingSection-CHFbSxJL.mjs} +3 -3
- package/dist/MessagingSection-Dtfv0DvU.js +1 -0
- package/dist/OrdersSection-BuzTs9XG.js +1 -0
- package/dist/{OrdersSection-Bd56F3cj.mjs → OrdersSection-vYNuVF5X.mjs} +2 -2
- package/dist/{PaymentSettingsSection-B5J56VAk.js → PaymentSettingsSection-BOaW8lLv.js} +1 -1
- package/dist/{PaymentSettingsSection-52iw47Su.mjs → PaymentSettingsSection-BqdGrXen.mjs} +3 -3
- package/dist/{ReturnsSection-DUVeKrCd.mjs → ReturnsSection-CRzhXKtI.mjs} +2 -2
- package/dist/ReturnsSection-i5W_3so1.js +1 -0
- package/dist/{SettingsSection-vK9WIwXE.mjs → SettingsSection-6o3d8DrH.mjs} +1 -1
- package/dist/{SettingsSection-DKkHykaC.js → SettingsSection-CIhO51Zj.js} +1 -1
- package/dist/ShippingSection-BUzPW1AG.js +1 -0
- package/dist/{ShippingSection-CZRrXrlh.mjs → ShippingSection-CbNzGyCP.mjs} +2 -2
- package/dist/SingleCategorySettings-BxVUUy8R.js +3 -0
- package/dist/{SingleCategorySettings-C8xJ47_T.mjs → SingleCategorySettings-Qj_ptB_x.mjs} +4 -4
- package/dist/{StatsBar-D4cOKG2e.mjs → StatsBar-CwCBHBn-.mjs} +1 -1
- package/dist/StatsBar-DDUWoizP.js +1 -0
- package/dist/StorefrontSection-CZZj5he9.js +1 -0
- package/dist/{StorefrontSection-uXSVbEAa.mjs → StorefrontSection-DIYDmj59.mjs} +4 -4
- package/dist/SubscriptionsSection-Bof5MElz.js +1 -0
- package/dist/{SubscriptionsSection-Ci_AZrWA.mjs → SubscriptionsSection-lMVHdV5X.mjs} +3 -3
- package/dist/TaxSection-Be-9v60Z.js +1 -0
- package/dist/{TaxSection-BTukS_cU.mjs → TaxSection-dD7PzQvG.mjs} +2 -2
- package/dist/Token22Section-Di5fHsrU.js +1 -0
- package/dist/{Token22Section-DRsPJuTq.mjs → Token22Section-Dos0CYEk.mjs} +2 -2
- package/dist/{WalletManager-D-eoqUDy.mjs → WalletManager-CGR69MiR.mjs} +1 -1
- package/dist/{WalletManager-DXChB9LA.js → WalletManager-ZJbGQHrn.js} +1 -1
- package/dist/{WebhooksSection-A8Y4ZGcj.mjs → WebhooksSection-5gqXzIhq.mjs} +2 -2
- package/dist/WebhooksSection-CiLDyl7c.js +1 -0
- package/dist/admin.js +1 -1
- package/dist/admin.mjs +1 -1
- package/dist/crypto-only.js +1 -1
- package/dist/crypto-only.mjs +102 -105
- package/dist/{index-9QF_UfSN.mjs → index-CU6M10Rs.mjs} +13 -14
- package/dist/{index-Cq9ya93W.js → index-DVxx_62C.js} +10 -10
- package/dist/index.js +1 -1
- package/dist/index.mjs +31 -34
- package/dist/pay-react.css +1 -1
- package/dist/plugin-BIkt3boU.mjs +339 -0
- package/dist/plugin-Dw8_Q8rE.js +1 -0
- package/dist/sections-D1d83mfH.js +1 -0
- package/dist/{sections-more-Ixw6mM6R.mjs → sections-DcUfZQNE.mjs} +263 -270
- package/dist/src/admin/plugin.d.ts.map +1 -1
- package/dist/src/admin/sectionIds.d.ts.map +1 -1
- package/dist/src/admin.d.ts +0 -7
- package/dist/src/admin.d.ts.map +1 -1
- package/dist/src/components/admin/index.d.ts +0 -1
- package/dist/src/components/admin/index.d.ts.map +1 -1
- package/dist/src/index.d.ts +0 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/stripe-only.js +1 -1
- package/dist/stripe-only.mjs +18 -19
- package/dist/styles-BwaDljnz.js +1 -0
- package/dist/{styles-DGagylUj.mjs → styles-fihm6qVA.mjs} +51 -52
- package/dist/testing/index.js +1 -1
- package/dist/testing/index.mjs +1 -1
- package/package.json +6 -8
- package/dist/AutosaveIndicator-DXRPr4P7.js +0 -1
- package/dist/CedrosContext-CCakH2SZ.js +0 -3
- package/dist/CedrosPayAdminDashboard-DaJ9JoGn.mjs +0 -250
- package/dist/CedrosPayAdminDashboard-Uvyh9p7A.js +0 -1
- package/dist/ChatLogsSection-FC3O536G.js +0 -1
- package/dist/ComplianceSection-BioTKm7k.js +0 -1
- package/dist/CryptoButton-DxFCYDlJ.js +0 -1
- package/dist/CustomersSection-z6ARxuex.js +0 -1
- package/dist/DisputesSection-BjHHQAi7.js +0 -1
- package/dist/Dropdown-j8o0OO5L.js +0 -1
- package/dist/ErrorBanner-CAgPnj62.js +0 -1
- package/dist/FAQSection-b34DMzgV.js +0 -1
- package/dist/ImagesSection-DGBA7iKY.js +0 -1
- package/dist/InventorySection-bVCECzX5.js +0 -1
- package/dist/LazyCedrosPayAdminDashboard-BqJDNrDI.mjs +0 -9
- package/dist/LazyCedrosPayAdminDashboard-CpfTtOBc.js +0 -1
- package/dist/MessagingSection-DU0dYNMy.js +0 -1
- package/dist/OrdersSection-FOFEAgs1.js +0 -1
- package/dist/ReturnsSection-BjpIVFfN.js +0 -1
- package/dist/ShippingSection-B5lk7zpS.js +0 -1
- package/dist/SingleCategorySettings-g7D-9lG1.js +0 -3
- package/dist/StatsBar-CWXw2ZT3.js +0 -1
- package/dist/StorefrontSection-BWnMB9k-.js +0 -1
- package/dist/SubscriptionsSection-DQfXkuDv.js +0 -1
- package/dist/TaxSection-cuPQISxZ.js +0 -1
- package/dist/ThemeContext-CFXyYx7A.js +0 -1
- package/dist/ThemeContext-l0bqcOGW.mjs +0 -126
- package/dist/Token22Section-CCfkDm8W.js +0 -1
- package/dist/WebhooksSection-CnEmaGH1.js +0 -1
- package/dist/icons-C3yDMnKE.mjs +0 -235
- package/dist/icons-Cjgd9YVo.js +0 -1
- package/dist/sectionIds-D46-_-h-.js +0 -1
- package/dist/sectionIds-YktNxmRt.mjs +0 -124
- package/dist/sections-511_XBh4.js +0 -1
- package/dist/sections-CRaMa8ZB.mjs +0 -9
- package/dist/sections-more-Cgw2qJlA.js +0 -1
- package/dist/src/components/admin/CedrosPayAdminDashboard.d.ts +0 -40
- package/dist/src/components/admin/CedrosPayAdminDashboard.d.ts.map +0 -1
- package/dist/src/components/admin/LazyCedrosPayAdminDashboard.d.ts +0 -4
- package/dist/src/components/admin/LazyCedrosPayAdminDashboard.d.ts.map +0 -1
- package/dist/src/standalone-admin.d.ts +0 -8
- package/dist/src/standalone-admin.d.ts.map +0 -1
- package/dist/standalone-admin.d.ts +0 -2
- package/dist/standalone-admin.js +0 -1
- package/dist/standalone-admin.mjs +0 -4
- package/dist/styles--fxb3lCl.js +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),n=require("react"),I=require("./plugin-Dw8_Q8rE.js"),D=require("./ErrorBanner-DxrRVqwe.js"),o=require("./dateHelpers-BKW_lGND.js");function $({serverUrl:_,apiKey:l,pageSize:i=20,authManager:m}){const[g,p]=n.useState([]),[h,w]=n.useState(0),[r,u]=n.useState(0),[A,b]=n.useState(!0),[k,x]=n.useState(null),[d,T]=n.useState("all"),[y,v]=n.useState(null),[L,S]=n.useState(!1),f=n.useCallback(async t=>{if(m?.isAuthenticated())return m.fetchWithAuth(t);const a={"Content-Type":"application/json"};l&&(a["X-API-Key"]=l);const s=await fetch(`${_}${t}`,{headers:a});if(!s.ok)throw new Error(`Request failed: ${s.status}`);return s.json()},[_,l,m]),C=n.useCallback(async()=>{b(!0),x(null);try{const t=new URLSearchParams;t.set("limit",String(i)),t.set("offset",String(r)),d!=="all"&&t.set("status",d);const a=await f(`/admin/chats?${t.toString()}`);p(a.sessions??[]),w(a.total??0)}catch{x("Failed to load chat sessions"),p([])}finally{b(!1)}},[f,i,r,d]);n.useEffect(()=>{C()},[C]);const E=async t=>{S(!0);try{const a=await f(`/admin/chats/${encodeURIComponent(t)}`);v(a)}catch{x("Failed to load chat session")}finally{S(!1)}},j=Math.max(1,Math.ceil(h/i)),N=Math.floor(r/i)+1;if(y){const{session:t,messages:a}=y;return e.jsxs("div",{children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",onClick:()=>v(null),style:{marginBottom:"1rem"},children:"← Back to sessions"}),e.jsx("div",{className:"cedros-admin__section-header",children:e.jsxs("h3",{className:"cedros-admin__section-title",children:["Chat Session",e.jsxs("span",{className:"cedros-admin__badge cedros-admin__badge--muted",style:{marginLeft:"0.5rem"},children:[t.messageCount," messages"]})]})}),e.jsxs("div",{style:{fontSize:"0.85rem",color:"var(--cedros-admin-text-muted, #888)",marginBottom:"1rem"},children:[t.customerEmail&&e.jsxs("span",{children:["Customer: ",e.jsx("strong",{children:t.customerEmail})," · "]}),"Started ",o.formatDateTime(t.createdAt)," · Last message ",o.formatDateTime(t.lastMessageAt)]}),e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:"0.75rem",maxWidth:"640px"},children:a.map(s=>e.jsxs("div",{style:{display:"flex",flexDirection:"column",alignItems:s.role==="user"?"flex-end":"flex-start"},children:[e.jsx("div",{style:{maxWidth:"85%",padding:"0.5rem 0.75rem",borderRadius:"0.75rem",fontSize:"0.85rem",lineHeight:"1.4",background:s.role==="user"?"var(--cedros-admin-bg-dark, #1a1a1a)":"var(--cedros-admin-bg-muted, #f5f5f5)",color:s.role==="user"?"#fff":"var(--cedros-admin-text, #333)"},children:e.jsx("span",{style:{whiteSpace:"pre-wrap",wordBreak:"break-word"},children:s.content})}),s.products&&s.products.length>0&&e.jsx("div",{style:{maxWidth:"85%",marginTop:"0.25rem",display:"flex",flexWrap:"wrap",gap:"0.25rem"},children:s.products.map(c=>e.jsxs("span",{className:"cedros-admin__badge cedros-admin__badge--muted",style:{fontSize:"0.75rem"},children:[c.name,c.priceCents!=null?` ($${(c.priceCents/100).toFixed(2)})`:""]},c.id))}),s.actions&&s.actions.length>0&&e.jsx("div",{style:{maxWidth:"85%",marginTop:"0.25rem",fontSize:"0.75rem",fontStyle:"italic",color:"var(--cedros-admin-text-muted, #888)"},children:s.actions.join(" · ")}),e.jsx("div",{style:{fontSize:"0.7rem",color:"var(--cedros-admin-text-muted, #aaa)",marginTop:"0.15rem"},children:o.formatDateTime(s.createdAt)})]},s.id))})]})}return e.jsxs("div",{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Chat Logs"})}),e.jsx(D.ErrorBanner,{message:k}),e.jsxs("div",{style:{display:"flex",gap:"0.5rem",marginBottom:"1rem",alignItems:"center"},children:[e.jsxs("select",{className:"cedros-admin__input",value:d,onChange:t=>{T(t.target.value),u(0)},style:{width:"auto",fontSize:"0.85rem"},children:[e.jsx("option",{value:"all",children:"All statuses"}),e.jsx("option",{value:"active",children:"Active"}),e.jsx("option",{value:"archived",children:"Archived"})]}),e.jsxs("span",{style:{fontSize:"0.85rem",color:"var(--cedros-admin-text-muted, #888)"},children:[h," session",h!==1?"s":""]})]}),A||L?e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Loading chat sessions..."]}):g.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No chat sessions found."}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Customer"}),e.jsx("th",{children:"Messages"}),e.jsx("th",{children:"Status"}),e.jsx("th",{children:"Last Message"}),e.jsx("th",{children:"Started"}),e.jsx("th",{})]})}),e.jsx("tbody",{children:g.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:t.customerEmail?e.jsx("span",{title:t.customerId,children:t.customerEmail}):t.customerId?e.jsxs("code",{style:{fontSize:"0.75rem"},children:[t.customerId.slice(0,12),"..."]}):e.jsx("span",{style:{color:"var(--cedros-admin-text-muted, #888)"},children:"Anonymous"})}),e.jsx("td",{children:t.messageCount}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${t.status==="active"?"success":"muted"}`,children:t.status})}),e.jsx("td",{children:o.formatDateTime(t.lastMessageAt)}),e.jsx("td",{children:o.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",onClick:()=>E(t.id),children:"View"})})]},t.id))})]})}),j>1&&e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",marginTop:"0.75rem",fontSize:"0.85rem"},children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:r===0,onClick:()=>u(Math.max(0,r-i)),children:"Previous"}),e.jsxs("span",{children:["Page ",N," of ",j]}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:N>=j,onClick:()=>u(r+i),children:"Next"})]})]})]})}exports.ChatLogsSection=$;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as s, jsx as e, Fragment as W } from "react/jsx-runtime";
|
|
2
2
|
import { useState as i, useCallback as k, useEffect as j } from "react";
|
|
3
|
-
import { I as B } from "./
|
|
4
|
-
import { E as M } from "./ErrorBanner-
|
|
3
|
+
import { I as B } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as M } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as d } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
function H({ serverUrl: b, apiKey: m, pageSize: o = 20, authManager: h }) {
|
|
7
7
|
const [y, v] = i([]), [u, I] = i(0), [r, f] = i(0), [E, x] = i(!0), [L, _] = i(null), [c, $] = i("all"), [S, C] = i(null), [F, N] = i(!1), p = k(async (t) => {
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { jsxs as n, jsx as e, Fragment as j } from "react/jsx-runtime";
|
|
2
2
|
import { useState as i, useCallback as L, useEffect as U } from "react";
|
|
3
|
-
import { I as $ } from "./
|
|
4
|
-
import { E as me } from "./ErrorBanner-
|
|
5
|
-
import { S as Z } from "./StatsBar-
|
|
3
|
+
import { I as $ } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as me } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
|
+
import { S as Z } from "./StatsBar-CwCBHBn-.mjs";
|
|
6
6
|
import { g as v } from "./fetchWithTimeout-DmMOwL0Q.mjs";
|
|
7
7
|
import { f as E } from "./dateHelpers-yvPkofYQ.mjs";
|
|
8
8
|
const b = (s) => s.length > 12 ? `${s.slice(0, 6)}...${s.slice(-4)}` : s, he = (s) => {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),n=require("react"),I=require("./plugin-Dw8_Q8rE.js"),ce=require("./ErrorBanner-DxrRVqwe.js"),V=require("./StatsBar-DDUWoizP.js"),_=require("./fetchWithTimeout-CG0EKbhf.js"),R=require("./dateHelpers-BKW_lGND.js"),j=a=>a.length>12?`${a.slice(0,6)}...${a.slice(-4)}`:a,de=a=>{switch(a){case"active":return"success";case"frozen":return"failed";case"thawed":return"pending";default:return"muted"}},X=a=>{switch(a){case"freeze":return"failed";case"thaw":return"success";case"sweep_freeze":return"failed";case"report_generated":return"muted";default:return"muted"}},oe=a=>{switch(a){case"verified":return"success";case"pending":return"pending";case"expired":return"failed";case"none":default:return"muted"}},le="https://explorer.solana.com/tx/",me={apiUrl:"",refreshIntervalSecs:3600,enabled:!1};function he({serverUrl:a,apiKey:m,authManager:h}){const[r,o]=n.useState(me),[y,C]=n.useState(!0),[u,g]=n.useState(!1),[i,w]=n.useState(!1),[N,p]=n.useState(null),[A,f]=n.useState(null),b=n.useCallback(async(s,l)=>{if(h?.isAuthenticated())return h.fetchWithAuth(s,l);const S={"Content-Type":"application/json"};m&&(S["X-API-Key"]=m);const T=await fetch(`${a}${s}`,{...l,headers:{...S,...l?.headers}});if(!T.ok)throw new Error(`Request failed: ${T.status}`);return T.json()},[a,m,h]);n.useEffect(()=>{(async()=>{try{const s=await b("/admin/compliance/sanctions-api");o(s)}catch(s){_.getLogger().error("[ComplianceSanctionsApi] Failed to fetch settings:",s)}finally{C(!1)}})()},[b]);const k=async()=>{g(!0),p(null),f(null);try{await b("/admin/compliance/sanctions-api",{method:"PUT",body:JSON.stringify(r)}),f("Settings saved")}catch(s){_.getLogger().error("[ComplianceSanctionsApi] Save failed:",s),p("Failed to save settings")}finally{g(!1)}},d=async()=>{w(!0),p(null),f(null);try{await b("/admin/compliance/sanctions-api/refresh",{method:"POST"}),f("Sanctions list refreshed")}catch(s){_.getLogger().error("[ComplianceSanctionsApi] Refresh failed:",s),p("Failed to refresh sanctions list")}finally{w(!1)}};return y?e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Loading sanctions API settings..."]}):e.jsxs("div",{style:{maxWidth:"500px",display:"flex",flexDirection:"column",gap:"1rem"},children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Dynamic Sanctions API"})}),N&&e.jsx("div",{className:"cedros-admin__badge cedros-admin__badge--failed",style:{padding:"0.5rem"},children:N}),A&&e.jsx("div",{className:"cedros-admin__badge cedros-admin__badge--success",style:{padding:"0.5rem"},children:A}),e.jsxs("label",{style:{display:"flex",alignItems:"center",gap:"0.5rem",fontSize:"0.9rem"},children:[e.jsx("input",{type:"checkbox",checked:r.enabled,onChange:s=>o(l=>({...l,enabled:s.target.checked}))}),"Enable dynamic sanctions list"]}),e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["API URL",e.jsx("input",{type:"url",className:"cedros-admin__input",placeholder:"https://sunscreen.cedros.io",value:r.apiUrl,onChange:s=>o(l=>({...l,apiUrl:s.target.value}))})]}),e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["Refresh interval (seconds, min 60)",e.jsx("input",{type:"number",className:"cedros-admin__input",min:60,value:r.refreshIntervalSecs,onChange:s=>o(l=>({...l,refreshIntervalSecs:Number(s.target.value)})),style:{width:"160px"}})]}),e.jsxs("div",{style:{display:"flex",gap:"0.5rem"},children:[e.jsx("button",{className:"cedros-admin__button cedros-admin__button--primary",onClick:k,disabled:u,children:u?"Saving...":"Save Settings"}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--ghost",onClick:d,disabled:i||!r.enabled||!r.apiUrl,children:i?"Refreshing...":"Force Refresh"})]})]})}function ue({serverUrl:a,apiKey:m,authManager:h}){const[r,o]=n.useState(""),[y,C]=n.useState(!1),[u,g]=n.useState(null),[i,w]=n.useState(null),[N,p]=n.useState(!1),A=n.useCallback(async(d,s)=>{if(h?.isAuthenticated())return h.fetchWithAuth(d,s);const l={"Content-Type":"application/json"};m&&(l["X-API-Key"]=m);const S=await fetch(`${a}${d}`,{...s,headers:{...l,...s?.headers}});if(!S.ok)throw new Error(`Request failed: ${S.status}`);return S.json()},[a,m,h]),f=async()=>{const d=r.trim();if(d){C(!0),g(null),w(null),p(!0);try{const s=await A(`/admin/compliance/user-status/${encodeURIComponent(d)}`);w(s)}catch(s){_.getLogger().error("[ComplianceKycTab] Lookup failed:",s),g("Failed to fetch user compliance status. Ensure cedros-login is configured.")}finally{C(!1)}}},b=d=>{d.key==="Enter"&&f()},k=d=>{switch(d){case"verified":return"Verified";case"pending":return"Pending";case"expired":return"Expired";case"none":default:return"Not Started"}};return e.jsxs("div",{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"KYC & Accredited Investor Status"})}),e.jsx("p",{style:{fontSize:"0.85rem",color:"var(--cedros-admin-text-muted, #888)",marginBottom:"1rem"},children:"Look up a user's KYC verification and accredited investor status from cedros-login."}),e.jsxs("div",{style:{display:"flex",gap:"0.5rem",alignItems:"flex-end",marginBottom:"1.5rem",maxWidth:"500px"},children:[e.jsxs("label",{style:{flex:1,display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["User ID",e.jsx("input",{type:"text",className:"cedros-admin__input",placeholder:"user_abc123",value:r,onChange:d=>o(d.target.value),onKeyDown:b})]}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--primary",onClick:f,disabled:y||!r.trim(),children:y?"Looking up...":"Look Up"})]}),u&&e.jsx("div",{className:"cedros-admin__badge cedros-admin__badge--failed",style:{padding:"0.5rem",marginBottom:"1rem"},children:u}),y&&e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Fetching compliance status..."]}),i&&!y&&e.jsxs("div",{style:{maxWidth:"500px"},children:[e.jsx("div",{className:"cedros-admin__table-container",children:e.jsx("table",{className:"cedros-admin__table",children:e.jsxs("tbody",{children:[e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600,width:"40%"},children:"User ID"}),e.jsx("td",{children:e.jsx("code",{children:i.userId})})]}),e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"KYC Status"}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${oe(i.kycStatus)}`,children:k(i.kycStatus)})})]}),e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Accredited Investor"}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${i.accreditedInvestor?"success":"muted"}`,children:i.accreditedInvestor?"Yes":"No"})})]}),i.accreditedVerifiedAt&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Accredited Since"}),e.jsx("td",{children:R.formatDateTime(i.accreditedVerifiedAt)})]})]})})}),e.jsx("div",{style:{marginTop:"0.75rem",padding:"0.75rem",borderRadius:"4px",fontSize:"0.85rem",background:i.kycStatus==="verified"?"var(--cedros-admin-bg-success, #f0fdf4)":"var(--cedros-admin-bg-muted, #f5f5f5)",color:"var(--cedros-admin-text, #333)"},children:i.kycStatus==="verified"&&i.accreditedInvestor?"This user is fully verified and accredited. They can access all compliance-gated products.":i.kycStatus==="verified"?"This user has KYC verification but is not an accredited investor.":i.kycStatus==="pending"?"This user has submitted KYC documents. Verification is in progress.":i.kycStatus==="expired"?"This user's KYC verification has expired. They will need to re-verify.":"This user has not started KYC verification."})]}),N&&!i&&!y&&!u&&e.jsx("div",{className:"cedros-admin__empty",children:"No compliance record found for this user."})]})}function xe({serverUrl:a,apiKey:m,pageSize:h=50,authManager:r}){const[o,y]=n.useState("holders"),[C,u]=n.useState(null),[g,i]=n.useState([]),[w,N]=n.useState(!0),[p,A]=n.useState(""),[f,b]=n.useState([]),[k,d]=n.useState(!0),[s,l]=n.useState(null),[S,T]=n.useState(!1),[W,M]=n.useState(""),[B,Q]=n.useState(""),[O,H]=n.useState({enabled:!0,batchSize:100}),[Z,ee]=n.useState(!0),[q,Y]=n.useState(!1),[x,z]=n.useState(null),[$,D]=n.useState(""),[F,K]=n.useState(!1),v=n.useCallback(async(t,c)=>{if(r?.isAuthenticated())return r.fetchWithAuth(t,c);const L={"Content-Type":"application/json"};m&&(L["X-API-Key"]=m);const U=await fetch(`${a}${t}`,{...c,headers:{...L,...c?.headers}});if(!U.ok)throw new Error(`Request failed: ${U.status}`);return U.json()},[a,m,r]),E=n.useCallback(async()=>{try{const t=p?`&status=${p}`:"",c=await v(`/admin/compliance/holders?limit=${h}&offset=0${t}`);i(c.holders||[])}catch(t){_.getLogger().error("[ComplianceSection] Failed to fetch holders:",t),i([]),u("Failed to load token holders")}finally{N(!1)}},[v,h,p]),P=n.useCallback(async()=>{try{const t=await v(`/admin/compliance/actions?limit=${h}&offset=0`);b(t.actions||[])}catch(t){_.getLogger().error("[ComplianceSection] Failed to fetch actions:",t),b([]),u("Failed to load compliance actions")}finally{d(!1)}},[v,h]),J=n.useCallback(async()=>{try{const t=await v("/admin/compliance/sweep-settings");H(t)}catch(t){_.getLogger().error("[ComplianceSection] Failed to fetch sweep settings:",t)}finally{ee(!1)}},[v]),te=async()=>{Y(!0);try{await v("/admin/compliance/sweep-settings",{method:"PUT",body:JSON.stringify(O)})}catch(t){_.getLogger().error("[ComplianceSection] Failed to save sweep settings:",t),u("Failed to save sweep settings")}finally{Y(!1)}};n.useEffect(()=>{E()},[E]),n.useEffect(()=>{P()},[P]),n.useEffect(()=>{J()},[J]);const se=async()=>{if(!(!x||!$.trim())){K(!0);try{const t=x.action==="freeze"?"/admin/compliance/freeze":"/admin/compliance/thaw";await v(t,{method:"POST",body:JSON.stringify({holderId:x.holder.id,reason:$})}),z(null),D(""),await E(),await P()}catch(t){_.getLogger().error(`[ComplianceSection] ${x.action} failed:`,t),u(`Failed to ${x.action} holder`)}finally{K(!1)}}},ne=async()=>{T(!0);try{const t=new URLSearchParams;W&&t.set("from",new Date(W).toISOString()),B&&t.set("to",new Date(B).toISOString());const c=await v(`/admin/compliance/report?${t.toString()}`);l(c.report)}catch(t){_.getLogger().error("[ComplianceSection] Failed to generate report:",t),u("Failed to generate compliance report")}finally{T(!1)}},ae=()=>{if(!s)return;const t=new Blob([JSON.stringify(s,null,2)],{type:"application/json"}),c=URL.createObjectURL(t),L=document.createElement("a");L.href=c,L.download=`compliance-report-${new Date().toISOString().slice(0,10)}.json`,L.click(),URL.revokeObjectURL(c)},ie=g.length,G=g.filter(t=>t.status==="frozen").length,re=g.filter(t=>t.status==="active").length;return e.jsxs("div",{className:"cedros-admin__page",children:[e.jsx(ce.ErrorBanner,{message:C,onRetry:()=>{E(),P()}}),e.jsx(V.StatsBar,{stats:[{label:"Total Holders",value:ie},{label:"Active",value:re,variant:"success"},{label:"Frozen",value:G,variant:G>0?"warning":"muted"},{label:"Actions Logged",value:f.length}],isLoading:w||k}),e.jsx("div",{className:"cedros-admin__tabs",style:{display:"flex",gap:"0.5rem",marginBottom:"1rem"},children:["holders","actions","reports","sweep-settings","sanctions-api","kyc"].map(t=>{const c=t==="holders"?"Token Holders":t==="actions"?"Actions Log":t==="reports"?"Reports":t==="sweep-settings"?"Sweep Settings":t==="sanctions-api"?"Sanctions API":"KYC & Accreditation";return e.jsx("button",{type:"button",className:`cedros-admin__button ${o===t?"cedros-admin__button--primary":"cedros-admin__button--ghost"}`,onClick:()=>y(t),children:c},t)})}),o==="holders"&&e.jsxs(e.Fragment,{children:[e.jsxs("div",{className:"cedros-admin__section-header",style:{display:"flex",alignItems:"center",gap:"0.75rem"},children:[e.jsx("h3",{className:"cedros-admin__section-title",children:"Token Holders"}),e.jsxs("select",{value:p,onChange:t=>{A(t.target.value),N(!0)},className:"cedros-admin__input",style:{width:"auto",padding:"0.25rem 0.5rem",fontSize:"0.85rem"},children:[e.jsx("option",{value:"",children:"All statuses"}),e.jsx("option",{value:"active",children:"Active"}),e.jsx("option",{value:"frozen",children:"Frozen"}),e.jsx("option",{value:"thawed",children:"Thawed"})]})]}),w?e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Loading holders..."]}):g.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No token holders found."}):e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Wallet"}),e.jsx("th",{children:"Collection"}),e.jsx("th",{children:"Mint"}),e.jsx("th",{children:"Amount"}),e.jsx("th",{children:"Status"}),e.jsx("th",{children:"Created"}),e.jsx("th",{children:"Actions"})]})}),e.jsx("tbody",{children:g.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:e.jsx("code",{title:t.walletAddress,children:j(t.walletAddress)})}),e.jsx("td",{children:e.jsx("code",{title:t.collectionId,children:j(t.collectionId)})}),e.jsx("td",{children:e.jsx("code",{title:t.mintAddress,children:j(t.mintAddress)})}),e.jsx("td",{children:t.amountMinted}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${de(t.status)}`,children:t.status})}),e.jsx("td",{children:R.formatDateTime(t.createdAt)}),e.jsx("td",{children:t.status==="active"||t.status==="thawed"?e.jsx("button",{className:"cedros-admin__button cedros-admin__button--danger cedros-admin__button--sm",onClick:()=>{z({holder:t,action:"freeze"}),D("")},children:"Freeze"}):t.status==="frozen"?e.jsx("button",{className:"cedros-admin__button cedros-admin__button--primary cedros-admin__button--sm",onClick:()=>{z({holder:t,action:"thaw"}),D("")},children:"Thaw"}):null})]},t.id))})]})})]}),o==="actions"&&e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Compliance Actions"})}),k?e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Loading actions..."]}):f.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No compliance actions recorded."}):e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Timestamp"}),e.jsx("th",{children:"Type"}),e.jsx("th",{children:"Wallet"}),e.jsx("th",{children:"Reason"}),e.jsx("th",{children:"Actor"}),e.jsx("th",{children:"Tx Signature"})]})}),e.jsx("tbody",{children:f.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:R.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${X(t.actionType)}`,children:t.actionType})}),e.jsx("td",{children:e.jsx("code",{title:t.walletAddress,children:j(t.walletAddress)})}),e.jsx("td",{children:t.reason||"—"}),e.jsx("td",{children:e.jsx("code",{children:j(t.actor)})}),e.jsx("td",{children:t.txSignature?e.jsx("a",{href:`${le}${t.txSignature}`,target:"_blank",rel:"noopener noreferrer",className:"cedros-admin__link",children:j(t.txSignature)}):"—"})]},t.id))})]})})]}),o==="reports"&&e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Compliance Report"})}),e.jsxs("div",{style:{display:"flex",gap:"0.75rem",alignItems:"flex-end",marginBottom:"1rem"},children:[e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["From",e.jsx("input",{type:"date",className:"cedros-admin__input",value:W,onChange:t=>M(t.target.value)})]}),e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["To",e.jsx("input",{type:"date",className:"cedros-admin__input",value:B,onChange:t=>Q(t.target.value)})]}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--primary",onClick:ne,disabled:S,children:S?"Generating...":"Generate Report"})]}),s&&e.jsxs("div",{children:[e.jsx(V.StatsBar,{stats:[{label:"Total Holders",value:s.totalHolders},{label:"Frozen",value:s.totalFrozen,variant:s.totalFrozen>0?"warning":"muted"},{label:"Freezes",value:s.freezeCount},{label:"Thaws",value:s.thawCount},{label:"Sweep Freezes",value:s.sweepFreezeCount,variant:s.sweepFreezeCount>0?"warning":"muted"}],isLoading:!1}),e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",margin:"1rem 0 0.5rem"},children:[e.jsxs("span",{style:{fontSize:"0.85rem",color:"var(--cedros-admin-text-muted, #888)"},children:["Generated ",R.formatDateTime(s.generatedAt)," · ",s.actionsInPeriod," actions in period"]}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--ghost",onClick:ae,children:"Download JSON"})]}),s.actions.length>0&&e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Timestamp"}),e.jsx("th",{children:"Type"}),e.jsx("th",{children:"Wallet"}),e.jsx("th",{children:"Reason"}),e.jsx("th",{children:"Actor"})]})}),e.jsx("tbody",{children:s.actions.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:R.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${X(t.actionType)}`,children:t.actionType})}),e.jsx("td",{children:e.jsx("code",{title:t.walletAddress,children:j(t.walletAddress)})}),e.jsx("td",{children:t.reason||"—"}),e.jsx("td",{children:e.jsx("code",{children:j(t.actor)})})]},t.id))})]})})]})]}),o==="sweep-settings"&&e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Sanctions Sweep Settings"})}),Z?e.jsxs("div",{className:"cedros-admin__loading",children:[I.Icons.loading," Loading settings..."]}):e.jsxs("div",{style:{maxWidth:"400px",display:"flex",flexDirection:"column",gap:"1rem"},children:[e.jsxs("label",{style:{display:"flex",alignItems:"center",gap:"0.5rem",fontSize:"0.9rem"},children:[e.jsx("input",{type:"checkbox",checked:O.enabled,onChange:t=>H(c=>({...c,enabled:t.target.checked}))}),"Enable automated sanctions sweep"]}),e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["Batch size (1 – 10,000)",e.jsx("input",{type:"number",className:"cedros-admin__input",min:1,max:1e4,value:O.batchSize,onChange:t=>H(c=>({...c,batchSize:Number(t.target.value)})),style:{width:"160px"}})]}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--primary",onClick:te,disabled:q,style:{alignSelf:"flex-start"},children:q?"Saving...":"Save Settings"})]})]}),o==="sanctions-api"&&e.jsx(he,{serverUrl:a,apiKey:m,authManager:r}),o==="kyc"&&e.jsx(ue,{serverUrl:a,apiKey:m,authManager:r}),x&&e.jsx("div",{className:"cedros-admin__modal-overlay",onClick:()=>!F&&z(null),children:e.jsxs("div",{className:"cedros-admin__modal",onClick:t=>t.stopPropagation(),children:[e.jsxs("div",{className:"cedros-admin__modal-header",children:[e.jsxs("h4",{className:"cedros-admin__modal-title",children:[x.action==="freeze"?"Freeze":"Thaw"," Token Account"]}),e.jsx("button",{type:"button",className:"cedros-admin__modal-close",onClick:()=>!F&&z(null),children:I.Icons.close})]}),e.jsxs("div",{className:"cedros-admin__modal-body",children:[e.jsxs("p",{style:{marginBottom:"0.5rem",fontSize:"0.9rem"},children:["Wallet: ",e.jsx("code",{children:j(x.holder.walletAddress)})]}),e.jsxs("p",{style:{marginBottom:"0.75rem",fontSize:"0.9rem"},children:["Mint: ",e.jsx("code",{children:j(x.holder.mintAddress)})]}),e.jsxs("label",{style:{display:"flex",flexDirection:"column",gap:"0.25rem",fontSize:"0.85rem"},children:["Reason (required)",e.jsx("textarea",{className:"cedros-admin__input",rows:3,value:$,onChange:t=>D(t.target.value),placeholder:`Reason for ${x.action}...`,maxLength:1024})]})]}),e.jsxs("div",{className:"cedros-admin__modal-footer",children:[e.jsx("button",{className:"cedros-admin__button cedros-admin__button--ghost",onClick:()=>z(null),disabled:F,children:"Cancel"}),e.jsx("button",{className:`cedros-admin__button ${x.action==="freeze"?"cedros-admin__button--danger":"cedros-admin__button--primary"}`,onClick:se,disabled:F||!$.trim(),children:F?"Processing...":x.action==="freeze"?"Freeze Account":"Thaw Account"})]})]})})]})}exports.ComplianceSection=xe;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const p=require("react/jsx-runtime"),a=require("react"),ie=require("@solana/wallet-adapter-react"),ce=require("@solana/wallet-adapter-base"),he=require("@solana/wallet-adapter-react-ui"),i=require("./styles-BwaDljnz.js"),N=require("./CedrosContext-3Dz7_9Ct.js"),n=require("./fetchWithTimeout-CG0EKbhf.js");function ue(){const{x402Manager:h,walletManager:l}=N.useCedrosContext(),{publicKey:W,signTransaction:q}=ie.useWallet(),[X,y]=a.useState({status:"idle",error:null,transactionId:null}),[R,L]=a.useState(null),[G,k]=a.useState(null),P=a.useRef(W);P.current=W;const C=a.useRef(q);C.current=q;const g=a.useRef(0),A=6e4,I=()=>{const o=g.current;return o>0&&Date.now()-o<A},S=a.useCallback(()=>{if(!W){const o="Wallet not connected";return y({status:"error",error:o,transactionId:null}),{valid:!1,error:o}}if(!q){const o="Wallet does not support signing";return y({status:"error",error:o,transactionId:null}),{valid:!1,error:o}}return{valid:!0}},[W,q]),j=a.useCallback(async o=>{try{y(d=>({...d,status:"loading"}));const c=await h.requestQuote({resource:o});if(!h.validateRequirement(c))throw new Error("Invalid requirement received from server");return L(c),y(d=>({...d,status:"idle"})),c}catch(c){const d=N.formatError(c,"Failed to fetch requirement");throw y({status:"error",error:d,transactionId:null}),c}},[h]),B=a.useCallback(async(o,c,d,x,r="regular")=>{const s=P.current,m=C.current;if(!s||!m)throw new Error("Wallet disconnected during payment flow");if(!!o.extra?.feePayer){n.getLogger().debug("[useX402Payment] Gasless flow enabled"),n.getLogger().debug("[useX402Payment] Building gasless transaction");const{transaction:b,blockhash:M}=await h.buildGaslessTransaction({resourceId:c,userWallet:s.toString(),feePayer:o.extra.feePayer,couponCode:d});n.getLogger().debug("[useX402Payment] Deserializing backend transaction");const K=l.deserializeTransaction(b);if(P.current?.toString()!==s.toString())throw new Error("Wallet changed during payment flow");n.getLogger().debug("[useX402Payment] Requesting partial signature");const E=await l.partiallySignTransaction({transaction:K,signTransaction:m,blockhash:M});n.getLogger().debug("[useX402Payment] Submitting partial transaction");const z=await h.submitGaslessTransaction({resource:c,partialTx:E,couponCode:d,metadata:x,resourceType:r,requirement:o});return z.success&&z.settlement&&k(z.settlement),z}else{const b=await l.buildTransaction({requirement:o,payerPublicKey:s});if(P.current?.toString()!==s.toString())throw new Error("Wallet changed during payment flow");const M=await l.signTransaction({transaction:b,signTransaction:m}),K=l.buildPaymentPayload({requirement:o,signedTx:M,payerPublicKey:s}),E=await h.submitPayment({resource:c,payload:K,couponCode:d,metadata:x,resourceType:r});return E.success&&E.settlement&&k(E.settlement),E}},[h,l]),w=a.useCallback(async(o,c,d)=>{if(I())return{success:!1,error:"Payment already in progress"};const x=S();if(!x.valid)return{success:!1,error:x.error};g.current=Date.now(),y({status:"loading",error:null,transactionId:null});try{n.getLogger().debug("[useX402Payment] Fetching fresh quote");const r=await h.requestQuote({resource:o,couponCode:c});n.getLogger().debug("[useX402Payment] Received quote",{amount:r.maxAmountRequired}),L(r),n.getLogger().debug("[useX402Payment] Executing payment flow");const s=await B(r,o,c,d,"regular");return s.success?y({status:"success",error:null,transactionId:s.transactionId||"payment-success"}):y({status:"error",error:s.error||"Payment failed",transactionId:null}),s}catch(r){const s=N.formatError(r,"Payment failed");return y({status:"error",error:s,transactionId:null}),{success:!1,error:s}}finally{g.current=0}},[S,h,B]),_=a.useCallback(async(o,c,d)=>{if(I())return{success:!1,error:"Payment already in progress"};const x=S();if(!x.valid)return{success:!1,error:x.error};g.current=Date.now(),y({status:"loading",error:null,transactionId:null});try{const r=i.normalizeCartItems(o),s=await h.requestCartQuote({items:r,metadata:c,couponCode:d}),m=s.cartId,u=s.quote;if(!h.validateRequirement(u))throw new Error("Invalid cart quote received from server");L(u);const b=await B(u,m,d,c,"cart");return b.success?y({status:"success",error:null,transactionId:b.transactionId||"cart-payment-success"}):y({status:"error",error:b.error||"Cart payment failed",transactionId:null}),b}catch(r){const s=N.formatError(r,"Cart payment failed");return y({status:"error",error:s,transactionId:null}),{success:!1,error:s}}finally{g.current=0}},[S,h,B]),T=a.useCallback(()=>{y({status:"idle",error:null,transactionId:null}),L(null),k(null),g.current=0},[]);return{...X,requirement:R,settlement:G,fetchQuote:j,processPayment:w,processCartPayment:_,reset:T}}function de({resource:h,items:l,label:W,disabled:q=!1,onAttempt:X,onSuccess:y,onError:R,className:L="",testPageUrl:G,hideMessages:k=!1,metadata:P,couponCode:C}){const{connected:g,connecting:A,connect:I,disconnect:S,select:j,wallets:B,wallet:w,publicKey:_}=ie.useWallet(),{status:T,error:o,transactionId:c,processPayment:d,processCartPayment:x}=ue(),r=N.useCedrosTheme(),{solanaError:s}=N.useCedrosContext(),{isCartMode:m,effectiveResource:u}=i.usePaymentMode(h,l),{t:b,translations:M}=i.useTranslation(),K=W||b("ui.pay_with_crypto"),E=o&&typeof o!="string"?o?.code??null:null,z=s&&typeof s!="string"?s?.code??null:null,Y=e=>{if(!e||!M)return"";const t=M.errors[e];return t?t.action?`${t.message} ${t.action}`:t.message:""},H=o?typeof o=="string"?o:Y(E):null,J=s?typeof s=="string"?s:Y(z):null,V=a.useRef(y),Z=a.useRef(R),ee=a.useRef(d),te=a.useRef(x);V.current=y,Z.current=R,ee.current=d,te.current=x;const ge=a.useMemo(()=>B.map(e=>`${e.adapter.name}-${e.readyState}`).join(","),[B]),O=a.useMemo(()=>B.filter(({readyState:e})=>e===ce.WalletReadyState.Installed||e===ce.WalletReadyState.Loadable),[ge]);a.useEffect(()=>{if(T==="success"&&c){const e=m&&l?i.getCartItemCount(l):void 0;i.emitPaymentSuccess("crypto",c,u,e),V.current?.(c)}},[T,c,m,l,u]),a.useEffect(()=>{if(T==="error"&&o){const e=m&&l?i.getCartItemCount(l):void 0;i.emitPaymentError("crypto",o,u,e),Z.current?.(o)}},[T,o,m,l,u]);const re=typeof window<"u"&&window.top!==window.self,[ne,$]=a.useState(!1),[oe,U]=a.useState(!1),[D,v]=a.useState(null),F=s;a.useEffect(()=>{let e=!1;return e||(async()=>{if(oe&&w&&!g&&!A){n.getLogger().debug("[CryptoButton] Wallet detected, attempting auto-connect:",w.adapter.name),U(!1),i.emitWalletConnect(w.adapter.name);try{await I(),e||n.getLogger().debug("[CryptoButton] Auto-connect successful")}catch(f){if(!e){n.getLogger().error("[CryptoButton] Auto-connect failed:",f);const Q=f instanceof Error?f.message:"Failed to connect wallet";i.emitWalletError(Q,w.adapter.name),v(null)}}}})(),()=>{e=!0}},[w,oe,g,A,I]),a.useEffect(()=>{let e=!0;if(n.getLogger().debug("[CryptoButton] Payment useEffect triggered",{connected:g,hasPendingPayment:!!D,hasPublicKey:!!_,pendingPaymentType:D?.type}),g&&D&&_&&w&&e){i.emitWalletConnected(w.adapter.name,_.toString()),n.getLogger().debug("[CryptoButton] All conditions met! Processing pending payment:",D);const t=D;v(null),$(!1);const f=t.type==="cart"&&t.items?i.getCartItemCount(t.items):void 0;i.emitPaymentProcessing("crypto",t.resource,f),t.type==="cart"&&t.items?(n.getLogger().debug("[CryptoButton] Auto-processing cart payment"),te.current(t.items,t.metadata,t.couponCode)):t.type==="single"&&t.resource&&(n.getLogger().debug("[CryptoButton] Auto-processing single payment"),ee.current(t.resource,t.couponCode,t.metadata))}return()=>{e=!1}},[g,D,_,w]);const ae=a.useCallback(async()=>{n.getLogger().debug("[CryptoButton] executePaymentFlow called",{connected:g,wallet:w?.adapter.name,couponCode:C,isCartMode:m,hasItems:!!l,effectiveResource:u});const e=m&&l?i.getCartItemCount(l):void 0;if(i.emitPaymentStart("crypto",u,e),X&&X("crypto"),F){n.getLogger().error("[CryptoButton] Solana dependencies missing:",F),i.emitPaymentError("crypto",F,u,e),R&&R(F);return}if(re){const t=G||window.location.href;try{if(new URL(t,window.location.origin).origin!==window.location.origin)throw n.getLogger().error("[CryptoButton] Blocked attempt to open external URL:",t),new Error("Cannot open external URLs from embedded context");window.open(t,"_blank","noopener,noreferrer")}catch(f){throw n.getLogger().error("[CryptoButton] URL validation failed:",f),f}return}if(g)i.emitPaymentProcessing("crypto",u,e),m&&l?(n.getLogger().debug("[CryptoButton] Processing cart payment with coupon:",C),await x(l,P,C)):u&&(n.getLogger().debug("[CryptoButton] Processing single payment with coupon:",C),await d(u,C,P));else{let t=!1;if(m&&l?(n.getLogger().debug("[CryptoButton] Setting pending cart payment with coupon:",C),v({type:"cart",items:l,metadata:P,couponCode:C}),t=!0):u&&(n.getLogger().debug("[CryptoButton] Setting pending single payment with coupon:",C),v({type:"single",resource:u,metadata:P,couponCode:C}),t=!0),!t){n.getLogger().error("[CryptoButton] No valid payment to process");return}try{if(w)n.getLogger().debug("[CryptoButton] Wallet already selected, connecting:",w.adapter.name),i.emitWalletConnect(w.adapter.name),await I();else{if(n.getLogger().debug("[CryptoButton] No wallet selected, showing selector. Available wallets:",O.map(f=>f.adapter.name)),O.length===0){v(null);const f="No wallets available";throw i.emitWalletError(f),new Error(f)}$(!0)}}catch(f){v(null);const Q=f instanceof Error?f.message:"Failed to connect wallet";n.getLogger().error("[CryptoButton] Connection error:",Q),i.emitWalletError(Q,w?.adapter.name)}}},[g,w,C,m,l,u,re,G,O,I,P,x,d,F,X,R]),se=a.useMemo(()=>m&&l?`crypto-cart-${l.map(e=>e.resource).join("-")}`:`crypto-${u||"unknown"}`,[m,l,u]),ye=a.useMemo(()=>i.createDedupedClickHandler(se,ae,{cooldownMs:200,deduplicationWindowMs:0}),[se,ae]),le=T==="loading",me=q||le||A||!!F,fe=le?b("ui.processing"):K,pe=a.useCallback(async()=>{try{U(!1),g&&await S(),j(null),$(!0)}catch(e){n.getLogger().error("Failed to change wallet:",e)}},[g,S,j]),we=a.useCallback(e=>{n.getLogger().debug("[CryptoButton] Wallet clicked:",e),$(!1),j(e),U(!0),n.getLogger().debug("[CryptoButton] Wallet selected, useEffect will auto-connect")},[j]),be=a.useCallback(async()=>{try{if(await S(),v(null),typeof window<"u"&&window.localStorage)try{window.localStorage.removeItem("walletName")}catch(e){e instanceof Error&&e.name==="QuotaExceededError"?n.getLogger().warn("localStorage quota exceeded when removing wallet preference"):n.getLogger().error("Failed to clear wallet preference from localStorage:",e)}}catch(e){n.getLogger().error("Failed to disconnect wallet:",e)}},[S]);return p.jsxs("div",{className:r.unstyled?L:`${r.className} cedros-theme__crypto-button ${L||""}`,style:r.unstyled?{}:r.style,children:[p.jsx("button",{onClick:ye,disabled:me,className:r.unstyled?L:"cedros-theme__button cedros-theme__crypto",type:"button",children:fe}),ne&&!k&&p.jsx("div",{className:"cedros-modal-overlay",style:{position:"fixed",top:0,left:0,right:0,bottom:0,backgroundColor:r.tokens.modalOverlay,display:"flex",alignItems:"center",justifyContent:"center",zIndex:9999,padding:"1rem"},onClick:()=>{$(!1),v(null)},children:p.jsxs("div",{className:"cedros-modal-content",style:{backgroundColor:r.tokens.modalBackground,borderRadius:"12px",padding:"2rem",maxWidth:"400px",width:"100%",boxShadow:"0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)",border:`1px solid ${r.tokens.modalBorder}`},onClick:e=>e.stopPropagation(),children:[p.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",marginBottom:"1.5rem"},children:[p.jsx("h3",{style:{margin:0,fontSize:"1.25rem",fontWeight:600,color:r.tokens.surfaceText},children:b("wallet.select_wallet")}),p.jsx("button",{onClick:()=>{$(!1),v(null)},style:i.getModalCloseButtonStyles(r.tokens.surfaceText),"aria-label":"Close modal",type:"button",children:"×"})]}),p.jsx("div",{style:{display:"flex",flexDirection:"column",gap:"0.75rem"},children:O.map(e=>p.jsxs("button",{onClick:()=>we(e.adapter.name),style:{width:"100%",padding:"1rem",backgroundColor:r.tokens.surfaceBackground,border:`1px solid ${r.tokens.surfaceBorder}`,borderRadius:"0.5rem",cursor:"pointer",fontSize:"1rem",textAlign:"left",color:r.tokens.surfaceText,display:"flex",alignItems:"center",gap:"1rem",transition:"all 0.2s ease"},onMouseEnter:t=>{t.currentTarget.style.backgroundColor=r.tokens.modalBackground,t.currentTarget.style.borderColor=r.tokens.surfaceText,t.currentTarget.style.transform="translateY(-2px)"},onMouseLeave:t=>{t.currentTarget.style.backgroundColor=r.tokens.surfaceBackground,t.currentTarget.style.borderColor=r.tokens.surfaceBorder,t.currentTarget.style.transform="translateY(0)"},type:"button",children:[p.jsx(he.WalletIcon,{wallet:e,style:{width:"24px",height:"24px"}}),p.jsx("span",{style:{fontWeight:500},children:e.adapter.name})]},e.adapter.name))})]})}),g&&!k&&!ne&&p.jsxs("div",{style:{display:"flex",justifyContent:"space-between",marginTop:"0.5rem",fontSize:"0.75rem",color:r.tokens.surfaceText,opacity:.7},children:[p.jsx("button",{onClick:pe,style:{background:"none",border:"none",padding:0,color:"inherit",textDecoration:"none",cursor:"pointer",fontSize:"inherit"},type:"button",children:b("wallet.change")}),p.jsx("button",{onClick:be,style:{background:"none",border:"none",padding:0,color:"inherit",textDecoration:"none",cursor:"pointer",fontSize:"inherit"},type:"button",children:b("ui.disconnect")})]}),!k&&J&&p.jsx("div",{className:r.unstyled?"":"cedros-theme__error",children:J}),!k&&H&&p.jsx("div",{className:r.unstyled?"":"cedros-theme__error",children:H}),!k&&c&&p.jsx("div",{className:r.unstyled?"":"cedros-theme__success",children:b("ui.payment_successful")})]})}const Ce=Object.freeze(Object.defineProperty({__proto__:null,CryptoButton:de},Symbol.toStringTag,{value:"Module"}));exports.CryptoButton=de;exports.CryptoButton$1=Ce;exports.useX402Payment=ue;
|
|
@@ -3,10 +3,9 @@ import { useState as K, useRef as R, useCallback as P, useMemo as Y, useEffect a
|
|
|
3
3
|
import { useWallet as be } from "@solana/wallet-adapter-react";
|
|
4
4
|
import { WalletReadyState as pe } from "@solana/wallet-adapter-base";
|
|
5
5
|
import { WalletIcon as Te } from "@solana/wallet-adapter-react-ui";
|
|
6
|
-
import { T as Ie, K as Ee, O as We, U as V, q as Re, n as fe, s as _e, o as ge, p as qe, r as we, t as Z, V as Me, W as ze } from "./styles-
|
|
7
|
-
import { u as he,
|
|
6
|
+
import { T as Ie, K as Ee, O as We, U as V, q as Re, n as fe, s as _e, o as ge, p as qe, r as we, t as Z, V as Me, W as ze } from "./styles-fihm6qVA.mjs";
|
|
7
|
+
import { u as he, m as ee, l as De } from "./CedrosContext-DQc_k5PG.mjs";
|
|
8
8
|
import { g as n } from "./fetchWithTimeout-DmMOwL0Q.mjs";
|
|
9
|
-
import { u as De } from "./ThemeContext-l0bqcOGW.mjs";
|
|
10
9
|
function $e() {
|
|
11
10
|
const { x402Manager: g, walletManager: s } = he(), { publicKey: _, signTransaction: q } = be(), [L, d] = K({
|
|
12
11
|
status: "idle",
|
|
@@ -533,12 +532,12 @@ function Fe({
|
|
|
533
532
|
!x && l && /* @__PURE__ */ h("div", { className: r.unstyled ? "" : "cedros-theme__success", children: f("ui.payment_successful") })
|
|
534
533
|
] });
|
|
535
534
|
}
|
|
536
|
-
const
|
|
535
|
+
const Qe = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
537
536
|
__proto__: null,
|
|
538
537
|
CryptoButton: Fe
|
|
539
538
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
540
539
|
export {
|
|
541
540
|
Fe as C,
|
|
542
|
-
|
|
541
|
+
Qe as a,
|
|
543
542
|
$e as u
|
|
544
543
|
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),n=require("react"),P=require("./plugin-Dw8_Q8rE.js"),T=require("./ErrorBanner-DxrRVqwe.js"),O=require("./dateHelpers-BKW_lGND.js");function W({serverUrl:y,apiKey:h,pageSize:r=20,authManager:x}){const[_,g]=n.useState([]),[k,C]=n.useState(!0),[q,l]=n.useState(null),[i,N]=n.useState(0),[A,p]=n.useState(!1),[v,S]=n.useState(!1),[o,w]=n.useState(null),[c,F]=n.useState(""),[a,d]=n.useState({email:"",name:"",phone:""}),m=n.useCallback(async(t,s)=>{if(x?.isAuthenticated())return x.fetchWithAuth(t,s);const E={"Content-Type":"application/json"};h&&(E["X-API-Key"]=h);const b=await fetch(`${y}${t}`,{...s,headers:{...E,...s?.headers}});if(!b.ok)throw new Error(`Request failed: ${b.status}`);return b.json()},[y,h,x]),f=n.useCallback(async()=>{C(!0),l(null);try{const t=await m(`/admin/customers?limit=${r}&offset=${i}`);g(t.customers??[])}catch{l("Failed to load customers"),g([])}finally{C(!1)}},[m,r,i]);n.useEffect(()=>{f()},[f]);const j=()=>{d({email:"",name:"",phone:""}),w(null),p(!1)},D=t=>{w(t),d({email:t.email,name:t.name??"",phone:t.phone??""}),p(!0)},I=async t=>{t.preventDefault(),S(!0),l(null);try{o?await m(`/admin/customers/${encodeURIComponent(o.id)}`,{method:"PUT",body:JSON.stringify({email:a.email,name:a.name||null,phone:a.phone||null,addresses:o.addresses})}):await m("/admin/customers",{method:"POST",body:JSON.stringify({email:a.email,name:a.name||null,phone:a.phone||null,addresses:[]})}),j(),f()}catch(s){l(s instanceof Error?s.message:"Failed to save customer")}finally{S(!1)}},u=c.trim()?_.filter(t=>{const s=c.toLowerCase();return t.email.toLowerCase().includes(s)||(t.name??"").toLowerCase().includes(s)||t.id.toLowerCase().includes(s)}):_,L=t=>[t.line1,t.city,t.state,t.postalCode,t.country].filter(Boolean).join(", ");return e.jsxs("div",{children:[e.jsxs("div",{className:"cedros-admin__section-header",children:[e.jsx("h3",{className:"cedros-admin__section-title",children:"Customers"}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--primary",onClick:()=>{j(),p(!0)},children:"+ Add Customer"})]}),e.jsx(T.ErrorBanner,{message:q}),e.jsx("div",{style:{marginBottom:"1rem",maxWidth:"400px"},children:e.jsx("input",{type:"text",className:"cedros-admin__input",placeholder:"Search by email, name, or ID...",value:c,onChange:t=>F(t.target.value),style:{fontSize:"0.85rem"}})}),A&&e.jsxs("form",{onSubmit:I,style:{border:"1px solid var(--cedros-admin-border, #e0e0e0)",borderRadius:"4px",padding:"1rem",marginBottom:"1.5rem",maxWidth:"500px"},children:[e.jsx("h4",{style:{margin:"0 0 0.75rem",fontSize:"0.9rem",fontWeight:600},children:o?"Edit Customer":"New Customer"}),e.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:"0.5rem"},children:[e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Email *"}),e.jsx("input",{type:"email",className:"cedros-admin__input",value:a.email,onChange:t=>d(s=>({...s,email:t.target.value})),required:!0,placeholder:"customer@example.com"})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Name"}),e.jsx("input",{type:"text",className:"cedros-admin__input",value:a.name,onChange:t=>d(s=>({...s,name:t.target.value})),placeholder:"Jane Doe"})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Phone"}),e.jsx("input",{type:"text",className:"cedros-admin__input",value:a.phone,onChange:t=>d(s=>({...s,phone:t.target.value})),placeholder:"+1 555 123 4567"})]})]}),e.jsxs("div",{style:{marginTop:"0.75rem",display:"flex",gap:"0.5rem"},children:[e.jsx("button",{type:"submit",className:"cedros-admin__button cedros-admin__button--primary",disabled:v,children:v?"Saving...":o?"Update":"Create"}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost",onClick:j,children:"Cancel"})]})]}),k?e.jsxs("div",{className:"cedros-admin__loading",children:[P.Icons.loading," Loading customers..."]}):u.length===0?e.jsx("div",{className:"cedros-admin__empty",children:c?"No matching customers.":"No customers found."}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Email"}),e.jsx("th",{children:"Name"}),e.jsx("th",{children:"Phone"}),e.jsx("th",{children:"Address"}),e.jsx("th",{children:"Created"}),e.jsx("th",{})]})}),e.jsx("tbody",{children:u.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:t.email}),e.jsx("td",{children:t.name??e.jsx("span",{style:{color:"var(--cedros-admin-text-muted, #888)"},children:"—"})}),e.jsx("td",{children:t.phone??e.jsx("span",{style:{color:"var(--cedros-admin-text-muted, #888)"},children:"—"})}),e.jsx("td",{style:{fontSize:"0.8rem",maxWidth:"200px",overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},children:t.addresses.length>0?L(t.addresses[0]):"—"}),e.jsx("td",{children:O.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",onClick:()=>D(t),children:"Edit"})})]},t.id))})]})}),e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",marginTop:"0.75rem",fontSize:"0.85rem"},children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:i===0,onClick:()=>N(Math.max(0,i-r)),children:"Previous"}),e.jsxs("span",{children:["Showing ",u.length," customer",u.length!==1?"s":""]}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:_.length<r,onClick:()=>N(i+r),children:"Next"})]})]})]})}exports.CustomersSection=W;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as s, jsx as t, Fragment as $ } from "react/jsx-runtime";
|
|
2
2
|
import { useState as o, useCallback as I, useEffect as O } from "react";
|
|
3
|
-
import { I as B } from "./
|
|
4
|
-
import { E as q } from "./ErrorBanner-
|
|
3
|
+
import { I as B } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as q } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as J } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
function G({ serverUrl: N, apiKey: p, pageSize: r = 20, authManager: f }) {
|
|
7
7
|
const [_, v] = o([]), [k, x] = o(!0), [D, m] = o(null), [i, w] = o(0), [L, b] = o(!1), [S, E] = o(!1), [d, A] = o(null), [c, j] = o(""), [a, l] = o({ email: "", name: "", phone: "" }), h = I(async (e, n) => {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),s=require("react"),k=require("./plugin-Dw8_Q8rE.js"),$=require("./ErrorBanner-DxrRVqwe.js"),g=require("./dateHelpers-BKW_lGND.js"),I=d=>{switch(d){case"won":return"success";case"lost":return"failed";case"needs_response":case"warning_needs_response":return"pending";default:return"muted"}},C=(d,i)=>`${i.toUpperCase()} ${(d/100).toFixed(2)}`;function F({serverUrl:d,apiKey:i,pageSize:a=20,authManager:x}){const[r,y]=s.useState([]),[W,b]=s.useState(!0),[D,l]=s.useState(null),[c,j]=s.useState(0),[o,U]=s.useState("all"),[h,p]=s.useState(null),[u,v]=s.useState(""),[S,N]=s.useState(!1),m=s.useCallback(async(t,n)=>{if(x?.isAuthenticated())return x.fetchWithAuth(t,n);const w={"Content-Type":"application/json"};i&&(w["X-API-Key"]=i);const f=await fetch(`${d}${t}`,{...n,headers:{...w,...n?.headers}});if(!f.ok)throw new Error(`Request failed: ${f.status}`);return f.json()},[d,i,x]),_=s.useCallback(async()=>{b(!0),l(null);try{const t=new URLSearchParams;t.set("limit",String(a)),t.set("offset",String(c)),o!=="all"&&t.set("status",o);const n=await m(`/admin/disputes?${t.toString()}`);y(n.disputes??[])}catch{l("Failed to load disputes"),y([])}finally{b(!1)}},[m,a,c,o]);s.useEffect(()=>{_()},[_]);const A=async t=>{try{const n=await m(`/admin/disputes/${encodeURIComponent(t)}`);p(n),v(n.status)}catch{l("Failed to load dispute details")}},R=async()=>{if(!(!h||!u.trim())){N(!0);try{const t=await m(`/admin/disputes/${encodeURIComponent(h.id)}/status`,{method:"PUT",body:JSON.stringify({status:u})});p(t),_()}catch{l("Failed to update dispute status")}finally{N(!1)}}};if(h){const t=h;return e.jsxs("div",{children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",onClick:()=>p(null),style:{marginBottom:"1rem"},children:"← Back to disputes"}),e.jsx("div",{className:"cedros-admin__section-header",children:e.jsxs("h3",{className:"cedros-admin__section-title",children:["Dispute ",e.jsx("code",{style:{fontSize:"0.8rem"},children:t.id.slice(0,12)})]})}),e.jsx("div",{className:"cedros-admin__table-container",style:{maxWidth:"500px"},children:e.jsx("table",{className:"cedros-admin__table",children:e.jsxs("tbody",{children:[e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600,width:"35%"},children:"Status"}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${I(t.status)}`,children:t.status})})]}),e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Amount"}),e.jsx("td",{children:C(t.amount,t.currency)})]}),e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Source"}),e.jsx("td",{children:t.source})]}),t.reason&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Reason"}),e.jsx("td",{children:t.reason})]}),t.orderId&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Order ID"}),e.jsx("td",{children:e.jsx("code",{children:t.orderId})})]}),t.chargeId&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Charge ID"}),e.jsx("td",{children:e.jsx("code",{children:t.chargeId})})]}),t.paymentIntentId&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Payment Intent"}),e.jsx("td",{children:e.jsx("code",{children:t.paymentIntentId})})]}),e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Created"}),e.jsx("td",{children:g.formatDateTime(t.createdAt)})]}),t.statusUpdatedAt&&e.jsxs("tr",{children:[e.jsx("td",{style:{fontWeight:600},children:"Status Updated"}),e.jsx("td",{children:g.formatDateTime(t.statusUpdatedAt)})]})]})})}),e.jsxs("div",{style:{marginTop:"1rem",display:"flex",gap:"0.5rem",alignItems:"flex-end",maxWidth:"400px"},children:[e.jsxs("div",{className:"cedros-admin__field",style:{flex:1},children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Update Status"}),e.jsxs("select",{className:"cedros-admin__input",value:u,onChange:n=>v(n.target.value),children:[e.jsx("option",{value:"needs_response",children:"Needs Response"}),e.jsx("option",{value:"under_review",children:"Under Review"}),e.jsx("option",{value:"won",children:"Won"}),e.jsx("option",{value:"lost",children:"Lost"}),e.jsx("option",{value:"warning_closed",children:"Warning Closed"})]})]}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--primary",onClick:R,disabled:S||u===t.status,children:S?"Updating...":"Update"})]})]})}return e.jsxs("div",{children:[e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Disputes & Chargebacks"})}),e.jsx($.ErrorBanner,{message:D}),e.jsx("div",{style:{display:"flex",gap:"0.5rem",marginBottom:"1rem",alignItems:"center"},children:e.jsxs("select",{className:"cedros-admin__input",value:o,onChange:t=>{U(t.target.value),j(0)},style:{width:"auto",fontSize:"0.85rem"},children:[e.jsx("option",{value:"all",children:"All statuses"}),e.jsx("option",{value:"needs_response",children:"Needs Response"}),e.jsx("option",{value:"under_review",children:"Under Review"}),e.jsx("option",{value:"won",children:"Won"}),e.jsx("option",{value:"lost",children:"Lost"})]})}),W?e.jsxs("div",{className:"cedros-admin__loading",children:[k.Icons.loading," Loading disputes..."]}):r.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No disputes found."}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"ID"}),e.jsx("th",{children:"Amount"}),e.jsx("th",{children:"Status"}),e.jsx("th",{children:"Reason"}),e.jsx("th",{children:"Source"}),e.jsx("th",{children:"Created"}),e.jsx("th",{})]})}),e.jsx("tbody",{children:r.map(t=>e.jsxs("tr",{children:[e.jsx("td",{children:e.jsx("code",{style:{fontSize:"0.75rem"},children:t.id.slice(0,12)})}),e.jsx("td",{children:C(t.amount,t.currency)}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${I(t.status)}`,children:t.status})}),e.jsx("td",{children:t.reason??"—"}),e.jsx("td",{children:t.source}),e.jsx("td",{children:g.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",onClick:()=>A(t.id),children:"View"})})]},t.id))})]})}),e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",marginTop:"0.75rem",fontSize:"0.85rem"},children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:c===0,onClick:()=>j(Math.max(0,c-a)),children:"Previous"}),e.jsxs("span",{children:["Showing ",r.length," dispute",r.length!==1?"s":""]}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:r.length<a,onClick:()=>j(c+a),children:"Next"})]})]})]})}exports.DisputesSection=F;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as n, jsx as e, Fragment as E } from "react/jsx-runtime";
|
|
2
2
|
import { useState as d, useCallback as x, useEffect as L } from "react";
|
|
3
|
-
import { I as j } from "./
|
|
4
|
-
import { E as B } from "./ErrorBanner-
|
|
3
|
+
import { I as j } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as B } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as v } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
const U = (i) => {
|
|
7
7
|
switch (i) {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { jsxs as a, jsx as r } from "react/jsx-runtime";
|
|
2
2
|
import { useState as v, useRef as b, useEffect as u } from "react";
|
|
3
|
-
import { I as _ } from "./
|
|
3
|
+
import { I as _ } from "./plugin-BIkt3boU.mjs";
|
|
4
4
|
function L({ value: s, onChange: f, options: i, placeholder: h = "Filter", disabled: t }) {
|
|
5
5
|
const [n, c] = v(!1), m = b(null), l = i.find((e) => e.value === s)?.label || h;
|
|
6
6
|
return u(() => {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const n=require("react/jsx-runtime"),c=require("react"),p=require("./plugin-Dw8_Q8rE.js");function v({value:r,onChange:_,options:l,placeholder:f="Filter",disabled:i}){const[s,a]=c.useState(!1),m=c.useRef(null),t=l.find(e=>e.value===r)?.label||f;return c.useEffect(()=>{const e=u=>{m.current&&!m.current.contains(u.target)&&a(!1)};if(s)return document.addEventListener("mousedown",e),()=>document.removeEventListener("mousedown",e)},[s]),c.useEffect(()=>{const e=u=>{u.key==="Escape"&&a(!1)};if(s)return document.addEventListener("keydown",e),()=>document.removeEventListener("keydown",e)},[s]),n.jsxs("div",{className:"cedros-admin__dropdown",ref:m,children:[n.jsxs("button",{type:"button",className:"cedros-admin__dropdown-trigger",onClick:()=>!i&&a(!s),"aria-expanded":s,"aria-haspopup":"listbox",disabled:i,children:[n.jsx("span",{children:t}),n.jsx("span",{className:`cedros-admin__dropdown-chevron ${s?"cedros-admin__dropdown-chevron--open":""}`,children:p.Icons.chevronDown})]}),s&&n.jsx("div",{className:"cedros-admin__dropdown-menu",role:"listbox",children:l.map(e=>n.jsxs("button",{type:"button",className:`cedros-admin__dropdown-item ${e.value===r?"cedros-admin__dropdown-item--selected":""}`,onClick:()=>{e.disabled||(_(e.value),a(!1))},role:"option","aria-selected":e.value===r,disabled:e.disabled,children:[e.label,e.value===r&&n.jsx("span",{className:"cedros-admin__dropdown-check",children:p.Icons.check})]},e.value))})]})}function b({value:r,onChange:_,options:l,label:f,description:i,disabled:s,className:a,style:m}){const[o,t]=c.useState(!1),e=c.useRef(null),h=l.find(d=>d.value===r)?.label||"Select...";return c.useEffect(()=>{const d=w=>{e.current&&!e.current.contains(w.target)&&t(!1)};if(o)return document.addEventListener("mousedown",d),()=>document.removeEventListener("mousedown",d)},[o]),c.useEffect(()=>{const d=w=>{w.key==="Escape"&&t(!1)};if(o)return document.addEventListener("keydown",d),()=>document.removeEventListener("keydown",d)},[o]),n.jsxs("div",{className:`cedros-admin__field ${a||""}`,style:m,children:[n.jsx("label",{className:"cedros-admin__field-label",children:f}),n.jsxs("div",{className:"cedros-admin__dropdown cedros-admin__dropdown--form",ref:e,children:[n.jsxs("button",{type:"button",className:"cedros-admin__dropdown-trigger cedros-admin__dropdown-trigger--form",onClick:()=>!s&&t(!o),"aria-expanded":o,"aria-haspopup":"listbox",disabled:s,children:[n.jsx("span",{children:h}),n.jsx("span",{className:`cedros-admin__dropdown-chevron ${o?"cedros-admin__dropdown-chevron--open":""}`,children:p.Icons.chevronDown})]}),o&&n.jsx("div",{className:"cedros-admin__dropdown-menu cedros-admin__dropdown-menu--form",role:"listbox",children:l.map(d=>n.jsxs("button",{type:"button",className:`cedros-admin__dropdown-item ${d.value===r?"cedros-admin__dropdown-item--selected":""}`,onClick:()=>{d.disabled||(_(d.value),t(!1))},role:"option","aria-selected":d.value===r,disabled:d.disabled,children:[d.label,d.value===r&&n.jsx("span",{className:"cedros-admin__dropdown-check",children:p.Icons.check})]},d.value))})]}),i&&n.jsx("p",{className:"cedros-admin__field-description",children:i})]})}exports.FilterDropdown=v;exports.FormDropdown=b;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { jsxs as e, jsx as o } from "react/jsx-runtime";
|
|
2
|
-
import { I as s } from "./
|
|
2
|
+
import { I as s } from "./plugin-BIkt3boU.mjs";
|
|
3
3
|
function i({ message: r, onRetry: n }) {
|
|
4
4
|
return r ? /* @__PURE__ */ e("div", { className: "cedros-admin__error-banner", children: [
|
|
5
5
|
/* @__PURE__ */ o("span", { children: r }),
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const r=require("react/jsx-runtime"),s=require("./plugin-Dw8_Q8rE.js");function i({message:n,onRetry:e}){return n?r.jsxs("div",{className:"cedros-admin__error-banner",children:[r.jsx("span",{children:n}),e&&r.jsxs("button",{type:"button",className:"cedros-admin__error-banner-retry",onClick:e,children:[s.Icons.refresh," Retry"]})]}):null}exports.ErrorBanner=i;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),c=require("react"),r=require("./plugin-Dw8_Q8rE.js"),R=require("./ErrorBanner-DxrRVqwe.js"),U=require("./StatsBar-DDUWoizP.js");function V({serverUrl:h,apiKey:d,pageSize:g=20,authManager:o}){const[u,N]=c.useState([]),[Q,w]=c.useState(!0),[S,f]=c.useState(!1),[p,A]=c.useState(null),[F,C]=c.useState(!1),[x,P]=c.useState(""),[v,O]=c.useState("all"),[q,b]=c.useState(null),[E,j]=c.useState(null),[n,l]=c.useState({question:"",answer:"",keywordsCsv:"",active:!0,useInChat:!0,displayOnPage:!0}),_=c.useCallback(async()=>{w(!0);try{j(null);let s;const t=`/admin/faqs?limit=${g}`;if(o?.isAuthenticated())s=await o.fetchWithAuth(t);else{const i={"Content-Type":"application/json"};d&&(i["X-API-Key"]=d);const a=await fetch(`${h}${t}`,{headers:i});if(!a.ok)throw new Error(`Failed to fetch FAQs: ${a.status}`);s=await a.json()}N(s.faqs||[])}catch{N([]),j("Failed to load FAQs")}finally{w(!1)}},[h,d,g,o]);c.useEffect(()=>{_()},[_]);const $=async s=>{if(s.preventDefault(),!(!n.question.trim()||!n.answer.trim())){C(!0);try{const t=n.keywordsCsv.split(",").map(a=>a.trim().toLowerCase()).filter(Boolean),i={question:n.question.trim(),answer:n.answer.trim(),keywords:t,active:n.active,useInChat:n.useInChat,displayOnPage:n.displayOnPage};if(p){const a=`/admin/faqs/${p.id}`;if(o?.isAuthenticated())await o.fetchWithAuth(a,{method:"PUT",body:JSON.stringify(i)});else{const m={"Content-Type":"application/json"};d&&(m["X-API-Key"]=d);const I=await fetch(`${h}${a}`,{method:"PUT",headers:m,body:JSON.stringify(i)});if(!I.ok)throw new Error(`Failed to update FAQ: ${I.status}`)}}else if(o?.isAuthenticated())await o.fetchWithAuth("/admin/faqs",{method:"POST",body:JSON.stringify(i)});else{const a={"Content-Type":"application/json"};d&&(a["X-API-Key"]=d);const m=await fetch(`${h}/admin/faqs`,{method:"POST",headers:a,body:JSON.stringify(i)});if(!m.ok)throw new Error(`Failed to create FAQ: ${m.status}`)}y(),_()}catch{j(p?"Failed to update FAQ":"Failed to create FAQ")}finally{C(!1)}}},T=async s=>{try{const t=`/admin/faqs/${s}`;if(o?.isAuthenticated())await o.fetchWithAuth(t,{method:"DELETE"});else{const i={"Content-Type":"application/json"};d&&(i["X-API-Key"]=d);const a=await fetch(`${h}${t}`,{method:"DELETE",headers:i});if(!a.ok)throw new Error(`Failed to delete FAQ: ${a.status}`)}_()}catch{j("Failed to delete FAQ")}b(null)},D=async s=>{try{const t=`/admin/faqs/${s.id}`,i={...s,active:!s.active};if(o?.isAuthenticated())await o.fetchWithAuth(t,{method:"PUT",body:JSON.stringify(i)});else{const a={"Content-Type":"application/json"};d&&(a["X-API-Key"]=d);const m=await fetch(`${h}${t}`,{method:"PUT",headers:a,body:JSON.stringify(i)});if(!m.ok)throw new Error(`Failed to update FAQ: ${m.status}`)}_()}catch{j("Failed to update FAQ status")}},y=()=>{l({question:"",answer:"",keywordsCsv:"",active:!0,useInChat:!0,displayOnPage:!0}),A(null),f(!1)},L=s=>{l({question:s.question,answer:s.answer,keywordsCsv:s.keywords.join(", "),active:s.active,useInChat:s.useInChat??!0,displayOnPage:s.displayOnPage??!0}),A(s),f(!0)},B=u.length,W=u.filter(s=>s.active).length,J=u.filter(s=>s.active&&s.useInChat).length,X=u.filter(s=>s.active&&s.displayOnPage).length,k=c.useMemo(()=>u.filter(s=>{if(v==="active"&&!s.active||v==="inactive"&&s.active)return!1;if(x){const t=x.toLowerCase();return s.question.toLowerCase().includes(t)||s.answer.toLowerCase().includes(t)||s.keywords.some(i=>i.includes(t))}return!0}),[u,v,x]);return e.jsxs("div",{className:"cedros-admin__faqs",children:[e.jsx(R.ErrorBanner,{message:E,onRetry:_}),e.jsx(U.StatsBar,{stats:[{label:"Total FAQs",value:B},{label:"Active",value:W,variant:"success"},{label:"In Chat",value:J},{label:"On Page",value:X}]}),e.jsxs("div",{className:"cedros-admin__section",children:[e.jsxs("div",{className:"cedros-admin__section-header",children:[e.jsxs("div",{className:"cedros-admin__section-header-left",children:[e.jsx("h3",{className:"cedros-admin__section-title",children:"Knowledge Base"}),e.jsx("p",{className:"cedros-admin__section-subtitle",children:"Manage FAQs for the AI chat assistant and public FAQ page."})]}),e.jsx("div",{className:"cedros-admin__section-header-right",children:e.jsxs("button",{className:"cedros-admin__button cedros-admin__button--primary",onClick:()=>{y(),f(!0)},children:[r.Icons.plus," Add FAQ"]})})]}),e.jsxs("div",{className:"cedros-admin__filters",style:{display:"flex",gap:"1rem",marginBottom:"1rem"},children:[e.jsx("input",{type:"text",placeholder:"Search FAQs...",value:x,onChange:s=>P(s.target.value),className:"cedros-admin__input",style:{flex:1,maxWidth:300}}),e.jsxs("select",{value:v,onChange:s=>O(s.target.value),className:"cedros-admin__select",children:[e.jsx("option",{value:"all",children:"All Status"}),e.jsx("option",{value:"active",children:"Active Only"}),e.jsx("option",{value:"inactive",children:"Inactive Only"})]})]}),S&&e.jsx("div",{className:"cedros-admin__form-container",style:{marginBottom:"1.5rem"},children:e.jsxs("form",{onSubmit:$,className:"cedros-admin__form",children:[e.jsxs("div",{className:"cedros-admin__form-header",children:[e.jsx("h4",{children:p?"Edit FAQ":"Add New FAQ"}),e.jsx("button",{type:"button",className:"cedros-admin__button--icon",onClick:y,children:r.Icons.close})]}),e.jsxs("div",{className:"cedros-admin__form-group",children:[e.jsx("label",{className:"cedros-admin__label",children:"Question *"}),e.jsx("input",{type:"text",value:n.question,onChange:s=>l(t=>({...t,question:s.target.value})),className:"cedros-admin__input",placeholder:"What is your return policy?",required:!0})]}),e.jsxs("div",{className:"cedros-admin__form-group",children:[e.jsx("label",{className:"cedros-admin__label",children:"Answer *"}),e.jsx("textarea",{value:n.answer,onChange:s=>l(t=>({...t,answer:s.target.value})),className:"cedros-admin__textarea",placeholder:"We accept returns within 30 days...",rows:4,required:!0}),e.jsx("span",{className:"cedros-admin__hint",children:"Supports markdown formatting."})]}),e.jsxs("div",{className:"cedros-admin__form-group",children:[e.jsx("label",{className:"cedros-admin__label",children:"Keywords"}),e.jsx("input",{type:"text",value:n.keywordsCsv,onChange:s=>l(t=>({...t,keywordsCsv:s.target.value})),className:"cedros-admin__input",placeholder:"returns, refund, policy"}),e.jsx("span",{className:"cedros-admin__hint",children:"Comma-separated keywords to help AI find this FAQ."})]}),e.jsxs("div",{className:"cedros-admin__form-group",children:[e.jsxs("label",{className:"cedros-admin__checkbox-label",children:[e.jsx("input",{type:"checkbox",checked:n.active,onChange:s=>l(t=>({...t,active:s.target.checked}))}),e.jsx("span",{children:"Active"})]}),e.jsx("span",{className:"cedros-admin__hint",children:"Inactive FAQs won't appear anywhere."})]}),e.jsxs("div",{className:"cedros-admin__form-group",children:[e.jsx("label",{className:"cedros-admin__label",children:"Visibility"}),e.jsxs("div",{className:"cedros-admin__checkbox-group",children:[e.jsxs("label",{className:"cedros-admin__checkbox-label",children:[e.jsx("input",{type:"checkbox",checked:n.useInChat,onChange:s=>l(t=>({...t,useInChat:s.target.checked}))}),e.jsx("span",{children:"Use in AI Chat"})]}),e.jsxs("label",{className:"cedros-admin__checkbox-label",children:[e.jsx("input",{type:"checkbox",checked:n.displayOnPage,onChange:s=>l(t=>({...t,displayOnPage:s.target.checked}))}),e.jsx("span",{children:"Display on FAQ Page"})]})]}),e.jsx("span",{className:"cedros-admin__hint",children:"Choose where this FAQ should appear."})]}),e.jsxs("div",{className:"cedros-admin__form-actions",children:[e.jsx("button",{type:"button",className:"cedros-admin__button",onClick:y,children:"Cancel"}),e.jsx("button",{type:"submit",className:"cedros-admin__button cedros-admin__button--primary",disabled:F||!n.question.trim()||!n.answer.trim(),children:F?r.Icons.loading:p?"Update FAQ":"Create FAQ"})]})]})}),Q?e.jsxs("div",{className:"cedros-admin__loading",children:[r.Icons.loading,e.jsx("span",{children:"Loading FAQs..."})]}):k.length===0?e.jsx("div",{className:"cedros-admin__empty",children:e.jsx("p",{children:x||v!=="all"?"No FAQs match your filters.":"No FAQs yet. Add one to get started."})}):e.jsx("div",{className:"cedros-admin__faq-list",children:k.map(s=>e.jsxs("div",{className:`cedros-admin__faq-item ${s.active?"":"cedros-admin__faq-item--inactive"}`,children:[e.jsxs("div",{className:"cedros-admin__faq-content",children:[e.jsxs("div",{className:"cedros-admin__faq-question",children:[e.jsx("span",{className:`cedros-admin__status-dot ${s.active?"cedros-admin__status-dot--active":"cedros-admin__status-dot--inactive"}`}),s.question]}),e.jsx("div",{className:"cedros-admin__faq-answer",children:s.answer}),e.jsxs("div",{className:"cedros-admin__faq-meta",children:[s.keywords.length>0&&e.jsx("div",{className:"cedros-admin__faq-keywords",children:s.keywords.map(t=>e.jsx("span",{className:"cedros-admin__tag",children:t},t))}),e.jsxs("div",{className:"cedros-admin__faq-visibility",children:[s.useInChat&&e.jsxs("span",{className:"cedros-admin__badge cedros-admin__badge--chat",title:"Used in AI Chat",children:[r.Icons.chat," Chat"]}),s.displayOnPage&&e.jsxs("span",{className:"cedros-admin__badge cedros-admin__badge--page",title:"Displayed on FAQ Page",children:[r.Icons.globe," Page"]})]})]})]}),e.jsxs("div",{className:"cedros-admin__faq-actions",children:[e.jsx("button",{className:"cedros-admin__button--icon",onClick:()=>D(s),title:s.active?"Deactivate":"Activate",children:s.active?r.Icons.eyeOff:r.Icons.eye}),e.jsx("button",{className:"cedros-admin__button--icon",onClick:()=>L(s),title:"Edit",children:r.Icons.edit}),e.jsx("button",{className:"cedros-admin__button--icon cedros-admin__btn--danger",onClick:()=>b(s.id),title:"Delete",children:r.Icons.trash})]}),q===s.id&&e.jsx("div",{className:"cedros-admin__confirm-overlay",children:e.jsxs("div",{className:"cedros-admin__confirm-dialog",children:[e.jsx("p",{children:"Delete this FAQ?"}),e.jsxs("div",{className:"cedros-admin__confirm-actions",children:[e.jsx("button",{className:"cedros-admin__button",onClick:()=>b(null),children:"Cancel"}),e.jsx("button",{className:"cedros-admin__button cedros-admin__button--danger",onClick:()=>T(s.id),children:"Delete"})]})]})})]},s.id))})]})]})}exports.FAQSection=V;
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { jsxs as a, jsx as t } from "react/jsx-runtime";
|
|
2
2
|
import { useState as r, useCallback as R, useEffect as V, useMemo as G } from "react";
|
|
3
|
-
import { I as l } from "./
|
|
4
|
-
import { E as H } from "./ErrorBanner-
|
|
5
|
-
import { S as Y } from "./StatsBar-
|
|
3
|
+
import { I as l } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as H } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
|
+
import { S as Y } from "./StatsBar-CwCBHBn-.mjs";
|
|
6
6
|
function te({ serverUrl: u, apiKey: d, pageSize: A = 20, authManager: o }) {
|
|
7
7
|
const [_, F] = r([]), [S, C] = r(!0), [E, N] = r(!1), [v, k] = r(null), [Q, I] = r(!1), [y, $] = r(""), [f, x] = r("all"), [q, w] = r(null), [T, b] = r(null), [n, m] = r({
|
|
8
8
|
question: "",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as l, jsx as t, Fragment as R } from "react/jsx-runtime";
|
|
2
2
|
import { useState as h, useRef as j, useCallback as U } from "react";
|
|
3
|
-
import { I as u } from "./
|
|
4
|
-
import { E as z } from "./ErrorBanner-
|
|
3
|
+
import { I as u } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as z } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as B } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
import { g as I } from "./fetchWithTimeout-DmMOwL0Q.mjs";
|
|
7
7
|
async function W(r, n, i, c) {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),i=require("react"),h=require("./plugin-Dw8_Q8rE.js"),A=require("./ErrorBanner-DxrRVqwe.js"),O=require("./dateHelpers-BKW_lGND.js"),v=require("./fetchWithTimeout-CG0EKbhf.js");async function R(s,l,n,c){const o=new FormData;if(o.append("file",c),n?.isAuthenticated())return n.fetchWithAuth("/admin/images/upload",{method:"POST",body:o,headers:{}});const r={};l&&(r["X-API-Key"]=l);const d=await fetch(`${s}/admin/images/upload`,{method:"POST",headers:r,body:o});if(!d.ok)throw new Error(`Upload failed: ${d.status}`);return d.json()}async function F(s,l,n,c){const o=JSON.stringify({url:c});if(n?.isAuthenticated()){await n.fetchWithAuth("/admin/images",{method:"DELETE",body:o});return}const r={"Content-Type":"application/json"};l&&(r["X-API-Key"]=l);const d=await fetch(`${s}/admin/images`,{method:"DELETE",headers:r,body:o});if(!d.ok)throw new Error(`Delete failed: ${d.status}`)}function z({serverUrl:s,apiKey:l,authManager:n}){const[c,o]=i.useState([]),[r,d]=i.useState(!1),[x,j]=i.useState(null),[D,m]=i.useState(null),[_,S]=i.useState(null),[p,f]=i.useState(!1),[u,g]=i.useState(null),b=i.useRef(null),w=i.useCallback(async t=>{d(!0),m(null);try{const a=await R(s,l,n,t);o(y=>[{url:a.url,thumbUrl:a.thumbUrl,uploadedAt:new Date().toISOString()},...y]),g(null),b.current&&(b.current.value="")}catch(a){v.getLogger().error("[ImagesSection] Upload failed:",a,{serverUrl:s.slice(0,20)+"..."}),m("Upload failed. Check file type and try again.")}finally{d(!1)}},[s,l,n]),C=t=>{const a=t.target.files?.[0]??null;g(a),m(null)},I=()=>{u&&w(u)},U=t=>{t.preventDefault(),f(!0)},N=()=>f(!1),k=t=>{t.preventDefault(),f(!1);const a=t.dataTransfer.files?.[0];a&&a.type.startsWith("image/")?(g(a),m(null)):a&&m("Only image files are accepted.")},T=i.useCallback(async t=>{j(t),m(null);try{await F(s,l,n,t),o(a=>a.filter(y=>y.url!==t))}catch(a){v.getLogger().error("[ImagesSection] Delete failed:",a,{serverUrl:s.slice(0,20)+"..."}),m("Failed to delete image.")}finally{j(null)}},[s,l,n]),E=async t=>{try{await navigator.clipboard.writeText(t),S(t),setTimeout(()=>S(null),2e3)}catch{m("Could not copy to clipboard.")}},L=["cedros-admin__drop-zone",p?"cedros-admin__drop-zone--active":""].filter(Boolean).join(" ");return e.jsxs("div",{className:"cedros-admin__page",children:[e.jsx(A.ErrorBanner,{message:D}),e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Image Upload"})}),e.jsxs("div",{className:L,onDragOver:U,onDragLeave:N,onDrop:k,role:"region","aria-label":"Image drop zone",style:{border:"2px dashed",borderColor:p?"var(--cedros-accent, #6366f1)":"var(--cedros-border, #e2e8f0)",borderRadius:"0.5rem",padding:"1.5rem",textAlign:"center",marginBottom:"1rem",transition:"border-color 0.15s",backgroundColor:p?"var(--cedros-accent-subtle, rgba(99,102,241,0.06))":void 0},children:[e.jsx("p",{style:{marginBottom:"0.75rem",fontSize:"0.9rem",opacity:.7},children:"Drag and drop an image here, or select a file below"}),e.jsxs("div",{style:{display:"flex",gap:"0.5rem",justifyContent:"center",alignItems:"center",flexWrap:"wrap"},children:[e.jsx("input",{ref:b,id:"cedros-image-file-input",type:"file",accept:"image/*",className:"cedros-admin__input",style:{maxWidth:260},onChange:C,"aria-label":"Select image file"}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--primary",onClick:I,disabled:!u||r,"aria-busy":r,children:r?e.jsxs(e.Fragment,{children:[h.Icons.loading," Uploading..."]}):"Upload"})]}),u&&!r&&e.jsxs("p",{style:{marginTop:"0.5rem",fontSize:"0.8rem",opacity:.65},children:["Selected: ",u.name," (",(u.size/1024).toFixed(1)," KB)"]})]}),e.jsx("div",{className:"cedros-admin__section-header",children:e.jsxs("h3",{className:"cedros-admin__section-title",children:["Uploaded This Session",c.length>0&&e.jsx("span",{className:"cedros-admin__section-badge",style:{marginLeft:"0.5rem"},children:c.length})]})}),c.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No images uploaded yet."}):e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Preview"}),e.jsx("th",{children:"URL"}),e.jsx("th",{children:"Uploaded"}),e.jsx("th",{children:"Actions"})]})}),e.jsx("tbody",{children:c.map(t=>e.jsxs("tr",{children:[e.jsx("td",{style:{width:72},children:e.jsx("img",{src:t.thumbUrl,alt:"Thumbnail preview",style:{width:56,height:56,objectFit:"cover",borderRadius:"0.25rem",display:"block"}})}),e.jsx("td",{style:{maxWidth:320,wordBreak:"break-all"},children:e.jsx("code",{style:{fontSize:"0.8rem"},children:t.url})}),e.jsx("td",{style:{whiteSpace:"nowrap"},children:O.formatDateTime(t.uploadedAt)}),e.jsx("td",{children:e.jsxs("div",{style:{display:"flex",gap:"0.4rem"},children:[e.jsxs("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost",onClick:()=>E(t.url),"aria-label":"Copy URL to clipboard",title:"Copy URL",children:[_===t.url?h.Icons.check:h.Icons.eye,_===t.url?"Copied":"Copy URL"]}),e.jsxs("button",{type:"button",className:"cedros-admin__button cedros-admin__button--destructive",onClick:()=>T(t.url),disabled:x===t.url,"aria-label":"Delete image",title:"Delete",children:[x===t.url?h.Icons.loading:h.Icons.trash,"Delete"]})]})})]},t.url))})]})})]})}exports.ImagesSection=z;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as n, jsx as t, Fragment as P } from "react/jsx-runtime";
|
|
2
2
|
import { useState as o, useCallback as S, useEffect as w } from "react";
|
|
3
|
-
import { I as j } from "./
|
|
4
|
-
import { E as R } from "./ErrorBanner-
|
|
3
|
+
import { I as j } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as R } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as T } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
import { g as E } from "./fetchWithTimeout-DmMOwL0Q.mjs";
|
|
7
7
|
const a = 50;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),s=require("react"),b=require("./plugin-Dw8_Q8rE.js"),L=require("./ErrorBanner-DxrRVqwe.js"),B=require("./dateHelpers-BKW_lGND.js"),S=require("./fetchWithTimeout-CG0EKbhf.js"),c=50;function k({serverUrl:o,apiKey:m,authManager:h}){const[y,N]=s.useState([]),[A,_]=s.useState(!0),[P,g]=s.useState(null),[d,w]=s.useState(""),[i,j]=s.useState([]),[E,p]=s.useState(!1),[I,f]=s.useState(null),[a,x]=s.useState(0),l=s.useCallback(async t=>{if(h?.isAuthenticated())return h.fetchWithAuth(t);const n={"Content-Type":"application/json"};m&&(n["X-API-Key"]=m);const r=await fetch(`${o}${t}`,{headers:n});if(!r.ok)throw new Error(`Request failed: ${r.status}`);return r.json()},[o,m,h]);s.useEffect(()=>{let t=!1;return _(!0),g(null),l("/admin/products?limit=100&offset=0").then(n=>{if(t)return;const r=Array.isArray(n)?n:n.products??[];N(r)}).catch(n=>{t||(S.getLogger().error("[InventorySection] Failed to load products:",n,{serverUrl:o.slice(0,20)+"..."}),g("Failed to load products"))}).finally(()=>{t||_(!1)}),()=>{t=!0}},[l,o]);const v=s.useCallback(async(t,n)=>{if(t){p(!0),f(null);try{const r=`/admin/products/${encodeURIComponent(t)}/inventory/adjustments?limit=${c}&offset=${n}`,F=await l(r);j(F.adjustments??[])}catch(r){S.getLogger().error("[InventorySection] Failed to load adjustments:",r,{productId:t,serverUrl:o.slice(0,20)+"..."}),f("Failed to load inventory adjustments"),j([])}finally{p(!1)}}},[l,o]);s.useEffect(()=>{d&&v(d,a)},[v,d,a]);const C=t=>{w(t),x(0),j([]),f(null)},q=()=>x(t=>Math.max(0,t-c)),$=()=>x(t=>t+c),u=y.find(t=>t.id===d);return e.jsxs("div",{className:"cedros-admin__page",children:[e.jsx(L.ErrorBanner,{message:P??I}),e.jsx("div",{className:"cedros-admin__section-header",children:e.jsx("h3",{className:"cedros-admin__section-title",children:"Inventory Adjustments"})}),e.jsx("div",{className:"cedros-admin__add-form",style:{marginBottom:"1rem"},children:e.jsx("div",{className:"cedros-admin__form-row",children:e.jsxs("div",{className:"cedros-admin__field",style:{flex:1},children:[e.jsx("label",{htmlFor:"inventory-product-select",className:"cedros-admin__field-label",children:"Select Product"}),A?e.jsxs("div",{className:"cedros-admin__loading",children:[b.Icons.loading," Loading products..."]}):e.jsxs("select",{id:"inventory-product-select",className:"cedros-admin__input",value:d,onChange:t=>C(t.target.value),"aria-label":"Select product to view inventory adjustments",children:[e.jsx("option",{value:"",children:"-- Choose a product --"}),y.map(t=>e.jsx("option",{value:t.id,children:t.title??t.description??t.id},t.id))]})]})})}),d?E?e.jsxs("div",{className:"cedros-admin__loading",children:[b.Icons.loading," Loading adjustments..."]}):e.jsxs(e.Fragment,{children:[u&&e.jsxs("p",{style:{marginBottom:"0.75rem",fontSize:"0.9rem",opacity:.7},children:["Showing adjustments for: ",e.jsx("strong",{children:u.title??u.description??u.id})]}),i.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No inventory adjustments found."}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"cedros-admin__table-container",children:e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Date"}),e.jsx("th",{children:"Delta"}),e.jsx("th",{children:"Before"}),e.jsx("th",{children:"After"}),e.jsx("th",{children:"Reason"}),e.jsx("th",{children:"Actor"})]})}),e.jsx("tbody",{children:i.map(t=>e.jsxs("tr",{children:[e.jsx("td",{style:{whiteSpace:"nowrap"},children:B.formatDateTime(t.createdAt)}),e.jsx("td",{children:e.jsx("span",{style:{fontWeight:600,color:t.delta>0?"var(--cedros-success, #16a34a)":t.delta<0?"var(--cedros-danger, #dc2626)":void 0},"aria-label":`Delta: ${t.delta>0?"plus":""}${t.delta}`,children:t.delta>0?`+${t.delta}`:t.delta})}),e.jsx("td",{children:t.quantityBefore}),e.jsx("td",{children:t.quantityAfter}),e.jsx("td",{children:t.reason??e.jsx("span",{style:{opacity:.45},children:"—"})}),e.jsx("td",{children:t.actor??e.jsx("span",{style:{opacity:.45},children:"—"})})]},t.id))})]})}),e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center",marginTop:"0.75rem",fontSize:"0.85rem"},children:[e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:a===0,onClick:q,children:"Previous"}),e.jsxs("span",{children:["Page ",Math.floor(a/c)+1," · ",i.length," record",i.length!==1?"s":""]}),e.jsx("button",{type:"button",className:"cedros-admin__button cedros-admin__button--ghost cedros-admin__button--sm",disabled:i.length<c,onClick:$,children:"Next"})]})]})]}):e.jsx("div",{className:"cedros-admin__empty",children:"Select a product to view its inventory adjustments."})]})}exports.InventorySection=k;
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { jsxs as i, jsx as e, Fragment as R } from "react/jsx-runtime";
|
|
2
2
|
import { useState as _, useCallback as k, useEffect as U } from "react";
|
|
3
|
-
import { I as $ } from "./
|
|
4
|
-
import { E as q } from "./ErrorBanner-
|
|
3
|
+
import { I as $ } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as q } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { T as C } from "./Toggle-DAxIdpY4.mjs";
|
|
6
6
|
import { u as F } from "./useAutosave-YwMqRzqy.mjs";
|
|
7
|
-
import { A as j } from "./AutosaveIndicator-
|
|
7
|
+
import { A as j } from "./AutosaveIndicator-D966vOrP.mjs";
|
|
8
8
|
const u = {
|
|
9
9
|
mailgun: { label: "Mailgun", host: "smtp.mailgun.org", username: "", credentialLabel: "SMTP Password", showUsername: !0, usernameEqualsPassword: !1 },
|
|
10
10
|
sendgrid: { label: "SendGrid", host: "smtp.sendgrid.net", username: "apikey", credentialLabel: "API Key", showUsername: !1, usernameEqualsPassword: !1 },
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),l=require("react"),q=require("./plugin-Dw8_Q8rE.js"),M=require("./ErrorBanner-DxrRVqwe.js"),y=require("./Toggle-CsPSF8Dr.js"),z=require("./useAutosave-B2p6iwh8.js"),R=require("./AutosaveIndicator-CJdkhZis.js"),p={mailgun:{label:"Mailgun",host:"smtp.mailgun.org",username:"",credentialLabel:"SMTP Password",showUsername:!0,usernameEqualsPassword:!1},sendgrid:{label:"SendGrid",host:"smtp.sendgrid.net",username:"apikey",credentialLabel:"API Key",showUsername:!1,usernameEqualsPassword:!1},postmark:{label:"Postmark",host:"smtp.postmarkapp.com",username:"",credentialLabel:"Server API Token",showUsername:!1,usernameEqualsPassword:!0},ses:{label:"AWS SES",host:"email-smtp.us-east-1.amazonaws.com",username:"",credentialLabel:"SMTP Password",showUsername:!0,usernameEqualsPassword:!1},resend:{label:"Resend",host:"smtp.resend.com",username:"resend",credentialLabel:"API Key",showUsername:!1,usernameEqualsPassword:!1},custom:{label:"Custom SMTP",host:"",username:"",credentialLabel:"SMTP Password",showUsername:!0,usernameEqualsPassword:!1}};function W(c){if(!c)return"custom";for(const[d,n]of Object.entries(p))if(n.host&&c===n.host)return d;return"custom"}const v={email_enabled:!1,email_provider:"custom",smtp_host:"",smtp_port:587,smtp_username:"",smtp_password:"",from_email:"",from_name:"",webhook_enabled:!1,webhook_url:"",webhook_secret:"",webhook_timeout:30};function U({serverUrl:c,apiKey:d,authManager:n}){const[m,b]=l.useState("messages"),[a,h]=l.useState(v),[S,N]=l.useState(!0),[k,C]=l.useState(!0),[E,f]=l.useState(null),[_,j]=l.useState(new Set),g=l.useCallback(async()=>{try{f(null);let s;const t="/admin/config/messaging";if(n?.isAuthenticated())s=await n.fetchWithAuth(t);else{const o={"Content-Type":"application/json"};d&&(o["X-API-Key"]=d);const u=await fetch(`${c}${t}`,{headers:o});if(!u.ok)throw new Error(`Failed to fetch: ${u.status}`);s=await u.json()}const i={...v,...s.config};i.email_provider||(i.email_provider=W(i.smtp_host)),h(i)}catch{h(v),f("Could not load saved settings. Showing defaults.")}finally{N(!1),setTimeout(()=>C(!1),100)}},[c,d,n]);l.useEffect(()=>{g()},[g]);const P=l.useCallback(async s=>{const t="/admin/config/messaging",i={...s};_.has("smtp_password")||delete i.smtp_password,_.has("webhook_secret")||delete i.webhook_secret;const o=JSON.stringify({config:i});try{if(n?.isAuthenticated())await n.fetchWithAuth(t,{method:"PUT",body:o});else{const u={"Content-Type":"application/json"};d&&(u["X-API-Key"]=d);const w=await fetch(`${c}${t}`,{method:"PUT",headers:u,body:o});if(!w.ok)throw new Error(`Failed to save: ${w.status}`)}}catch{throw f("Failed to save messaging settings"),new Error("Save failed")}},[c,d,n,_]),{status:T,error:A}=z.useAutosave({data:a,onSave:P,debounceMs:1500,enabled:!k}),r=(s,t)=>{(s==="smtp_password"||s==="webhook_secret")&&j(i=>new Set(i).add(s)),h(i=>({...i,[s]:t}))},I=s=>{const t=p[s];h(i=>({...i,email_provider:s,smtp_host:t.host||i.smtp_host,smtp_port:587,smtp_username:t.username||(t.showUsername?i.smtp_username:"")}))},L=s=>{const t=a.email_provider||"custom",i=p[t];j(o=>new Set(o).add("smtp_password")),i.usernameEqualsPassword?h(o=>({...o,smtp_password:s,smtp_username:s})):h(o=>({...o,smtp_password:s}))},x=p[a.email_provider||"custom"]??p.custom;return S?e.jsxs("div",{className:"cedros-admin__messaging-settings",children:[e.jsxs("div",{className:"cedros-admin__page-header",children:[e.jsx("h2",{className:"cedros-admin__page-title",children:"Store Messages"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Configure email delivery and webhook notifications."})]}),e.jsxs("div",{className:"cedros-admin__loading",style:{marginTop:"1rem"},children:[q.Icons.loading," Loading message settings..."]})]}):e.jsxs("div",{className:"cedros-admin__messaging-settings",children:[e.jsxs("div",{className:"cedros-admin__page-header",children:[e.jsx("h2",{className:"cedros-admin__page-title",children:"Store Messages"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Configure email delivery and webhook notifications."})]}),e.jsxs("div",{className:"cedros-admin__tabs cedros-admin__tabs--line",children:[e.jsx("button",{type:"button",className:`cedros-admin__tab ${m==="messages"?"cedros-admin__tab--active":""}`,onClick:()=>b("messages"),children:"Messages"}),e.jsx("button",{type:"button",className:`cedros-admin__tab ${m==="email"?"cedros-admin__tab--active":""}`,onClick:()=>b("email"),children:"Email"}),e.jsx("button",{type:"button",className:`cedros-admin__tab ${m==="webhooks"?"cedros-admin__tab--active":""}`,onClick:()=>b("webhooks"),children:"Webhooks"}),e.jsx("div",{style:{flex:1}}),e.jsx(R.AutosaveIndicator,{status:T,error:A})]}),e.jsx(M.ErrorBanner,{message:E,onRetry:g}),e.jsxs("div",{className:"cedros-admin__tab-content",style:{marginTop:"1rem"},children:[m==="messages"&&e.jsxs("div",{className:"cedros-admin__section",children:[e.jsx("p",{style:{marginBottom:"1.5rem",fontSize:"0.875rem",opacity:.7},children:"Enable or disable notification types. Configure the delivery settings in the Email or Webhooks tab."}),e.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:"1rem"},children:[e.jsxs("div",{style:{display:"flex",alignItems:"flex-start",gap:"1rem",padding:"1rem",border:"1px solid var(--cedros-admin-border, #e5e5e5)",borderRadius:"0.5rem"},children:[e.jsx(y.Toggle,{checked:a.email_enabled,onChange:s=>r("email_enabled",s)}),e.jsxs("div",{style:{flex:1},children:[e.jsx("div",{style:{fontWeight:500},children:"Email Confirmation"}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.8125rem",opacity:.6},children:"Send order confirmation emails to customers after successful purchase."}),e.jsx("p",{style:{margin:"0.5rem 0 0",fontSize:"0.75rem",opacity:.5},children:"Requires Email configuration"})]})]}),e.jsxs("div",{style:{display:"flex",alignItems:"flex-start",gap:"1rem",padding:"1rem",border:"1px solid var(--cedros-admin-border, #e5e5e5)",borderRadius:"0.5rem"},children:[e.jsx(y.Toggle,{checked:a.webhook_enabled,onChange:s=>r("webhook_enabled",s)}),e.jsxs("div",{style:{flex:1},children:[e.jsx("div",{style:{fontWeight:500},children:"Admin Purchase Notification"}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.8125rem",opacity:.6},children:"Send webhook notifications to your server when a purchase is completed."}),e.jsx("p",{style:{margin:"0.5rem 0 0",fontSize:"0.75rem",opacity:.5},children:"Requires Webhook configuration"})]})]})]})]}),m==="email"&&e.jsxs("div",{className:"cedros-admin__section",children:[e.jsx("p",{style:{marginBottom:"1.5rem",fontSize:"0.875rem",opacity:.7},children:"Select your email service provider for automatic configuration."}),!a.email_enabled&&e.jsx("div",{style:{padding:"1rem",marginBottom:"1.5rem",background:"var(--cedros-admin-bg-accent, #fef3c7)",borderRadius:"0.5rem",border:"1px solid var(--cedros-admin-warning, #f59e0b)",fontSize:"0.875rem"},children:"Email notifications are disabled. Enable them in the Messages tab."}),e.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:"1rem",opacity:a.email_enabled?1:.5},children:[e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Email Provider"}),e.jsx("select",{className:"cedros-admin__input",value:a.email_provider||"custom",onChange:s=>I(s.target.value),disabled:!a.email_enabled,children:Object.entries(p).map(([s,{label:t}])=>e.jsx("option",{value:s,children:t},s))})]}),a.email_provider==="custom"&&e.jsxs(e.Fragment,{children:[e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"SMTP Host"}),e.jsx("input",{type:"text",className:"cedros-admin__input",value:a.smtp_host,onChange:s=>r("smtp_host",s.target.value),placeholder:"smtp.example.com",disabled:!a.email_enabled})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"SMTP Port"}),e.jsx("input",{type:"number",className:"cedros-admin__input",value:a.smtp_port,onChange:s=>r("smtp_port",parseInt(s.target.value)||587),placeholder:"587",disabled:!a.email_enabled,style:{maxWidth:120}}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.75rem",opacity:.6},children:"Common: 587 (TLS), 465 (SSL), 25 (unencrypted)."})]})]}),x.showUsername&&e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"SMTP Username"}),e.jsx("input",{type:"text",className:"cedros-admin__input",value:a.smtp_username,onChange:s=>r("smtp_username",s.target.value),placeholder:a.email_provider==="mailgun"?"postmaster@your-domain.com":"username",disabled:!a.email_enabled})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:x.credentialLabel}),e.jsx("input",{type:"password",className:"cedros-admin__input",value:_.has("smtp_password")?a.smtp_password:"",onChange:s=>L(s.target.value),placeholder:a.smtp_password?"••••••••":`Enter ${x.credentialLabel.toLowerCase()}`,disabled:!a.email_enabled})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"From Email"}),e.jsx("input",{type:"email",className:"cedros-admin__input",value:a.from_email,onChange:s=>r("from_email",s.target.value),placeholder:"noreply@example.com",disabled:!a.email_enabled}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.75rem",opacity:.6},children:"Default sender email address."})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"From Name"}),e.jsx("input",{type:"text",className:"cedros-admin__input",value:a.from_name,onChange:s=>r("from_name",s.target.value),placeholder:"Your Store",disabled:!a.email_enabled}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.75rem",opacity:.6},children:"Default sender display name."})]})]})]}),m==="webhooks"&&e.jsxs("div",{className:"cedros-admin__section",children:[e.jsx("p",{style:{marginBottom:"1.5rem",fontSize:"0.875rem",opacity:.7},children:"Configure webhook endpoint for receiving purchase notifications."}),!a.webhook_enabled&&e.jsx("div",{style:{padding:"1rem",marginBottom:"1.5rem",background:"var(--cedros-admin-bg-accent, #fef3c7)",borderRadius:"0.5rem",border:"1px solid var(--cedros-admin-warning, #f59e0b)",fontSize:"0.875rem"},children:"Webhook notifications are disabled. Enable them in the Messages tab."}),e.jsxs("div",{style:{display:"flex",flexDirection:"column",gap:"1rem",opacity:a.webhook_enabled?1:.5},children:[e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Webhook URL"}),e.jsx("input",{type:"url",className:"cedros-admin__input",value:a.webhook_url,onChange:s=>r("webhook_url",s.target.value),placeholder:"https://api.yoursite.com/webhooks/orders",disabled:!a.webhook_enabled})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Webhook Secret"}),e.jsx("input",{type:"password",className:"cedros-admin__input",value:_.has("webhook_secret")?a.webhook_secret:"",onChange:s=>r("webhook_secret",s.target.value),placeholder:a.webhook_secret?"••••••••":"Enter secret for HMAC-SHA256",disabled:!a.webhook_enabled}),e.jsx("p",{style:{margin:"0.25rem 0 0",fontSize:"0.75rem",opacity:.6},children:"Used for HMAC-SHA256 signature verification"})]}),e.jsxs("div",{className:"cedros-admin__field",children:[e.jsx("label",{className:"cedros-admin__field-label",children:"Timeout (seconds)"}),e.jsx("input",{type:"number",className:"cedros-admin__input",value:a.webhook_timeout,onChange:s=>r("webhook_timeout",parseInt(s.target.value)||30),placeholder:"30",disabled:!a.webhook_enabled,style:{maxWidth:120}})]})]})]})]})]})}exports.MessagingSection=U;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),a=require("react"),A=require("./plugin-Dw8_Q8rE.js"),B=require("./ErrorBanner-DxrRVqwe.js"),k=require("./dateHelpers-BKW_lGND.js"),C=require("./safeHref-DyHIpVjY.js");function P({serverUrl:n,apiKey:r,pageSize:o=20,authManager:d}){const[l,s]=a.useState([]),[c,f]=a.useState(0),[L,y]=a.useState(!0),[v,b]=a.useState(null),[u,S]=a.useState(null),[R,p]=a.useState(null),[$,_]=a.useState([]),[F,N]=a.useState(!1),[x,O]=a.useState(""),h=a.useCallback(async(t,i)=>{if(d?.isAuthenticated())return d.fetchWithAuth(t,i);const g={"Content-Type":"application/json"};r&&(g["X-API-Key"]=r);const m=await fetch(`${n}${t}`,{...i,headers:{...g,...i?.headers}});if(!m.ok){const I=await m.text().catch(()=>`HTTP ${m.status}`);throw new Error(I)}return m.json()},[n,r,d]),j=a.useCallback(async()=>{y(!0);try{b(null);const t=new URLSearchParams({limit:String(o)});x&&t.set("status",x);const i=await h(`/admin/orders?${t}`);s(i.orders),f(i.total)}catch{b("Failed to load orders")}finally{y(!1)}},[h,o,x]);a.useEffect(()=>{j()},[j]);const T=a.useCallback(async t=>{N(!0);try{const[i,g]=await Promise.all([h(`/admin/orders/${encodeURIComponent(t)}`),h("/admin/gift-card-redemptions?limit=50").catch(()=>[])]);p(i),_(g.filter(m=>m.orderId===t))}catch{p(null),_([])}finally{N(!1)}},[h]),D=t=>{u===t?(S(null),p(null),_([])):(S(t),T(t))},E=(t,i)=>i==="USD"||i==="usd"?`$${(t/100).toFixed(2)}`:`${t} ${i}`;return e.jsxs("div",{className:"cedros-admin__section",children:[e.jsxs("div",{className:"cedros-admin__section-header",children:[e.jsx("h2",{className:"cedros-admin__section-title",children:"Orders"}),e.jsxs("div",{style:{display:"flex",gap:"0.5rem",alignItems:"center"},children:[e.jsxs("select",{className:"cedros-admin__input",style:{width:"auto",minWidth:"120px"},value:x,onChange:t=>O(t.target.value),children:[e.jsx("option",{value:"",children:"All statuses"}),e.jsx("option",{value:"paid",children:"Paid"}),e.jsx("option",{value:"processing",children:"Processing"}),e.jsx("option",{value:"fulfilled",children:"Fulfilled"}),e.jsx("option",{value:"shipped",children:"Shipped"}),e.jsx("option",{value:"delivered",children:"Delivered"}),e.jsx("option",{value:"cancelled",children:"Cancelled"}),e.jsx("option",{value:"refunded",children:"Refunded"})]}),e.jsxs("button",{type:"button",className:"cedros-admin__button cedros-admin__button--secondary",onClick:j,children:[A.Icons.refresh," Refresh"]})]})]}),v?e.jsx(B.ErrorBanner,{message:v,onRetry:j}):null,L?e.jsx("div",{className:"cedros-admin__loading-text",children:"Loading orders..."}):l.length===0?e.jsx("div",{className:"cedros-admin__empty",children:"No orders found."}):e.jsxs(e.Fragment,{children:[e.jsxs("div",{className:"cedros-admin__table-info",children:[c," order",c===1?"":"s"," total"]}),e.jsxs("table",{className:"cedros-admin__table",children:[e.jsx("thead",{children:e.jsxs("tr",{children:[e.jsx("th",{children:"Order"}),e.jsx("th",{children:"Status"}),e.jsx("th",{children:"Amount"}),e.jsx("th",{children:"Source"}),e.jsx("th",{children:"Customer"}),e.jsx("th",{children:"Date"})]})}),e.jsx("tbody",{children:l.map(t=>e.jsx(q,{order:t,expanded:u===t.id,detail:u===t.id?R:null,redemptions:u===t.id?$:[],detailLoading:u===t.id&&F,onToggle:()=>D(t.id),formatAmount:E},t.id))})]})]})]})}function q({order:n,expanded:r,detail:o,redemptions:d,detailLoading:l,onToggle:s,formatAmount:c}){const f=n.metadata?.recipient_email||d.length>0;return e.jsxs(e.Fragment,{children:[e.jsxs("tr",{onClick:s,style:{cursor:"pointer"},className:r?"cedros-admin__table-row--active":"",children:[e.jsxs("td",{children:[e.jsxs("span",{className:"cedros-admin__mono",children:[n.id.slice(0,12),"..."]}),f?e.jsx("span",{className:"cedros-admin__badge cedros-admin__badge--info",style:{marginLeft:"0.5rem"},children:"Gift Card"}):null]}),e.jsx("td",{children:e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${w(n.status)}`,children:n.status})}),e.jsx("td",{children:c(n.amount,n.amountAsset)}),e.jsx("td",{children:n.source}),e.jsx("td",{children:n.customerEmail||n.customerName||"—"}),e.jsx("td",{children:k.formatDateTime(n.createdAt)})]}),r?e.jsx("tr",{children:e.jsx("td",{colSpan:6,style:{padding:0},children:e.jsx(H,{detail:o,redemptions:d,loading:l,formatAmount:c,metadata:n.metadata})})}):null]})}function H({detail:n,redemptions:r,loading:o,formatAmount:d,metadata:l}){return o?e.jsx("div",{style:{padding:"1rem"},className:"cedros-admin__loading-text",children:"Loading details..."}):e.jsxs("div",{style:{padding:"1rem",background:"var(--cedros-admin-bg-muted, #f9fafb)"},children:[Object.keys(l).length>0?e.jsxs("div",{style:{marginBottom:"1rem"},children:[e.jsx("div",{className:"cedros-admin__label",children:"Order Metadata"}),e.jsx("div",{style:{display:"grid",gridTemplateColumns:"auto 1fr",gap:"0.25rem 1rem",fontSize:"0.8125rem"},children:Object.entries(l).map(([s,c])=>e.jsxs("div",{style:{display:"contents"},children:[e.jsx("span",{style:{fontWeight:500,color:"var(--cedros-admin-text-muted)"},children:s}),e.jsx("span",{children:c})]},s))})]}):null,r.length>0?e.jsxs("div",{style:{marginBottom:"1rem"},children:[e.jsx("div",{className:"cedros-admin__label",children:"Gift Card Fulfillment"}),r.map(s=>e.jsxs("div",{style:{fontSize:"0.8125rem",padding:"0.5rem",border:"1px solid var(--cedros-admin-border)",borderRadius:"0.5rem",marginBottom:"0.5rem"},children:[e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"center"},children:[e.jsxs("span",{children:["Face value: ",d(s.faceValueCents,s.currency)]}),e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${s.creditsIssued>0?"success":"warning"}`,children:s.creditsIssued>0?"Credits issued":"Pending"})]}),e.jsxs("div",{style:{marginTop:"0.25rem",color:"var(--cedros-admin-text-muted)"},children:["Recipient: ",s.recipientUserId||"—",s.tokenMinted?e.jsx("span",{className:"cedros-admin__badge cedros-admin__badge--info",style:{marginLeft:"0.5rem"},children:"Token minted"}):null]})]},s.id))]}):null,n?.fulfillments&&n.fulfillments.length>0?e.jsxs("div",{style:{marginBottom:"1rem"},children:[e.jsx("div",{className:"cedros-admin__label",children:"Fulfillments"}),n.fulfillments.map(s=>e.jsxs("div",{style:{fontSize:"0.8125rem",marginBottom:"0.25rem"},children:[e.jsx("span",{className:`cedros-admin__badge cedros-admin__badge--${w(s.status)}`,children:s.status}),s.carrier?e.jsx("span",{style:{marginLeft:"0.5rem"},children:s.carrier}):null,s.trackingNumber?C.safeHref(s.trackingUrl)?e.jsx("a",{href:C.safeHref(s.trackingUrl),target:"_blank",rel:"noreferrer",style:{marginLeft:"0.5rem"},children:s.trackingNumber}):e.jsx("span",{style:{marginLeft:"0.5rem"},children:s.trackingNumber}):null]},s.id))]}):null,n?.history&&n.history.length>0?e.jsxs("div",{children:[e.jsx("div",{className:"cedros-admin__label",children:"Status History"}),n.history.map(s=>e.jsxs("div",{style:{fontSize:"0.8125rem",marginBottom:"0.25rem"},children:[e.jsx("span",{style:{color:"var(--cedros-admin-text-muted)"},children:k.formatDateTime(s.createdAt)})," ",s.fromStatus," → ",s.toStatus,s.note?e.jsx("span",{style:{marginLeft:"0.5rem",fontStyle:"italic"},children:s.note}):null]},s.id))]}):null]})}function w(n){switch(n){case"paid":case"fulfilled":case"delivered":case"success":return"success";case"processing":case"shipped":case"pending":return"warning";case"cancelled":case"refunded":case"failed":return"error";default:return"default"}}exports.OrdersSection=P;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsxs as i, jsx as e, Fragment as $ } from "react/jsx-runtime";
|
|
2
2
|
import { useState as s, useCallback as N, useEffect as U } from "react";
|
|
3
|
-
import { I as z } from "./
|
|
4
|
-
import { E as G } from "./ErrorBanner-
|
|
3
|
+
import { I as z } from "./plugin-BIkt3boU.mjs";
|
|
4
|
+
import { E as G } from "./ErrorBanner-DAjYj6Dx.mjs";
|
|
5
5
|
import { f as F } from "./dateHelpers-yvPkofYQ.mjs";
|
|
6
6
|
import { s as k } from "./safeHref-DqJPLPl5.mjs";
|
|
7
7
|
function Y({ serverUrl: a, apiKey: r, pageSize: m = 20, authManager: l }) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),u=require("react"),L=require("./SingleCategorySettings-g7D-9lG1.js"),F=require("./configApi-BS5UJfzm.js"),W=require("./ErrorBanner-CAgPnj62.js"),q=require("./StatsBar-CWXw2ZT3.js"),O="https://github.com/conorholds/cedros-pay/tree/main/ui/docs/cross-channel-setup.md";function M({title:t,description:i,steps:n}){return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.75rem",padding:"1rem",background:"var(--cedros-admin-surface, #ffffff)"},children:[e.jsx("div",{style:{fontWeight:700,marginBottom:"0.35rem"},children:t}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.9rem",marginBottom:"0.75rem",lineHeight:1.5},children:i}),e.jsx("ol",{style:{margin:0,paddingLeft:"1.1rem",lineHeight:1.6,fontSize:"0.9rem"},children:n.map(o=>e.jsx("li",{children:o},o))})]})}function R({children:t}){return e.jsx("code",{style:{display:"block",padding:"0.65rem 0.75rem",background:"rgba(15, 23, 42, 0.04)",borderRadius:"0.5rem",marginTop:"0.5rem",wordBreak:"break-all"},children:t})}function z({serverUrl:t}){const i=`${t.replace(/\/$/,"")}/webhook/stripe`,n=`${t.replace(/\/$/,"")}/paywall/v1/native-store/apple/notifications`,o=`${t.replace(/\/$/,"")}/paywall/v1/native-store/google/notifications`,r=[{title:"Stripe Web Checkout",description:"Use this for website payments and any mobile redirect Checkout flows. Cedros owns the checkout session creation, but Stripe still needs your API keys and webhook endpoint configured.",steps:["Add your Stripe publishable key, secret key, and webhook signing secret in Payment Options → Stripe.","Create a Stripe webhook endpoint that sends subscription and checkout events to the Cedros webhook URL shown below.","If your app uses custom deep links for Stripe redirects, add the scheme in Stripe → allowed redirect schemes."]},{title:"Apple App Store Billing",description:"Use this for digital goods and subscriptions distributed through the Apple App Store. Cedros verifies purchases and handles server notifications, but you still need to create App Store Connect products and credentials.",steps:["In Products, map each store-managed product to its Apple product ID and choose the correct store-managed kind.","In Payment Options → App Stores, enter your App Store Server API issuer ID, key ID, private key, and bundle ID.","Create the matching products and subscriptions in App Store Connect, then point App Store Server Notifications at the Cedros Apple notification URL.","If you rely on reader, US external purchase link, or similar exceptions, configure those policies in the app build and only after Apple approves the relevant entitlement."]},{title:"Google Play Billing",description:"Use this for digital goods and subscriptions distributed through Google Play. Cedros verifies purchases, acknowledges them server-side, and processes RTDNs, but you still need Play Console catalog and service-account setup.",steps:["In Products, map each Play product ID and, for subscriptions, the package name, base plan ID, and optional offer ID.","In Payment Options → App Stores, enter your Google Play service-account email, private key, package name, push service-account email, and push audience.","Create the matching one-time products or subscriptions in Google Play Console and point RTDN delivery at the Cedros Google notification URL.","If you participate in User Choice Billing, Alternative Billing Only, or External Offers programs, configure those policies explicitly in the app build only for approved storefronts."]}];return e.jsxs("div",{style:{display:"grid",gap:"1rem",marginBottom:"1rem"},children:[e.jsxs("div",{style:{padding:"1rem",borderRadius:"0.75rem",background:"var(--cedros-admin-subtle, rgba(15, 23, 42, 0.03))",border:"1px solid var(--cedros-admin-border, #e5e7eb)"},children:[e.jsx("div",{style:{fontWeight:700,marginBottom:"0.4rem"},children:"Turnkey setup path"}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",lineHeight:1.6,fontSize:"0.9rem"},children:"Create the product once in Cedros, configure each payment channel here, then point Stripe, App Store Connect, and Google Play Console at the Cedros endpoints below. Cedros packages can then load the same product catalog and apply the right rail at runtime."}),e.jsx(R,{children:i}),e.jsx(R,{children:n}),e.jsx(R,{children:o}),e.jsx("div",{style:{marginTop:"0.5rem",color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.8rem",lineHeight:1.5},children:"Store notifications must target a tenant-specific Cedros deployment URL. If your deployment injects tenant context via domain, path prefix, or headers, use that tenant-scoped URL here instead of a generic shared endpoint."}),e.jsx("a",{href:O,target:"_blank",rel:"noopener noreferrer",style:{display:"inline-block",marginTop:"0.75rem",fontSize:"0.85rem",fontWeight:600,textDecoration:"underline",color:"inherit"},children:"Open the full cross-channel setup guide"})]}),e.jsx("div",{style:{display:"grid",gap:"1rem",gridTemplateColumns:"repeat(auto-fit, minmax(260px, 1fr))"},children:r.map(a=>e.jsx(M,{...a},a.title))})]})}function p(t){return typeof t=="string"&&t.trim().length>0}function G(t){switch(t){case"complete":return"Complete";case"manual":return"Manual check";case"incomplete":default:return"Needs setup"}}function N(t){switch(t){case"complete":return{background:"rgba(34, 197, 94, 0.12)",color:"#166534",border:"rgba(34, 197, 94, 0.24)"};case"manual":return{background:"rgba(245, 158, 11, 0.12)",color:"#92400e",border:"rgba(245, 158, 11, 0.24)"};case"incomplete":default:return{background:"rgba(239, 68, 68, 0.12)",color:"#991b1b",border:"rgba(239, 68, 68, 0.24)"}}}function U(t){const i=t.metadata?.store_policy_fulfillment_type;if(i==="digital_in_app"||i==="physical_goods"||i==="real_world_service"||i==="reader_content"||i==="other")return i;switch(t.fulfillment?.type){case"shipping":return"physical_goods";case"service":return"real_world_service";case"digital_download":return"digital_in_app";default:return}}function H(t){let i=0,n=0,o=0,r=0,a=0;return t.forEach(d=>{if(U(d)!=="digital_in_app")return;i+=1;const s=d.storeBilling,x=!!s?.apple?.productId,y=!!s?.google?.productId,b=s?.kind==="auto_renewable_subscription"&&y,k=!!s?.google?.basePlanId;x&&y&&(!b||k)&&(n+=1),x||(o+=1),y||(r+=1),b&&!k&&(a+=1)}),{digitalCount:i,fullyMappedCount:n,missingAppleCount:o,missingGoogleCount:r,missingBasePlanCount:a}}function V(t){return t.some(i=>i.status==="incomplete")?"incomplete":t.some(i=>i.status==="manual")?"manual":"complete"}async function Q(t){const{serverUrl:i,apiKey:n,authManager:o}=t;if(o?.isAuthenticated())return(await o.fetchWithAuth("/admin/products?limit=500")).products??[];const r={"Content-Type":"application/json"};n&&(r["X-API-Key"]=n);const a=await fetch(`${i.replace(/\/$/,"")}/admin/products?limit=500`,{headers:r});if(!a.ok)throw new Error(`Failed to fetch products (${a.status})`);return(await a.json()).products??[]}function X({section:t}){const i=V(t.items),n=N(i);return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.75rem",padding:"1rem",background:"var(--cedros-admin-surface, #ffffff)"},children:[e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"flex-start",gap:"1rem",marginBottom:"0.5rem"},children:[e.jsxs("div",{children:[e.jsx("div",{style:{fontWeight:700},children:t.title}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.9rem",lineHeight:1.5},children:t.description})]}),e.jsx("span",{style:{background:n.background,color:n.color,border:`1px solid ${n.border}`,borderRadius:"999px",padding:"0.2rem 0.6rem",fontSize:"0.78rem",fontWeight:600,whiteSpace:"nowrap"},children:G(i)})]}),e.jsx("div",{style:{display:"grid",gap:"0.65rem",marginTop:"0.85rem"},children:t.items.map(o=>{const r=N(o.status);return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.65rem",padding:"0.8rem",background:"rgba(15, 23, 42, 0.015)"},children:[e.jsxs("div",{style:{display:"flex",alignItems:"center",justifyContent:"space-between",gap:"1rem",marginBottom:"0.35rem"},children:[e.jsx("div",{style:{fontWeight:600},children:o.title}),e.jsx("span",{style:{background:r.background,color:r.color,border:`1px solid ${r.border}`,borderRadius:"999px",padding:"0.15rem 0.5rem",fontSize:"0.75rem",fontWeight:600,whiteSpace:"nowrap"},children:G(o.status)})]}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.88rem",lineHeight:1.5},children:o.detail})]},`${t.title}-${o.title}`)})})]})}function J({serverUrl:t,apiKey:i,authManager:n}){const o=u.useMemo(()=>new F.ConfigApiClient(t,void 0,n),[t,n]),[r,a]=u.useState([]),[d,A]=u.useState({}),[s,x]=u.useState({}),[y,b]=u.useState(!0),[k,D]=u.useState(null),[B,E]=u.useState(0);u.useEffect(()=>{let l=!1;return(async()=>{b(!0),D(null);try{const[g,m,C]=await Promise.all([o.getConfig("stripe",!0),o.getConfig("native_store",!0),Q({serverUrl:t,apiKey:i,authManager:n})]);if(l)return;A(g.config??{}),x(m.config??{}),a(C)}catch(g){if(l)return;D(g instanceof Error?g.message:"Failed to load payment readiness data")}finally{l||b(!1)}})(),()=>{l=!0}},[i,n,o,B,t]);const v=u.useMemo(()=>{const l=p(d.secret_key)&&p(d.publishable_key),S=p(d.webhook_secret),g=s.apple_enabled===!0,m=g&&p(s.apple_issuer_id)&&p(s.apple_key_id)&&p(s.apple_private_key)&&p(s.apple_bundle_id),C=s.google_enabled===!0,h=C&&p(s.google_service_account_email)&&p(s.google_private_key)&&p(s.google_package_name)&&p(s.google_push_service_account_email)&&p(s.google_push_audience),{digitalCount:c,fullyMappedCount:P,missingAppleCount:j,missingGoogleCount:w,missingBasePlanCount:_}=H(r),$=[{title:"Website / Stripe",description:"Web checkout and browser-based mobile Stripe flows rely on your Stripe keys and webhook wiring.",items:[{title:"Stripe API keys",status:l?"complete":"incomplete",detail:l?"Publishable and secret keys are configured in Cedros.":"Add both the Stripe publishable key and secret key in Payment Options → Stripe."},{title:"Stripe webhook signing secret",status:S?"complete":"incomplete",detail:S?"Cedros has a webhook signing secret configured.":"Add the Stripe webhook signing secret so Cedros can trust subscription and checkout lifecycle events."},{title:"Stripe dashboard webhook endpoint",status:l&&S?"manual":"incomplete",detail:l&&S?`Confirm Stripe sends events to ${t.replace(/\/$/,"")}/webhook/stripe and that test events succeed.`:"Finish the Stripe config above, then create the webhook in Stripe Dashboard and point it at Cedros."}]},{title:"Apple App Store",description:"Apple digital goods require App Store billing plus matching App Store Connect catalog and server credentials.",items:[{title:"Apple native-store credentials",status:m?"complete":"incomplete",detail:m?"Issuer ID, key ID, private key, and bundle ID are configured.":g?"Apple billing is enabled, but Cedros is still missing one or more App Store Server API credentials.":"Enable Apple App Store billing and add the App Store Server API credentials in Payment Options → App Stores."},{title:"Apple product mapping",status:c===0?"manual":j===0?"complete":"incomplete",detail:c===0?"No digital in-app products are classified yet. Create or classify a digital product before shipping on the App Store.":j===0?`All ${c} digital in-app products have an Apple product ID.`:`${j} of ${c} digital in-app products still need an Apple product ID.`},{title:"App Store Connect server notifications",status:m?"manual":"incomplete",detail:m?`Confirm App Store Server Notifications point to ${t.replace(/\/$/,"")}/paywall/v1/native-store/apple/notifications using your tenant-scoped Cedros URL.`:"Finish the Apple credentials first, then configure App Store Server Notifications in App Store Connect."}]},{title:"Google Play",description:"Google digital goods require Play Billing plus Play Console product mapping, service-account access, and RTDN wiring.",items:[{title:"Google Play API and RTDN credentials",status:h?"complete":"incomplete",detail:h?"Service account, package name, RTDN push identity, and audience are configured.":C?"Google Play billing is enabled, but Cedros is still missing one or more API or RTDN verification fields.":"Enable Google Play billing and add the Android Publisher / RTDN credentials in Payment Options → App Stores."},{title:"Google product and base-plan mapping",status:c===0?"manual":w===0&&_===0?"complete":"incomplete",detail:c===0?"No digital in-app products are classified yet. Create or classify a digital product before shipping on Google Play.":w===0&&_===0?`All ${c} digital in-app products have a Google Play mapping${_===0?"":" and required base plans"}.`:`${w} products still need a Google product ID and ${_} subscription products still need a base plan ID.`},{title:"Play Console RTDN delivery",status:h?"manual":"incomplete",detail:h?`Confirm Real-time developer notifications are configured to reach ${t.replace(/\/$/,"")}/paywall/v1/native-store/google/notifications through your approved Pub/Sub push identity.`:"Finish the Google Play credentials first, then configure RTDN delivery in Google Play Console and Google Cloud Pub/Sub."}]},{title:"Cedros product catalog",description:"Cedros packages can only route correctly when the catalog itself is classified and mapped cleanly.",items:[{title:"Products created in Cedros",status:r.length>0?"complete":"incomplete",detail:r.length>0?`${r.length} products are present in the Cedros catalog.`:"Create at least one product in Admin → Products."},{title:"Digital product app-store mapping coverage",status:c===0?"manual":P===c?"complete":"incomplete",detail:c===0?"No digital in-app products are currently classified. If you sell only physical goods or real-world services, this is expected.":`${P} of ${c} digital in-app products currently have both Apple/Google mapping requirements satisfied.`},{title:"Manual end-to-end store test purchases",status:l||m||h?"manual":"incomplete",detail:l||m||h?"Run at least one website purchase, one App Store sandbox purchase, and one Google Play test purchase before shipping.":"Finish the payment channel setup first, then run real test purchases through every channel you plan to support."}]}];return{sections:$,stats:{products:r.length,digitalProducts:c,fullyMappedProducts:P,autoVerifiedChecks:$.flatMap(I=>I.items).filter(I=>I.status==="complete").length}}},[s,r,t,d]);return e.jsxs("div",{style:{marginBottom:"1rem"},children:[e.jsxs("div",{className:"cedros-admin__page-header",style:{marginBottom:"1rem"},children:[e.jsx("h3",{className:"cedros-admin__page-title",children:"Readiness Checklist"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Cedros can verify configuration and product mapping automatically, but external console wiring and test purchases still require a human check."})]}),e.jsx(W.ErrorBanner,{message:k,onRetry:()=>{E(l=>l+1)}}),e.jsx(q.StatsBar,{stats:[{label:"Products",value:v.stats.products},{label:"Digital App Products",value:v.stats.digitalProducts},{label:"Fully Mapped",value:v.stats.fullyMappedProducts},{label:"Auto-Verified Checks",value:v.stats.autoVerifiedChecks}],isLoading:y}),e.jsx("div",{style:{display:"grid",gap:"1rem",gridTemplateColumns:"repeat(auto-fit, minmax(280px, 1fr))",marginTop:"1rem"},children:v.sections.map(l=>e.jsx(X,{section:l},l.title))})]})}function f({href:t,children:i}){return e.jsx("a",{href:t,target:"_blank",rel:"noopener noreferrer",style:{color:"inherit",textDecoration:"underline"},children:i})}const T=[{id:"app_stores",label:"App Stores",category:"native_store",description:e.jsx(e.Fragment,{children:"Configure Apple App Store and Google Play verification, lifecycle notifications, and server credentials. Use the setup guide below to connect App Store Connect and Google Play Console to Cedros."})},{id:"stripe",label:"Stripe",category:"stripe",description:e.jsxs(e.Fragment,{children:["Configure your Stripe integration for card payments. Get your API keys from the"," ",e.jsx(f,{href:"https://dashboard.stripe.com/apikeys",children:"Stripe Dashboard"}),"."]})},{id:"crypto",label:"Crypto",category:"x402",description:e.jsxs(e.Fragment,{children:["Configure Solana wallet and token settings for crypto payments. Get a fast RPC endpoint from"," ",e.jsx(f,{href:"https://www.helius.dev",children:"Helius"})," or"," ",e.jsx(f,{href:"https://www.quicknode.com/chains/sol",children:"QuickNode"}),". Set up a payment address using"," ",e.jsx(f,{href:"https://phantom.app",children:"Phantom"})," or"," ",e.jsx(f,{href:"https://solflare.com",children:"Solflare"})," wallet."]})},{id:"credits",label:"Credits",category:"cedros_login",description:e.jsxs(e.Fragment,{children:["Configure Cedros Login integration for credits payments. See the"," ",e.jsx(f,{href:"https://docs.cedros.dev/credits",children:"Credits API documentation"}),"."]})}];function K({serverUrl:t,apiKey:i,authManager:n}){const[o,r]=u.useState("app_stores"),a=T.find(d=>d.id===o);return e.jsxs("div",{className:"cedros-admin__payment-settings",children:[e.jsxs("div",{className:"cedros-admin__page-header",children:[e.jsx("h2",{className:"cedros-admin__page-title",children:"Payment Options"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Configure the payment rails Cedros can use across web, iOS, Android, and crypto flows."})]}),e.jsx("div",{className:"cedros-admin__tabs cedros-admin__tabs--line",children:T.map(d=>e.jsx("button",{type:"button",className:`cedros-admin__tab ${o===d.id?"cedros-admin__tab--active":""}`,onClick:()=>r(d.id),children:d.label},d.id))}),e.jsxs("div",{style:{marginTop:"1rem"},children:[o==="app_stores"&&e.jsxs(e.Fragment,{children:[e.jsx(z,{serverUrl:t}),e.jsx(J,{serverUrl:t,apiKey:i,authManager:n})]}),e.jsx(L.SingleCategorySettings,{serverUrl:t,apiKey:i,authManager:n,category:a.category,title:`${a.label} Settings`,description:a.description,showEnabledToggle:!0},a.category)]})]})}exports.PaymentSettingsSection=K;
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),u=require("react"),L=require("./SingleCategorySettings-BxVUUy8R.js"),F=require("./configApi-BS5UJfzm.js"),W=require("./ErrorBanner-DxrRVqwe.js"),q=require("./StatsBar-DDUWoizP.js"),O="https://github.com/conorholds/cedros-pay/tree/main/ui/docs/cross-channel-setup.md";function M({title:t,description:i,steps:n}){return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.75rem",padding:"1rem",background:"var(--cedros-admin-surface, #ffffff)"},children:[e.jsx("div",{style:{fontWeight:700,marginBottom:"0.35rem"},children:t}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.9rem",marginBottom:"0.75rem",lineHeight:1.5},children:i}),e.jsx("ol",{style:{margin:0,paddingLeft:"1.1rem",lineHeight:1.6,fontSize:"0.9rem"},children:n.map(o=>e.jsx("li",{children:o},o))})]})}function R({children:t}){return e.jsx("code",{style:{display:"block",padding:"0.65rem 0.75rem",background:"rgba(15, 23, 42, 0.04)",borderRadius:"0.5rem",marginTop:"0.5rem",wordBreak:"break-all"},children:t})}function z({serverUrl:t}){const i=`${t.replace(/\/$/,"")}/webhook/stripe`,n=`${t.replace(/\/$/,"")}/paywall/v1/native-store/apple/notifications`,o=`${t.replace(/\/$/,"")}/paywall/v1/native-store/google/notifications`,r=[{title:"Stripe Web Checkout",description:"Use this for website payments and any mobile redirect Checkout flows. Cedros owns the checkout session creation, but Stripe still needs your API keys and webhook endpoint configured.",steps:["Add your Stripe publishable key, secret key, and webhook signing secret in Payment Options → Stripe.","Create a Stripe webhook endpoint that sends subscription and checkout events to the Cedros webhook URL shown below.","If your app uses custom deep links for Stripe redirects, add the scheme in Stripe → allowed redirect schemes."]},{title:"Apple App Store Billing",description:"Use this for digital goods and subscriptions distributed through the Apple App Store. Cedros verifies purchases and handles server notifications, but you still need to create App Store Connect products and credentials.",steps:["In Products, map each store-managed product to its Apple product ID and choose the correct store-managed kind.","In Payment Options → App Stores, enter your App Store Server API issuer ID, key ID, private key, and bundle ID.","Create the matching products and subscriptions in App Store Connect, then point App Store Server Notifications at the Cedros Apple notification URL.","If you rely on reader, US external purchase link, or similar exceptions, configure those policies in the app build and only after Apple approves the relevant entitlement."]},{title:"Google Play Billing",description:"Use this for digital goods and subscriptions distributed through Google Play. Cedros verifies purchases, acknowledges them server-side, and processes RTDNs, but you still need Play Console catalog and service-account setup.",steps:["In Products, map each Play product ID and, for subscriptions, the package name, base plan ID, and optional offer ID.","In Payment Options → App Stores, enter your Google Play service-account email, private key, package name, push service-account email, and push audience.","Create the matching one-time products or subscriptions in Google Play Console and point RTDN delivery at the Cedros Google notification URL.","If you participate in User Choice Billing, Alternative Billing Only, or External Offers programs, configure those policies explicitly in the app build only for approved storefronts."]}];return e.jsxs("div",{style:{display:"grid",gap:"1rem",marginBottom:"1rem"},children:[e.jsxs("div",{style:{padding:"1rem",borderRadius:"0.75rem",background:"var(--cedros-admin-subtle, rgba(15, 23, 42, 0.03))",border:"1px solid var(--cedros-admin-border, #e5e7eb)"},children:[e.jsx("div",{style:{fontWeight:700,marginBottom:"0.4rem"},children:"Turnkey setup path"}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",lineHeight:1.6,fontSize:"0.9rem"},children:"Create the product once in Cedros, configure each payment channel here, then point Stripe, App Store Connect, and Google Play Console at the Cedros endpoints below. Cedros packages can then load the same product catalog and apply the right rail at runtime."}),e.jsx(R,{children:i}),e.jsx(R,{children:n}),e.jsx(R,{children:o}),e.jsx("div",{style:{marginTop:"0.5rem",color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.8rem",lineHeight:1.5},children:"Store notifications must target a tenant-specific Cedros deployment URL. If your deployment injects tenant context via domain, path prefix, or headers, use that tenant-scoped URL here instead of a generic shared endpoint."}),e.jsx("a",{href:O,target:"_blank",rel:"noopener noreferrer",style:{display:"inline-block",marginTop:"0.75rem",fontSize:"0.85rem",fontWeight:600,textDecoration:"underline",color:"inherit"},children:"Open the full cross-channel setup guide"})]}),e.jsx("div",{style:{display:"grid",gap:"1rem",gridTemplateColumns:"repeat(auto-fit, minmax(260px, 1fr))"},children:r.map(a=>e.jsx(M,{...a},a.title))})]})}function p(t){return typeof t=="string"&&t.trim().length>0}function G(t){switch(t){case"complete":return"Complete";case"manual":return"Manual check";case"incomplete":default:return"Needs setup"}}function N(t){switch(t){case"complete":return{background:"rgba(34, 197, 94, 0.12)",color:"#166534",border:"rgba(34, 197, 94, 0.24)"};case"manual":return{background:"rgba(245, 158, 11, 0.12)",color:"#92400e",border:"rgba(245, 158, 11, 0.24)"};case"incomplete":default:return{background:"rgba(239, 68, 68, 0.12)",color:"#991b1b",border:"rgba(239, 68, 68, 0.24)"}}}function U(t){const i=t.metadata?.store_policy_fulfillment_type;if(i==="digital_in_app"||i==="physical_goods"||i==="real_world_service"||i==="reader_content"||i==="other")return i;switch(t.fulfillment?.type){case"shipping":return"physical_goods";case"service":return"real_world_service";case"digital_download":return"digital_in_app";default:return}}function H(t){let i=0,n=0,o=0,r=0,a=0;return t.forEach(d=>{if(U(d)!=="digital_in_app")return;i+=1;const s=d.storeBilling,x=!!s?.apple?.productId,y=!!s?.google?.productId,b=s?.kind==="auto_renewable_subscription"&&y,k=!!s?.google?.basePlanId;x&&y&&(!b||k)&&(n+=1),x||(o+=1),y||(r+=1),b&&!k&&(a+=1)}),{digitalCount:i,fullyMappedCount:n,missingAppleCount:o,missingGoogleCount:r,missingBasePlanCount:a}}function V(t){return t.some(i=>i.status==="incomplete")?"incomplete":t.some(i=>i.status==="manual")?"manual":"complete"}async function Q(t){const{serverUrl:i,apiKey:n,authManager:o}=t;if(o?.isAuthenticated())return(await o.fetchWithAuth("/admin/products?limit=500")).products??[];const r={"Content-Type":"application/json"};n&&(r["X-API-Key"]=n);const a=await fetch(`${i.replace(/\/$/,"")}/admin/products?limit=500`,{headers:r});if(!a.ok)throw new Error(`Failed to fetch products (${a.status})`);return(await a.json()).products??[]}function X({section:t}){const i=V(t.items),n=N(i);return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.75rem",padding:"1rem",background:"var(--cedros-admin-surface, #ffffff)"},children:[e.jsxs("div",{style:{display:"flex",justifyContent:"space-between",alignItems:"flex-start",gap:"1rem",marginBottom:"0.5rem"},children:[e.jsxs("div",{children:[e.jsx("div",{style:{fontWeight:700},children:t.title}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.9rem",lineHeight:1.5},children:t.description})]}),e.jsx("span",{style:{background:n.background,color:n.color,border:`1px solid ${n.border}`,borderRadius:"999px",padding:"0.2rem 0.6rem",fontSize:"0.78rem",fontWeight:600,whiteSpace:"nowrap"},children:G(i)})]}),e.jsx("div",{style:{display:"grid",gap:"0.65rem",marginTop:"0.85rem"},children:t.items.map(o=>{const r=N(o.status);return e.jsxs("div",{style:{border:"1px solid var(--cedros-admin-border, #e5e7eb)",borderRadius:"0.65rem",padding:"0.8rem",background:"rgba(15, 23, 42, 0.015)"},children:[e.jsxs("div",{style:{display:"flex",alignItems:"center",justifyContent:"space-between",gap:"1rem",marginBottom:"0.35rem"},children:[e.jsx("div",{style:{fontWeight:600},children:o.title}),e.jsx("span",{style:{background:r.background,color:r.color,border:`1px solid ${r.border}`,borderRadius:"999px",padding:"0.15rem 0.5rem",fontSize:"0.75rem",fontWeight:600,whiteSpace:"nowrap"},children:G(o.status)})]}),e.jsx("div",{style:{color:"var(--cedros-admin-text-muted, #64748b)",fontSize:"0.88rem",lineHeight:1.5},children:o.detail})]},`${t.title}-${o.title}`)})})]})}function J({serverUrl:t,apiKey:i,authManager:n}){const o=u.useMemo(()=>new F.ConfigApiClient(t,void 0,n),[t,n]),[r,a]=u.useState([]),[d,A]=u.useState({}),[s,x]=u.useState({}),[y,b]=u.useState(!0),[k,D]=u.useState(null),[B,E]=u.useState(0);u.useEffect(()=>{let l=!1;return(async()=>{b(!0),D(null);try{const[g,m,C]=await Promise.all([o.getConfig("stripe",!0),o.getConfig("native_store",!0),Q({serverUrl:t,apiKey:i,authManager:n})]);if(l)return;A(g.config??{}),x(m.config??{}),a(C)}catch(g){if(l)return;D(g instanceof Error?g.message:"Failed to load payment readiness data")}finally{l||b(!1)}})(),()=>{l=!0}},[i,n,o,B,t]);const v=u.useMemo(()=>{const l=p(d.secret_key)&&p(d.publishable_key),S=p(d.webhook_secret),g=s.apple_enabled===!0,m=g&&p(s.apple_issuer_id)&&p(s.apple_key_id)&&p(s.apple_private_key)&&p(s.apple_bundle_id),C=s.google_enabled===!0,h=C&&p(s.google_service_account_email)&&p(s.google_private_key)&&p(s.google_package_name)&&p(s.google_push_service_account_email)&&p(s.google_push_audience),{digitalCount:c,fullyMappedCount:P,missingAppleCount:j,missingGoogleCount:w,missingBasePlanCount:_}=H(r),$=[{title:"Website / Stripe",description:"Web checkout and browser-based mobile Stripe flows rely on your Stripe keys and webhook wiring.",items:[{title:"Stripe API keys",status:l?"complete":"incomplete",detail:l?"Publishable and secret keys are configured in Cedros.":"Add both the Stripe publishable key and secret key in Payment Options → Stripe."},{title:"Stripe webhook signing secret",status:S?"complete":"incomplete",detail:S?"Cedros has a webhook signing secret configured.":"Add the Stripe webhook signing secret so Cedros can trust subscription and checkout lifecycle events."},{title:"Stripe dashboard webhook endpoint",status:l&&S?"manual":"incomplete",detail:l&&S?`Confirm Stripe sends events to ${t.replace(/\/$/,"")}/webhook/stripe and that test events succeed.`:"Finish the Stripe config above, then create the webhook in Stripe Dashboard and point it at Cedros."}]},{title:"Apple App Store",description:"Apple digital goods require App Store billing plus matching App Store Connect catalog and server credentials.",items:[{title:"Apple native-store credentials",status:m?"complete":"incomplete",detail:m?"Issuer ID, key ID, private key, and bundle ID are configured.":g?"Apple billing is enabled, but Cedros is still missing one or more App Store Server API credentials.":"Enable Apple App Store billing and add the App Store Server API credentials in Payment Options → App Stores."},{title:"Apple product mapping",status:c===0?"manual":j===0?"complete":"incomplete",detail:c===0?"No digital in-app products are classified yet. Create or classify a digital product before shipping on the App Store.":j===0?`All ${c} digital in-app products have an Apple product ID.`:`${j} of ${c} digital in-app products still need an Apple product ID.`},{title:"App Store Connect server notifications",status:m?"manual":"incomplete",detail:m?`Confirm App Store Server Notifications point to ${t.replace(/\/$/,"")}/paywall/v1/native-store/apple/notifications using your tenant-scoped Cedros URL.`:"Finish the Apple credentials first, then configure App Store Server Notifications in App Store Connect."}]},{title:"Google Play",description:"Google digital goods require Play Billing plus Play Console product mapping, service-account access, and RTDN wiring.",items:[{title:"Google Play API and RTDN credentials",status:h?"complete":"incomplete",detail:h?"Service account, package name, RTDN push identity, and audience are configured.":C?"Google Play billing is enabled, but Cedros is still missing one or more API or RTDN verification fields.":"Enable Google Play billing and add the Android Publisher / RTDN credentials in Payment Options → App Stores."},{title:"Google product and base-plan mapping",status:c===0?"manual":w===0&&_===0?"complete":"incomplete",detail:c===0?"No digital in-app products are classified yet. Create or classify a digital product before shipping on Google Play.":w===0&&_===0?`All ${c} digital in-app products have a Google Play mapping${_===0?"":" and required base plans"}.`:`${w} products still need a Google product ID and ${_} subscription products still need a base plan ID.`},{title:"Play Console RTDN delivery",status:h?"manual":"incomplete",detail:h?`Confirm Real-time developer notifications are configured to reach ${t.replace(/\/$/,"")}/paywall/v1/native-store/google/notifications through your approved Pub/Sub push identity.`:"Finish the Google Play credentials first, then configure RTDN delivery in Google Play Console and Google Cloud Pub/Sub."}]},{title:"Cedros product catalog",description:"Cedros packages can only route correctly when the catalog itself is classified and mapped cleanly.",items:[{title:"Products created in Cedros",status:r.length>0?"complete":"incomplete",detail:r.length>0?`${r.length} products are present in the Cedros catalog.`:"Create at least one product in Admin → Products."},{title:"Digital product app-store mapping coverage",status:c===0?"manual":P===c?"complete":"incomplete",detail:c===0?"No digital in-app products are currently classified. If you sell only physical goods or real-world services, this is expected.":`${P} of ${c} digital in-app products currently have both Apple/Google mapping requirements satisfied.`},{title:"Manual end-to-end store test purchases",status:l||m||h?"manual":"incomplete",detail:l||m||h?"Run at least one website purchase, one App Store sandbox purchase, and one Google Play test purchase before shipping.":"Finish the payment channel setup first, then run real test purchases through every channel you plan to support."}]}];return{sections:$,stats:{products:r.length,digitalProducts:c,fullyMappedProducts:P,autoVerifiedChecks:$.flatMap(I=>I.items).filter(I=>I.status==="complete").length}}},[s,r,t,d]);return e.jsxs("div",{style:{marginBottom:"1rem"},children:[e.jsxs("div",{className:"cedros-admin__page-header",style:{marginBottom:"1rem"},children:[e.jsx("h3",{className:"cedros-admin__page-title",children:"Readiness Checklist"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Cedros can verify configuration and product mapping automatically, but external console wiring and test purchases still require a human check."})]}),e.jsx(W.ErrorBanner,{message:k,onRetry:()=>{E(l=>l+1)}}),e.jsx(q.StatsBar,{stats:[{label:"Products",value:v.stats.products},{label:"Digital App Products",value:v.stats.digitalProducts},{label:"Fully Mapped",value:v.stats.fullyMappedProducts},{label:"Auto-Verified Checks",value:v.stats.autoVerifiedChecks}],isLoading:y}),e.jsx("div",{style:{display:"grid",gap:"1rem",gridTemplateColumns:"repeat(auto-fit, minmax(280px, 1fr))",marginTop:"1rem"},children:v.sections.map(l=>e.jsx(X,{section:l},l.title))})]})}function f({href:t,children:i}){return e.jsx("a",{href:t,target:"_blank",rel:"noopener noreferrer",style:{color:"inherit",textDecoration:"underline"},children:i})}const T=[{id:"app_stores",label:"App Stores",category:"native_store",description:e.jsx(e.Fragment,{children:"Configure Apple App Store and Google Play verification, lifecycle notifications, and server credentials. Use the setup guide below to connect App Store Connect and Google Play Console to Cedros."})},{id:"stripe",label:"Stripe",category:"stripe",description:e.jsxs(e.Fragment,{children:["Configure your Stripe integration for card payments. Get your API keys from the"," ",e.jsx(f,{href:"https://dashboard.stripe.com/apikeys",children:"Stripe Dashboard"}),"."]})},{id:"crypto",label:"Crypto",category:"x402",description:e.jsxs(e.Fragment,{children:["Configure Solana wallet and token settings for crypto payments. Get a fast RPC endpoint from"," ",e.jsx(f,{href:"https://www.helius.dev",children:"Helius"})," or"," ",e.jsx(f,{href:"https://www.quicknode.com/chains/sol",children:"QuickNode"}),". Set up a payment address using"," ",e.jsx(f,{href:"https://phantom.app",children:"Phantom"})," or"," ",e.jsx(f,{href:"https://solflare.com",children:"Solflare"})," wallet."]})},{id:"credits",label:"Credits",category:"cedros_login",description:e.jsxs(e.Fragment,{children:["Configure Cedros Login integration for credits payments. See the"," ",e.jsx(f,{href:"https://docs.cedros.dev/credits",children:"Credits API documentation"}),"."]})}];function K({serverUrl:t,apiKey:i,authManager:n}){const[o,r]=u.useState("app_stores"),a=T.find(d=>d.id===o);return e.jsxs("div",{className:"cedros-admin__payment-settings",children:[e.jsxs("div",{className:"cedros-admin__page-header",children:[e.jsx("h2",{className:"cedros-admin__page-title",children:"Payment Options"}),e.jsx("p",{className:"cedros-admin__page-description",children:"Configure the payment rails Cedros can use across web, iOS, Android, and crypto flows."})]}),e.jsx("div",{className:"cedros-admin__tabs cedros-admin__tabs--line",children:T.map(d=>e.jsx("button",{type:"button",className:`cedros-admin__tab ${o===d.id?"cedros-admin__tab--active":""}`,onClick:()=>r(d.id),children:d.label},d.id))}),e.jsxs("div",{style:{marginTop:"1rem"},children:[o==="app_stores"&&e.jsxs(e.Fragment,{children:[e.jsx(z,{serverUrl:t}),e.jsx(J,{serverUrl:t,apiKey:i,authManager:n})]}),e.jsx(L.SingleCategorySettings,{serverUrl:t,apiKey:i,authManager:n,category:a.category,title:`${a.label} Settings`,description:a.description,showEnabledToggle:!0},a.category)]})]})}exports.PaymentSettingsSection=K;
|