@lockerverse/sdk 0.1.0-alpha.2 → 0.1.0-alpha.3
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 +32 -0
- package/dist/checkout.js +1 -1
- package/dist/checkout.js.map +1 -1
- package/dist/signup.d.ts +8 -2
- package/dist/signup.d.ts.map +1 -1
- package/dist/signup.js +1 -1
- package/dist/signup.js.map +1 -1
- package/dist/transport.js +1 -1
- package/dist/transport.js.map +1 -1
- package/dist/types.d.ts +1 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js +1 -1
- package/dist/types.js.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -92,6 +92,24 @@ const checkout = createLockerverseCheckout({
|
|
|
92
92
|
});
|
|
93
93
|
```
|
|
94
94
|
|
|
95
|
+
Every SDK HTTP operation has a 20-second deadline by default. Hosts can choose a
|
|
96
|
+
different positive whole-number deadline in milliseconds, up to
|
|
97
|
+
`2_147_483_647`, with `requestTimeoutMs` on either checkout or signup. The
|
|
98
|
+
deadline includes receiving and validating the complete JSON response body:
|
|
99
|
+
|
|
100
|
+
```ts
|
|
101
|
+
const checkout = createLockerverseCheckout({
|
|
102
|
+
communitySlug: "auburn",
|
|
103
|
+
requestTimeoutMs: 10_000,
|
|
104
|
+
widgetSlug: "auburn-tailgate-party",
|
|
105
|
+
});
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
A timeout only means the browser stopped waiting; it does not prove that a
|
|
109
|
+
payment mutation failed on Lockerverse's server. After an ambiguous payment
|
|
110
|
+
confirmation, read `recoverablePaymentReference` from the `error` state and
|
|
111
|
+
pass it to `getPaymentStatus()`.
|
|
112
|
+
|
|
95
113
|
`widget.customFields` is a discriminated union covering `text`, `textarea`,
|
|
96
114
|
`select`, `multi_select`, `radio`, and `checkboxes`. Archived fields and options
|
|
97
115
|
are omitted. Hosts own rendering and client-side required-field feedback:
|
|
@@ -132,6 +150,20 @@ const submission = await signup.submit({
|
|
|
132
150
|
});
|
|
133
151
|
```
|
|
134
152
|
|
|
153
|
+
The same ambiguity applies when a signup submission times out. Read
|
|
154
|
+
`recoverableSubmissionReference` from the `error` state and retry the same
|
|
155
|
+
values with that reference so Lockerverse can return the original submission
|
|
156
|
+
instead of creating a duplicate:
|
|
157
|
+
|
|
158
|
+
```ts
|
|
159
|
+
const state = signup.getState();
|
|
160
|
+
if (state.phase === "error" && state.recoverableSubmissionReference) {
|
|
161
|
+
await signup.submit(values, {
|
|
162
|
+
submissionReference: state.recoverableSubmissionReference,
|
|
163
|
+
});
|
|
164
|
+
}
|
|
165
|
+
```
|
|
166
|
+
|
|
135
167
|
`subscribe()` observes `idle`, `loading`, `ready`, `submitting`, `submitted`,
|
|
136
168
|
and `error`. Definitions and submission results are immutable snapshots.
|
|
137
169
|
Lockerverse validates enabled and required built-in fields, custom-field
|
package/dist/checkout.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{a as e,c as t,d as n,f as r,i,l as a,n as o,o as s,p as c,r as l,s as u,t as d,u as f}from"./transport.js";import{n as p,t as m}from"./types.js";const h={development:`pk_test_51O7FkjDHAhgRuLtFHdkXdIe8T5i7rOVaG9PCtDetK3UUVKojVUEKHmQacGzigf9mOX1wz3zSOKoYwFjRcTfML9PU00OjJko2lk`,production:`pk_live_51O7FkjDHAhgRuLtFlzLdxJrwo7F09WCKTlzT9lnBePjOGizWnuijkH9oCkoAddkmBT8ngIuqAPkDiHlPEAH4KXbz00Tm0DaPT4`};function g(e){let t=c(e,`widgetSlug`);return{...t,stripePublishableKey:h[t.environment],widgetSlug:t.resourceSlug,widgetSlugValue:t.resourceSlugValue}}function _(e,t){if(!Number.isSafeInteger(e)||e<t)throw TypeError(`Expected a safe integer.`);return e}function v(e,t,n){if(typeof e!=`number`||!Number.isFinite(e)||e<t||e>n)throw TypeError(`Expected a bounded finite number.`);return e}function y(e,t){return e===null?null:_(e,t)}function b(e){if(e===`one-time`||e===`monthly`||e===`annually`)return e;throw TypeError(`Expected a supported payment option.`)}function x(e){if(e===`fixed`||e===`custom`)return e;throw TypeError(`Expected a supported pricing mode.`)}function S(e){if(e===`action_required`||e===`failed`||e===`pending`||e===`success`)return e;throw TypeError(`Expected a supported payment status.`)}function C(e){if(e===null)return null;let t=f(e);if(t.source!==`email_list`&&t.source!==`promo_code`)throw TypeError(`Expected a supported discount source.`);let n=t.source;return{percentageOff:v(t.percentageOff,0,100),source:n}}function w(e){let t=e===void 0?{}:f(e);return{memberId:u(t.memberId,!1),merchSize:u(t.merchSize,!1),phone:u(t.phone,!1),promoCode:u(t.promoCode,!1),serviceFee:u(t.serviceFee,!1),shipping:u(t.shipping,!1),tipping:u(t.tipping,!1)}}function T(n){let r=f(n);return{amountCents:y(r.amountCents,0),description:t(r.description,null),id:e(r.id),inventoryQuantity:y(r.inventoryQuantity,0),maxQuantity:y(r.maxQuantity,0),minimumAmountCents:y(r.minimumAmountCents,0),minQuantity:y(r.minQuantity,0),name:e(r.name),paymentOption:b(r.paymentOption),pricingMode:x(r.pricingMode)}}function E(t){let n=f(t);return{acceptsDiscounts:u(n.acceptsDiscounts,!1),id:e(n.id),product:T(n.product),productId:e(n.productId),slug:e(n.slug)}}function D(e){let n=f(e),r=n.config===void 0?{}:f(n.config),o=n.pricingPolicy===void 0?{currency:`usd`,serviceFeeRateBasisPoints:0}:f(n.pricingPolicy),s=n.products===void 0?[]:n.products;if(!Array.isArray(s))throw TypeError(`Expected a Product array.`);if(o.currency!==`usd`)throw TypeError(`Expected USD checkout pricing policy.`);return{config:{customFields:i(r.customFields),fields:w(r.fields)},description:t(n.description,null),id:a(n.id,``),name:a(n.name,`Lockerverse widget`),pricingPolicy:{currency:`usd`,serviceFeeRateBasisPoints:_(o.serviceFeeRateBasisPoints,0)},products:s.map(E),showCommunityBranding:u(n.showCommunityBranding,!0),title:t(n.title,null)}}function O(t){let n=f(t);return{acceptsDiscounts:l(n.acceptsDiscounts),listingId:e(n.listingId),listingSlug:e(n.listingSlug),paymentOption:b(n.paymentOption),pricingMode:x(n.pricingMode),productId:e(n.productId),productName:e(n.productName),quantity:_(n.quantity,1),subtotalCents:_(n.subtotalCents,0),unitAmountCents:_(n.unitAmountCents,0)}}function k(t){let n=f(t);if(!Array.isArray(n.lineItems))throw TypeError(`Expected a line item array.`);return{amountCents:_(n.amountCents,0),appliedDiscount:C(n.appliedDiscount),connectedAccountId:n.connectedAccountId===null?null:e(n.connectedAccountId),discountableSubtotalCents:_(n.discountableSubtotalCents,0),discountCents:_(n.discountCents,0),lineItems:n.lineItems.map(O),paymentOption:b(n.paymentOption),serviceFeeCents:_(n.serviceFeeCents,0),subtotalCents:_(n.subtotalCents,0),tipCents:_(n.tipCents,0),totalCents:_(n.totalCents,0)}}function A(t){let n=f(t);return{checkoutId:e(n.checkoutId),checkoutStatus:S(n.checkoutStatus),clientSecret:s(n.clientSecret),paymentReference:e(n.paymentReference),requiresAction:l(n.requiresAction),status:s(n.status)}}const j=1e4;function M(e,t){if(!Number.isSafeInteger(e)||e<0)throw TypeError(t);return e}function N(e,t){return M(e+t,`The selected checkout total is too large.`)}function P(e,t){return M(e*t,`The selected Product quantity produces an unsafe total.`)}function F(e,t){let n=(BigInt(e)*BigInt(t)+BigInt(j/2))/BigInt(j);if(n>BigInt(2**53-1))throw TypeError(`The selected checkout total is too large.`);return Number(n)}function I(e,t,n){let r=0,i=0;for(let n of t.items){let t=e.products.find(({id:e,slug:t})=>e===n.productId&&t===n.productSlug);if(!t)throw TypeError(`The selected Product is no longer available.`);if(t.paymentOption!==`one-time`)throw TypeError(`Recurring Products are not supported by this SDK checkout yet.`);let a=`quantity`in n?P(t.amountCents??0,n.quantity):n.amountCents;r=N(r,a),t.acceptsDiscounts&&(i=N(i,a))}let a=n.includeServiceFee?F(r,e.pricingPolicy.serviceFeeRateBasisPoints):0,o=n.tipCents??0,s=N(r,a);return{amountCents:s,appliedDiscount:null,authoritative:!1,discountableSubtotalCents:i,discountCents:0,serviceFeeCents:a,subtotalCents:r,tipCents:o,totalCents:N(s,o)}}function L(e){let{product:t}=e;return{acceptsDiscounts:e.acceptsDiscounts??!1,amountCents:t.amountCents,description:t.description??null,id:t.id,inventoryQuantity:t.inventoryQuantity,listingId:e.id,maximumQuantity:t.maxQuantity,minimumAmountCents:t.minimumAmountCents,minimumQuantity:t.minQuantity,name:t.name,paymentOption:t.paymentOption,pricingMode:t.pricingMode,slug:e.slug}}function R(e,t){let n=e.config?.fields??{};return{payment:{currency:`usd`,publishableKey:t},pricingPolicy:{currency:`usd`,serviceFeeRateBasisPoints:e.pricingPolicy?.serviceFeeRateBasisPoints??0},products:(e.products??[]).map(L),widget:{customFields:e.config?.customFields??[],description:e.description??null,fields:{memberId:n.memberId??!1,merchSize:n.merchSize??!1,phone:n.phone??!1,promoCode:n.promoCode??!1,serviceFee:n.serviceFee??!1,shipping:n.shipping??!1,tipping:n.tipping??!1},id:e.id??``,name:e.name??`Lockerverse widget`,showCommunityBranding:e.showCommunityBranding??!0,title:e.title??null}}}function z(e){return r({payment:{...e.payment},pricingPolicy:{...e.pricingPolicy},products:e.products.map(e=>({...e})),widget:{...e.widget,customFields:e.widget.customFields.map(e=>`options`in e?{...e,options:e.options.map(e=>({...e}))}:{...e}),fields:{...e.widget.fields}}})}function B(e){return r({...e,appliedDiscount:e.appliedDiscount?{...e.appliedDiscount}:null,lineItems:e.lineItems.map(e=>({...e})),payment:{...e.payment}})}function V(e){return r({...e})}function H(e){let{apiBaseUrl:t,communitySlug:i,communitySlugValue:a,environment:s,fetchImplementation:c,onError:l,sentryDsn:u,stripePublishableKey:f,widgetSlug:m,widgetSlugValue:h}=g(e),_=null,v=null,y=null,b=null,x=null,S=0,C=0,w=!1,T=new Map,E=o({phase:`idle`,selection:r({items:[]})});function O(e){let t=_,n=t?t.products.find(({slug:t})=>t===e):void 0;if(!n)throw Error(`Lockerverse Product "${e}" is unavailable.`);return n}let j=n({communitySlug:a,environment:s,getContext:()=>({paymentReference:b,widgetSlug:h}),onError:l,resourceContextName:`lockerverse_widget`,sentryDsn:u});function M(e,t=`update_selection`){throw j(new p({code:`invalid_selection`,message:e,operation:t,reportable:!1}))}let{fetchResponse:N,parseResponseJson:P}=d(c,j);function F(){let e=_;return r({items:(e?e.products:[]).flatMap(e=>{let t=T.get(e.slug);return t?[{productId:e.id,productSlug:e.slug,...t}]:[]})})}function L(){v=null,y=null,b=null,x=null}function H(){w&&M(`Selection cannot change while a payment is being submitted.`)}function U(e){w&&M(`This operation cannot run while a payment is being submitted.`,e)}function W(){C+=1,L()}function G(e=null){_&&E.commit({catalog:_,phase:`ready`,preview:e,selection:F()})}function K(e,t=null){E.commit({catalog:_,error:e,phase:`error`,recoverablePaymentReference:t,selection:F()})}function q(e,t){if(e!==C||t!==S)throw j(new p({code:`total_calculation_failed`,message:`This Lockerverse checkout total was superseded. Calculate the total again for the current selection.`,operation:`calculate_total`,reportable:!1}))}function J(e={}){if(U(`calculate_total`),!_)throw Error(`Load the Lockerverse widget before previewing the total.`);T.size===0&&M(`Select at least one Product before previewing.`);let t=Y(_,e);W();try{let e=r(I(_,F(),t));return x=e,G(e),e}catch(e){M(e instanceof Error?e.message:`Unable to preview checkout.`)}}function Y(e,t){X(e,t);let n=t.tipCents??0,r=t.email?.trim().toLowerCase(),i=t.promoCode?.trim();return{...r?{email:r}:{},...t.includeServiceFee===void 0?{}:{includeServiceFee:t.includeServiceFee},...i?{promoCode:i}:{},...t.tipCents===void 0?{}:{tipCents:n}}}function X(e,t){let n=t.tipCents??0;(!Number.isSafeInteger(n)||n<0)&&M(`Tip must be a non-negative whole number of cents.`),t.includeServiceFee&&!e.widget.fields.serviceFee&&M(`Service fee is not enabled for this widget.`),t.includeServiceFee&&e.pricingPolicy.serviceFeeRateBasisPoints===0&&M(`Service fee pricing is unavailable. Reload the widget and try again.`),n>0&&!e.widget.fields.tipping&&M(`Tipping is not enabled for this widget.`)}async function Z(e={}){if(U(`calculate_total`),!_)throw Error(`Load the Lockerverse widget before calculating the total.`);let n=Y(_,e);T.size===0&&M(`Select at least one Product before calculating the total.`,`calculate_total`);let a=F(),o=r(I(_,a,n));x=o,E.commit({catalog:_,phase:`quoting`,preview:o,selection:a});let s=a.items.map(({productSlug:e,...t})=>t),c=C,l=S+1;S=l,v=null,b=null;let u;try{u=await N(`${t}/v2/community/${i}/payment-widgets/${m}/checkout/quote`,{body:JSON.stringify({...n,items:s}),headers:{"Content-Type":`application/json`},method:`POST`},{code:`total_calculation_failed`,message:`Unable to calculate the Lockerverse checkout total because the request failed.`,operation:`calculate_total`,report:!1})}catch(e){throw q(c,l),e instanceof p?(K(e),j(e)):e}if(q(c,l),!u.ok){let e=new p({code:`total_calculation_failed`,message:`Unable to calculate the Lockerverse checkout total (${u.status}).`,operation:`calculate_total`,reportable:u.status>=500,status:u.status});throw K(e),j(e)}let d;try{if(d=await P(u,k,{code:`total_calculation_failed`,message:`Lockerverse returned an invalid checkout total.`,operation:`calculate_total`,report:!1}),d.paymentOption!==`one-time`)throw new p({code:`total_calculation_failed`,message:`Lockerverse returned an unsupported checkout cadence.`,operation:`calculate_total`,reportable:!0})}catch(e){throw q(c,l),e instanceof p?(K(e),j(e)):e}q(c,l);let f=globalThis.crypto.randomUUID(),{connectedAccountId:h,paymentOption:g,...w}=d,D=r({...w,authoritative:!0,payment:{..._.payment,connectedAccountId:h},paymentOption:`one-time`,paymentReference:f});return v=D,y=r({...n}),b=f,E.commit({catalog:_,phase:`quoted`,preview:o,quote:D,selection:a}),B(D)}return{calculateTotal:Z,clear(){H(),T.clear(),W(),G()},async getPaymentStatus(e=b??``){U(`get_payment_status`),e||M(`Provide a payment reference to recover its status.`,`get_payment_status`),b=e;let n=F();E.commit({catalog:_,paymentReference:e,phase:`recovering`,selection:n});try{let r=await N(`${t}/v2/community/${i}/payment-widgets/${m}/checkout/${encodeURIComponent(e)}/status`,void 0,{code:`payment_status_failed`,message:`Unable to recover the Lockerverse payment status because the request failed.`,operation:`get_payment_status`});if(!r.ok)throw j(new p({code:`payment_status_failed`,message:`Unable to recover the Lockerverse payment status (${r.status}).`,operation:`get_payment_status`,reportable:r.status>=500,status:r.status}));let a=V(await P(r,A,{code:`payment_status_failed`,message:`Lockerverse returned an invalid payment status.`,operation:`get_payment_status`}));return E.commit({catalog:_,payment:a,phase:`payment`,quote:v?.paymentReference===e?v:null,selection:n}),V(a)}catch(t){throw t instanceof p&&K(t,e),t}},getSelection:F,getState:E.getState,async load(){U(`load_widget`),W(),E.commit({phase:`loading`,selection:F()});let e={code:`widget_load_failed`,message:`Unable to load Lockerverse widget because the request failed.`,operation:`load_widget`,report:!1},n;try{n=await N(`${t}/v2/community/${i}/payment-widgets/${m}`,void 0,e)}catch(e){throw e instanceof p?(K(e),j(e)):e}if(!n.ok){let e=new p({code:`widget_load_failed`,message:`Unable to load Lockerverse widget (${n.status}).`,operation:`load_widget`,reportable:n.status>=500,status:n.status});throw K(e),j(e)}let a=await P(n,D,{code:`widget_load_failed`,message:`Lockerverse returned an invalid widget catalog.`,operation:`load_widget`});return T.clear(),_=r(R(a,f)),G(),z(_)},previewTotal:J,remove(e){H(),T.delete(e),W(),G()},setAmount(e,t){H();let n=O(e);n.pricingMode!==`custom`&&M(`Fixed-price Products do not accept custom amounts.`),(!Number.isSafeInteger(t)||t<=0)&&M(`Product amount must be a positive integer in cents.`),n.minimumAmountCents!==null&&t<n.minimumAmountCents&&M(`Product amount must be at least ${n.minimumAmountCents} cents.`),T.set(e,{amountCents:t}),W(),G()},setQuantity(e,t){H();let n=O(e);n.pricingMode!==`fixed`&&M(`Custom-amount Products do not accept quantities.`),(!Number.isSafeInteger(t)||t<=0)&&M(`Product quantity must be a positive integer.`),n.minimumQuantity!==null&&t<n.minimumQuantity&&M(`Product quantity must be at least ${n.minimumQuantity}.`),n.maximumQuantity!==null&&t>n.maximumQuantity&&M(`Product quantity must not exceed ${n.maximumQuantity}.`),n.inventoryQuantity!==null&&t>n.inventoryQuantity&&M(`Requested Product quantity is unavailable.`),T.set(e,{quantity:t}),W(),G()},async submitPayment(e){_&&v&&y||M(`Calculate the current total before submitting a payment.`,`submit_payment`),w&&M(`A Lockerverse payment is already being submitted.`,`submit_payment`);let n=_,r=v,a=y,o=F(),s=x??I(n,o,a),c=e.email.trim().toLowerCase();(!c||c!==a.email)&&M(`Payment email must match the current checkout quote.`,`submit_payment`);let l=o.items.map(({productSlug:e,...t})=>t);w=!0,E.commit({catalog:n,phase:`submitting`,preview:s,quote:r,selection:o});try{let s=await N(`${t}/v2/community/${i}/payment-widgets/${m}/checkout/confirm`,{body:JSON.stringify({confirmationToken:e.confirmationToken,customFieldAnswers:e.customFieldAnswers,email:c,expectedAmountCents:r.amountCents,expectedAppliedDiscount:r.appliedDiscount,expectedConnectedAccountId:r.payment.connectedAccountId,expectedDiscountableSubtotalCents:r.discountableSubtotalCents,expectedDiscountCents:r.discountCents,expectedServiceFeeCents:r.serviceFeeCents,expectedSubtotalCents:r.subtotalCents,expectedTipCents:r.tipCents,expectedTotalCents:r.totalCents,...a,items:l,memberId:e.memberId,merchSize:e.merchSize,metadata:e.metadata,paymentReference:r.paymentReference,phone:e.phone,quoteContractVersion:1}),headers:{"Content-Type":`application/json`},method:`POST`},{code:`payment_submit_failed`,message:`Unable to submit the Lockerverse payment because the request failed.`,operation:`submit_payment`});if(!s.ok)throw j(new p({code:`payment_submit_failed`,message:`Unable to submit the Lockerverse payment (${s.status}).`,operation:`submit_payment`,reportable:s.status>=500,status:s.status}));let u=V(await P(s,A,{code:`payment_submit_failed`,message:`Lockerverse returned an invalid payment confirmation.`,operation:`submit_payment`}));return E.commit({catalog:n,payment:u,phase:`payment`,quote:r,selection:o}),V(u)}catch(e){throw e instanceof p&&K(e,r.paymentReference),e}finally{w=!1}},subscribe:E.subscribe}}export{m as LOCKERVERSE_SDK_VERSION,p as LockerverseSdkError,H as createLockerverseCheckout};
|
|
1
|
+
import{a as e,c as t,d as n,f as r,i,l as a,n as o,o as s,p as c,r as l,s as u,t as d,u as f}from"./transport.js";import{n as p,t as m}from"./types.js";const h={development:`pk_test_51O7FkjDHAhgRuLtFHdkXdIe8T5i7rOVaG9PCtDetK3UUVKojVUEKHmQacGzigf9mOX1wz3zSOKoYwFjRcTfML9PU00OjJko2lk`,production:`pk_live_51O7FkjDHAhgRuLtFlzLdxJrwo7F09WCKTlzT9lnBePjOGizWnuijkH9oCkoAddkmBT8ngIuqAPkDiHlPEAH4KXbz00Tm0DaPT4`};function g(e){let t=c(e,`widgetSlug`);return{...t,stripePublishableKey:h[t.environment],widgetSlug:t.resourceSlug,widgetSlugValue:t.resourceSlugValue}}function _(e,t){if(!Number.isSafeInteger(e)||e<t)throw TypeError(`Expected a safe integer.`);return e}function v(e,t,n){if(typeof e!=`number`||!Number.isFinite(e)||e<t||e>n)throw TypeError(`Expected a bounded finite number.`);return e}function y(e,t){return e===null?null:_(e,t)}function b(e){if(e===`one-time`||e===`monthly`||e===`annually`)return e;throw TypeError(`Expected a supported payment option.`)}function x(e){if(e===`fixed`||e===`custom`)return e;throw TypeError(`Expected a supported pricing mode.`)}function S(e){if(e===`action_required`||e===`failed`||e===`pending`||e===`success`)return e;throw TypeError(`Expected a supported payment status.`)}function C(e){if(e===null)return null;let t=f(e);if(t.source!==`email_list`&&t.source!==`promo_code`)throw TypeError(`Expected a supported discount source.`);let n=t.source;return{percentageOff:v(t.percentageOff,0,100),source:n}}function w(e){let t=e===void 0?{}:f(e);return{memberId:u(t.memberId,!1),merchSize:u(t.merchSize,!1),phone:u(t.phone,!1),promoCode:u(t.promoCode,!1),serviceFee:u(t.serviceFee,!1),shipping:u(t.shipping,!1),tipping:u(t.tipping,!1)}}function T(n){let r=f(n);return{amountCents:y(r.amountCents,0),description:t(r.description,null),id:e(r.id),inventoryQuantity:y(r.inventoryQuantity,0),maxQuantity:y(r.maxQuantity,0),minimumAmountCents:y(r.minimumAmountCents,0),minQuantity:y(r.minQuantity,0),name:e(r.name),paymentOption:b(r.paymentOption),pricingMode:x(r.pricingMode)}}function E(t){let n=f(t);return{acceptsDiscounts:u(n.acceptsDiscounts,!1),id:e(n.id),product:T(n.product),productId:e(n.productId),slug:e(n.slug)}}function D(e){let n=f(e),r=n.config===void 0?{}:f(n.config),o=n.pricingPolicy===void 0?{currency:`usd`,serviceFeeRateBasisPoints:0}:f(n.pricingPolicy),s=n.products===void 0?[]:n.products;if(!Array.isArray(s))throw TypeError(`Expected a Product array.`);if(o.currency!==`usd`)throw TypeError(`Expected USD checkout pricing policy.`);return{config:{customFields:i(r.customFields),fields:w(r.fields)},description:t(n.description,null),id:a(n.id,``),name:a(n.name,`Lockerverse widget`),pricingPolicy:{currency:`usd`,serviceFeeRateBasisPoints:_(o.serviceFeeRateBasisPoints,0)},products:s.map(E),showCommunityBranding:u(n.showCommunityBranding,!0),title:t(n.title,null)}}function O(t){let n=f(t);return{acceptsDiscounts:l(n.acceptsDiscounts),listingId:e(n.listingId),listingSlug:e(n.listingSlug),paymentOption:b(n.paymentOption),pricingMode:x(n.pricingMode),productId:e(n.productId),productName:e(n.productName),quantity:_(n.quantity,1),subtotalCents:_(n.subtotalCents,0),unitAmountCents:_(n.unitAmountCents,0)}}function k(t){let n=f(t);if(!Array.isArray(n.lineItems))throw TypeError(`Expected a line item array.`);return{amountCents:_(n.amountCents,0),appliedDiscount:C(n.appliedDiscount),connectedAccountId:n.connectedAccountId===null?null:e(n.connectedAccountId),discountableSubtotalCents:_(n.discountableSubtotalCents,0),discountCents:_(n.discountCents,0),lineItems:n.lineItems.map(O),paymentOption:b(n.paymentOption),serviceFeeCents:_(n.serviceFeeCents,0),subtotalCents:_(n.subtotalCents,0),tipCents:_(n.tipCents,0),totalCents:_(n.totalCents,0)}}function A(t){let n=f(t);return{checkoutId:e(n.checkoutId),checkoutStatus:S(n.checkoutStatus),clientSecret:s(n.clientSecret),paymentReference:e(n.paymentReference),requiresAction:l(n.requiresAction),status:s(n.status)}}const j=1e4;function M(e,t){if(!Number.isSafeInteger(e)||e<0)throw TypeError(t);return e}function N(e,t){return M(e+t,`The selected checkout total is too large.`)}function P(e,t){return M(e*t,`The selected Product quantity produces an unsafe total.`)}function F(e,t){let n=(BigInt(e)*BigInt(t)+BigInt(j/2))/BigInt(j);if(n>BigInt(2**53-1))throw TypeError(`The selected checkout total is too large.`);return Number(n)}function I(e,t,n){let r=0,i=0;for(let n of t.items){let t=e.products.find(({id:e,slug:t})=>e===n.productId&&t===n.productSlug);if(!t)throw TypeError(`The selected Product is no longer available.`);if(t.paymentOption!==`one-time`)throw TypeError(`Recurring Products are not supported by this SDK checkout yet.`);let a=`quantity`in n?P(t.amountCents??0,n.quantity):n.amountCents;r=N(r,a),t.acceptsDiscounts&&(i=N(i,a))}let a=n.includeServiceFee?F(r,e.pricingPolicy.serviceFeeRateBasisPoints):0,o=n.tipCents??0,s=N(r,a);return{amountCents:s,appliedDiscount:null,authoritative:!1,discountableSubtotalCents:i,discountCents:0,serviceFeeCents:a,subtotalCents:r,tipCents:o,totalCents:N(s,o)}}function L(e){let{product:t}=e;return{acceptsDiscounts:e.acceptsDiscounts??!1,amountCents:t.amountCents,description:t.description??null,id:t.id,inventoryQuantity:t.inventoryQuantity,listingId:e.id,maximumQuantity:t.maxQuantity,minimumAmountCents:t.minimumAmountCents,minimumQuantity:t.minQuantity,name:t.name,paymentOption:t.paymentOption,pricingMode:t.pricingMode,slug:e.slug}}function R(e,t){let n=e.config?.fields??{};return{payment:{currency:`usd`,publishableKey:t},pricingPolicy:{currency:`usd`,serviceFeeRateBasisPoints:e.pricingPolicy?.serviceFeeRateBasisPoints??0},products:(e.products??[]).map(L),widget:{customFields:e.config?.customFields??[],description:e.description??null,fields:{memberId:n.memberId??!1,merchSize:n.merchSize??!1,phone:n.phone??!1,promoCode:n.promoCode??!1,serviceFee:n.serviceFee??!1,shipping:n.shipping??!1,tipping:n.tipping??!1},id:e.id??``,name:e.name??`Lockerverse widget`,showCommunityBranding:e.showCommunityBranding??!0,title:e.title??null}}}function z(e){return r({payment:{...e.payment},pricingPolicy:{...e.pricingPolicy},products:e.products.map(e=>({...e})),widget:{...e.widget,customFields:e.widget.customFields.map(e=>`options`in e?{...e,options:e.options.map(e=>({...e}))}:{...e}),fields:{...e.widget.fields}}})}function B(e){return r({...e,appliedDiscount:e.appliedDiscount?{...e.appliedDiscount}:null,lineItems:e.lineItems.map(e=>({...e})),payment:{...e.payment}})}function V(e){return r({...e})}function H(e){let{apiBaseUrl:t,communitySlug:i,communitySlugValue:a,environment:s,fetchImplementation:c,onError:l,requestTimeoutMs:u,sentryDsn:f,stripePublishableKey:m,widgetSlug:h,widgetSlugValue:_}=g(e),v=null,y=null,b=null,x=null,S=null,C=0,w=0,T=!1,E=new Map,O=o({phase:`idle`,selection:r({items:[]})});function j(e){let t=v,n=t?t.products.find(({slug:t})=>t===e):void 0;if(!n)throw Error(`Lockerverse Product "${e}" is unavailable.`);return n}let M=n({communitySlug:a,environment:s,getContext:()=>({paymentReference:x,widgetSlug:_}),onError:l,resourceContextName:`lockerverse_widget`,sentryDsn:f});function N(e,t=`update_selection`){throw M(new p({code:`invalid_selection`,message:e,operation:t,reportable:!1}))}let{requestJson:P}=d(c,M,u);function F(){let e=v;return r({items:(e?e.products:[]).flatMap(e=>{let t=E.get(e.slug);return t?[{productId:e.id,productSlug:e.slug,...t}]:[]})})}function L(){y=null,b=null,x=null,S=null}function H(){T&&N(`Selection cannot change while a payment is being submitted.`)}function U(e){T&&N(`This operation cannot run while a payment is being submitted.`,e)}function W(){w+=1,L()}function G(e=null){v&&O.commit({catalog:v,phase:`ready`,preview:e,selection:F()})}function K(e,t=null){O.commit({catalog:v,error:e,phase:`error`,recoverablePaymentReference:t,selection:F()})}function q(e,t){return e instanceof p?e:new p({...t,reportable:!0})}function J(){return C+=1,C}function Y(e,t,n=!0){if(e===C)return;let r=new p({...t,reportable:!1});throw n?M(r):r}function X(e,t){if(e!==w||t!==C)throw M(new p({code:`total_calculation_failed`,message:`This Lockerverse checkout total was superseded. Calculate the total again for the current selection.`,operation:`calculate_total`,reportable:!1}))}function Z(e={}){if(U(`calculate_total`),!v)throw Error(`Load the Lockerverse widget before previewing the total.`);E.size===0&&N(`Select at least one Product before previewing.`);let t=Q(v,e);W();try{let e=r(I(v,F(),t));return S=e,G(e),e}catch(e){N(e instanceof Error?e.message:`Unable to preview checkout.`)}}function Q(e,t){$(e,t);let n=t.tipCents??0,r=t.email?.trim().toLowerCase(),i=t.promoCode?.trim();return{...r?{email:r}:{},...t.includeServiceFee===void 0?{}:{includeServiceFee:t.includeServiceFee},...i?{promoCode:i}:{},...t.tipCents===void 0?{}:{tipCents:n}}}function $(e,t){let n=t.tipCents??0;(!Number.isSafeInteger(n)||n<0)&&N(`Tip must be a non-negative whole number of cents.`),t.includeServiceFee&&!e.widget.fields.serviceFee&&N(`Service fee is not enabled for this widget.`),t.includeServiceFee&&e.pricingPolicy.serviceFeeRateBasisPoints===0&&N(`Service fee pricing is unavailable. Reload the widget and try again.`),n>0&&!e.widget.fields.tipping&&N(`Tipping is not enabled for this widget.`)}async function ee(e={}){if(U(`calculate_total`),!v)throw Error(`Load the Lockerverse widget before calculating the total.`);let n=Q(v,e);E.size===0&&N(`Select at least one Product before calculating the total.`,`calculate_total`);let a=F(),o=J(),s=r(I(v,a,n));S=s,O.commit({catalog:v,phase:`quoting`,preview:s,selection:a});let c=a.items.map(({productSlug:e,...t})=>t),l=w;y=null,x=null;let u=P(`${t}/v2/community/${i}/payment-widgets/${h}/checkout/quote`,{body:JSON.stringify({...n,items:c}),headers:{"Content-Type":`application/json`},method:`POST`},k,{code:`total_calculation_failed`,message:`Unable to calculate the Lockerverse checkout total because the request failed.`,operation:`calculate_total`,report:!1},{code:`total_calculation_failed`,message:`Lockerverse returned an invalid checkout total.`,operation:`calculate_total`,report:!1}),d;try{d=await u}catch(e){throw X(l,o),e instanceof p?(K(e),M(e)):e}if(X(l,o),!d.ok){let e=new p({code:`total_calculation_failed`,message:`Unable to calculate the Lockerverse checkout total (${d.response.status}).`,operation:`calculate_total`,reportable:d.response.status>=500,status:d.response.status});throw K(e),M(e)}let f;try{if(f=d.value,f.paymentOption!==`one-time`)throw new p({code:`total_calculation_failed`,message:`Lockerverse returned an unsupported checkout cadence.`,operation:`calculate_total`,reportable:!0})}catch(e){throw X(l,o),e instanceof p?(K(e),M(e)):e}X(l,o);let m=globalThis.crypto.randomUUID(),{connectedAccountId:g,paymentOption:_,...C}=f,T=r({...C,authoritative:!0,payment:{...v.payment,connectedAccountId:g},paymentOption:`one-time`,paymentReference:m});return y=T,b=r({...n}),x=m,O.commit({catalog:v,phase:`quoted`,preview:s,quote:T,selection:a}),B(T)}return{calculateTotal:ee,clear(){H(),E.clear(),W(),G()},async getPaymentStatus(e=x??``){U(`get_payment_status`),e||N(`Provide a payment reference to recover its status.`,`get_payment_status`);let n=J(),r={code:`payment_status_failed`,message:`This Lockerverse payment status request was superseded.`,operation:`get_payment_status`};x=e;let a=F();O.commit({catalog:v,paymentReference:e,phase:`recovering`,selection:a});try{let o=await P(`${t}/v2/community/${i}/payment-widgets/${h}/checkout/${encodeURIComponent(e)}/status`,void 0,A,{code:`payment_status_failed`,message:`Unable to recover the Lockerverse payment status because the request failed.`,operation:`get_payment_status`,report:!1},{code:`payment_status_failed`,message:`Lockerverse returned an invalid payment status.`,operation:`get_payment_status`,report:!1});if(Y(n,r,!1),!o.ok)throw new p({code:`payment_status_failed`,message:`Unable to recover the Lockerverse payment status (${o.response.status}).`,operation:`get_payment_status`,reportable:o.response.status>=500,status:o.response.status});let s=V(o.value);if(Y(n,r,!1),s.paymentReference!==e)throw new p({code:`payment_status_failed`,message:`Lockerverse returned an invalid payment status.`,operation:`get_payment_status`,reportable:!0});return O.commit({catalog:v,payment:s,phase:`payment`,quote:y?.paymentReference===e?y:null,selection:a}),V(s)}catch(t){Y(n,r);let i=q(t,{code:`payment_status_failed`,message:`Lockerverse returned an invalid payment status.`,operation:`get_payment_status`});throw K(i,e),M(i)}},getSelection:F,getState:O.getState,async load(){U(`load_widget`);let e=J(),n={code:`widget_load_failed`,message:`This Lockerverse widget load was superseded.`,operation:`load_widget`};W(),O.commit({phase:`loading`,selection:F()});let a={code:`widget_load_failed`,message:`Unable to load Lockerverse widget because the request failed.`,operation:`load_widget`,report:!1};try{let o=await P(`${t}/v2/community/${i}/payment-widgets/${h}`,void 0,D,a,{code:`widget_load_failed`,message:`Lockerverse returned an invalid widget catalog.`,operation:`load_widget`,report:!1});if(Y(e,n,!1),!o.ok)throw new p({code:`widget_load_failed`,message:`Unable to load Lockerverse widget (${o.response.status}).`,operation:`load_widget`,reportable:o.response.status>=500,status:o.response.status});let s=o.value;Y(e,n,!1);let c=r(R(s,m)),l=z(c);return E.clear(),v=c,G(),l}catch(t){Y(e,n);let r=q(t,{code:`widget_load_failed`,message:`Lockerverse returned an invalid widget catalog.`,operation:`load_widget`});throw K(r),M(r)}},previewTotal:Z,remove(e){H(),E.delete(e),W(),G()},setAmount(e,t){H();let n=j(e);n.pricingMode!==`custom`&&N(`Fixed-price Products do not accept custom amounts.`),(!Number.isSafeInteger(t)||t<=0)&&N(`Product amount must be a positive integer in cents.`),n.minimumAmountCents!==null&&t<n.minimumAmountCents&&N(`Product amount must be at least ${n.minimumAmountCents} cents.`),E.set(e,{amountCents:t}),W(),G()},setQuantity(e,t){H();let n=j(e);n.pricingMode!==`fixed`&&N(`Custom-amount Products do not accept quantities.`),(!Number.isSafeInteger(t)||t<=0)&&N(`Product quantity must be a positive integer.`),n.minimumQuantity!==null&&t<n.minimumQuantity&&N(`Product quantity must be at least ${n.minimumQuantity}.`),n.maximumQuantity!==null&&t>n.maximumQuantity&&N(`Product quantity must not exceed ${n.maximumQuantity}.`),n.inventoryQuantity!==null&&t>n.inventoryQuantity&&N(`Requested Product quantity is unavailable.`),E.set(e,{quantity:t}),W(),G()},async submitPayment(e){v&&y&&b||N(`Calculate the current total before submitting a payment.`,`submit_payment`),T&&N(`A Lockerverse payment is already being submitted.`,`submit_payment`);let n=v,r=y,a=b,o=F(),s=S??I(n,o,a),c=e.email.trim().toLowerCase();(!c||c!==a.email)&&N(`Payment email must match the current checkout quote.`,`submit_payment`);let l=o.items.map(({productSlug:e,...t})=>t);J(),T=!0,O.commit({catalog:n,phase:`submitting`,preview:s,quote:r,selection:o});try{let s=await P(`${t}/v2/community/${i}/payment-widgets/${h}/checkout/confirm`,{body:JSON.stringify({confirmationToken:e.confirmationToken,customFieldAnswers:e.customFieldAnswers,email:c,expectedAmountCents:r.amountCents,expectedAppliedDiscount:r.appliedDiscount,expectedConnectedAccountId:r.payment.connectedAccountId,expectedDiscountableSubtotalCents:r.discountableSubtotalCents,expectedDiscountCents:r.discountCents,expectedServiceFeeCents:r.serviceFeeCents,expectedSubtotalCents:r.subtotalCents,expectedTipCents:r.tipCents,expectedTotalCents:r.totalCents,...a,items:l,memberId:e.memberId,merchSize:e.merchSize,metadata:e.metadata,paymentReference:r.paymentReference,phone:e.phone,quoteContractVersion:1}),headers:{"Content-Type":`application/json`},method:`POST`},A,{code:`payment_submit_failed`,message:`Unable to submit the Lockerverse payment because the request failed.`,operation:`submit_payment`,report:!1},{code:`payment_submit_failed`,message:`Lockerverse returned an invalid payment confirmation.`,operation:`submit_payment`,report:!1});if(!s.ok)throw new p({code:`payment_submit_failed`,message:`Unable to submit the Lockerverse payment (${s.response.status}).`,operation:`submit_payment`,reportable:s.response.status>=500,status:s.response.status});let u=V(s.value);if(u.paymentReference!==r.paymentReference)throw new p({code:`payment_submit_failed`,message:`Lockerverse returned an invalid payment confirmation.`,operation:`submit_payment`,reportable:!0});return O.commit({catalog:n,payment:u,phase:`payment`,quote:r,selection:o}),V(u)}catch(e){let t=q(e,{code:`payment_submit_failed`,message:`Lockerverse returned an invalid payment confirmation.`,operation:`submit_payment`});throw K(t,r.paymentReference),M(t)}finally{T=!1}},subscribe:O.subscribe}}export{m as LOCKERVERSE_SDK_VERSION,p as LockerverseSdkError,H as createLockerverseCheckout};
|
|
2
2
|
//# sourceMappingURL=checkout.js.map
|
package/dist/checkout.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"checkout.js","names":[],"sources":["../src/checkout-environment.ts","../src/parsers.ts","../src/pricing.ts","../src/snapshots.ts","../src/checkout.ts"],"sourcesContent":["import { resolveResourceEnvironment } from \"./environment.ts\";\nimport type {\n CreateLockerverseWidgetOptions,\n LockerverseEnvironment,\n} from \"./types.ts\";\n\nconst STRIPE_PUBLISHABLE_KEYS: Record<LockerverseEnvironment, string> = {\n development:\n \"pk_test_51O7FkjDHAhgRuLtFHdkXdIe8T5i7rOVaG9PCtDetK3UUVKojVUEKHmQacGzigf9mOX1wz3zSOKoYwFjRcTfML9PU00OjJko2lk\",\n production:\n \"pk_live_51O7FkjDHAhgRuLtFlzLdxJrwo7F09WCKTlzT9lnBePjOGizWnuijkH9oCkoAddkmBT8ngIuqAPkDiHlPEAH4KXbz00Tm0DaPT4\",\n};\n\nexport function resolveWidgetEnvironment(\n options: CreateLockerverseWidgetOptions\n) {\n const runtime = resolveResourceEnvironment(options, \"widgetSlug\");\n return {\n ...runtime,\n stripePublishableKey: STRIPE_PUBLISHABLE_KEYS[runtime.environment],\n widgetSlug: runtime.resourceSlug,\n widgetSlugValue: runtime.resourceSlugValue,\n };\n}\n","import type {\n PublicCheckoutQuote,\n PublicProduct,\n PublicProductListing,\n PublicWidget,\n} from \"./contracts.ts\";\nimport {\n parseBoolean,\n parseCustomFields,\n parseNonEmptyString,\n parseNullableString,\n parseOptionalBoolean,\n parseOptionalNullableString,\n parseOptionalString,\n parseRecord,\n} from \"./parsing.ts\";\nimport type {\n LockerverseAppliedDiscount,\n LockerverseCheckoutLineItem,\n LockerversePaymentOption,\n LockerversePaymentResult,\n LockerversePaymentStatus,\n LockerverseWidgetFields,\n} from \"./types.ts\";\n\nfunction parseSafeInteger(value: unknown, minimum: number): number {\n if (!Number.isSafeInteger(value) || (value as number) < minimum) {\n throw new TypeError(\"Expected a safe integer.\");\n }\n\n return value as number;\n}\n\nfunction parseFiniteNumber(\n value: unknown,\n minimum: number,\n maximum: number\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isFinite(value) ||\n value < minimum ||\n value > maximum\n ) {\n throw new TypeError(\"Expected a bounded finite number.\");\n }\n return value;\n}\n\nfunction parseNullableSafeInteger(\n value: unknown,\n minimum: number\n): number | null {\n return value === null ? null : parseSafeInteger(value, minimum);\n}\n\nfunction parsePaymentOption(value: unknown): LockerversePaymentOption {\n if (value === \"one-time\" || value === \"monthly\" || value === \"annually\") {\n return value;\n }\n\n throw new TypeError(\"Expected a supported payment option.\");\n}\n\nfunction parsePricingMode(value: unknown): \"fixed\" | \"custom\" {\n if (value === \"fixed\" || value === \"custom\") {\n return value;\n }\n\n throw new TypeError(\"Expected a supported pricing mode.\");\n}\n\nfunction parsePaymentStatus(value: unknown): LockerversePaymentStatus {\n if (\n value === \"action_required\" ||\n value === \"failed\" ||\n value === \"pending\" ||\n value === \"success\"\n ) {\n return value;\n }\n\n throw new TypeError(\"Expected a supported payment status.\");\n}\n\nfunction parseAppliedDiscount(\n value: unknown\n): LockerverseAppliedDiscount | null {\n if (value === null) {\n return null;\n }\n const discount = parseRecord(value);\n if (discount.source !== \"email_list\" && discount.source !== \"promo_code\") {\n throw new TypeError(\"Expected a supported discount source.\");\n }\n const source = discount.source as LockerverseAppliedDiscount[\"source\"];\n return {\n percentageOff: parseFiniteNumber(discount.percentageOff, 0, 100),\n source,\n };\n}\n\nfunction parseWidgetFields(value: unknown): LockerverseWidgetFields {\n const fields = value === undefined ? {} : parseRecord(value);\n\n return {\n memberId: parseOptionalBoolean(fields.memberId, false),\n merchSize: parseOptionalBoolean(fields.merchSize, false),\n phone: parseOptionalBoolean(fields.phone, false),\n promoCode: parseOptionalBoolean(fields.promoCode, false),\n serviceFee: parseOptionalBoolean(fields.serviceFee, false),\n shipping: parseOptionalBoolean(fields.shipping, false),\n tipping: parseOptionalBoolean(fields.tipping, false),\n };\n}\n\nfunction parsePublicProduct(value: unknown): PublicProduct {\n const product = parseRecord(value);\n\n return {\n amountCents: parseNullableSafeInteger(product.amountCents, 0),\n description: parseOptionalNullableString(product.description, null),\n id: parseNonEmptyString(product.id),\n inventoryQuantity: parseNullableSafeInteger(product.inventoryQuantity, 0),\n maxQuantity: parseNullableSafeInteger(product.maxQuantity, 0),\n minimumAmountCents: parseNullableSafeInteger(product.minimumAmountCents, 0),\n minQuantity: parseNullableSafeInteger(product.minQuantity, 0),\n name: parseNonEmptyString(product.name),\n paymentOption: parsePaymentOption(product.paymentOption),\n pricingMode: parsePricingMode(product.pricingMode),\n };\n}\n\nfunction parseProductListing(value: unknown): PublicProductListing {\n const listing = parseRecord(value);\n\n return {\n acceptsDiscounts: parseOptionalBoolean(listing.acceptsDiscounts, false),\n id: parseNonEmptyString(listing.id),\n product: parsePublicProduct(listing.product),\n productId: parseNonEmptyString(listing.productId),\n slug: parseNonEmptyString(listing.slug),\n };\n}\n\nexport function parsePublicWidget(value: unknown): PublicWidget {\n const widget = parseRecord(value);\n const config = widget.config === undefined ? {} : parseRecord(widget.config);\n const pricingPolicy =\n widget.pricingPolicy === undefined\n ? { currency: \"usd\", serviceFeeRateBasisPoints: 0 }\n : parseRecord(widget.pricingPolicy);\n const products = widget.products === undefined ? [] : widget.products;\n if (!Array.isArray(products)) {\n throw new TypeError(\"Expected a Product array.\");\n }\n if (pricingPolicy.currency !== \"usd\") {\n throw new TypeError(\"Expected USD checkout pricing policy.\");\n }\n\n return {\n config: {\n customFields: parseCustomFields(config.customFields),\n fields: parseWidgetFields(config.fields),\n },\n description: parseOptionalNullableString(widget.description, null),\n id: parseOptionalString(widget.id, \"\"),\n name: parseOptionalString(widget.name, \"Lockerverse widget\"),\n pricingPolicy: {\n currency: \"usd\",\n serviceFeeRateBasisPoints: parseSafeInteger(\n pricingPolicy.serviceFeeRateBasisPoints,\n 0\n ),\n },\n products: products.map(parseProductListing),\n showCommunityBranding: parseOptionalBoolean(\n widget.showCommunityBranding,\n true\n ),\n title: parseOptionalNullableString(widget.title, null),\n };\n}\n\nfunction parseCheckoutLineItem(value: unknown): LockerverseCheckoutLineItem {\n const lineItem = parseRecord(value);\n\n return {\n acceptsDiscounts: parseBoolean(lineItem.acceptsDiscounts),\n listingId: parseNonEmptyString(lineItem.listingId),\n listingSlug: parseNonEmptyString(lineItem.listingSlug),\n paymentOption: parsePaymentOption(lineItem.paymentOption),\n pricingMode: parsePricingMode(lineItem.pricingMode),\n productId: parseNonEmptyString(lineItem.productId),\n productName: parseNonEmptyString(lineItem.productName),\n quantity: parseSafeInteger(lineItem.quantity, 1),\n subtotalCents: parseSafeInteger(lineItem.subtotalCents, 0),\n unitAmountCents: parseSafeInteger(lineItem.unitAmountCents, 0),\n };\n}\n\nexport function parseCheckoutQuote(value: unknown): PublicCheckoutQuote {\n const quote = parseRecord(value);\n if (!Array.isArray(quote.lineItems)) {\n throw new TypeError(\"Expected a line item array.\");\n }\n\n return {\n amountCents: parseSafeInteger(quote.amountCents, 0),\n appliedDiscount: parseAppliedDiscount(quote.appliedDiscount),\n connectedAccountId:\n quote.connectedAccountId === null\n ? null\n : parseNonEmptyString(quote.connectedAccountId),\n discountableSubtotalCents: parseSafeInteger(\n quote.discountableSubtotalCents,\n 0\n ),\n discountCents: parseSafeInteger(quote.discountCents, 0),\n lineItems: quote.lineItems.map(parseCheckoutLineItem),\n paymentOption: parsePaymentOption(quote.paymentOption),\n serviceFeeCents: parseSafeInteger(quote.serviceFeeCents, 0),\n subtotalCents: parseSafeInteger(quote.subtotalCents, 0),\n tipCents: parseSafeInteger(quote.tipCents, 0),\n totalCents: parseSafeInteger(quote.totalCents, 0),\n };\n}\n\nexport function parsePaymentResult(value: unknown): LockerversePaymentResult {\n const paymentResult = parseRecord(value);\n\n return {\n checkoutId: parseNonEmptyString(paymentResult.checkoutId),\n checkoutStatus: parsePaymentStatus(paymentResult.checkoutStatus),\n clientSecret: parseNullableString(paymentResult.clientSecret),\n paymentReference: parseNonEmptyString(paymentResult.paymentReference),\n requiresAction: parseBoolean(paymentResult.requiresAction),\n status: parseNullableString(paymentResult.status),\n };\n}\n","import type {\n LockerverseCatalog,\n LockerverseCheckoutPreview,\n LockerverseCheckoutPricingInput,\n LockerverseSelection,\n} from \"./types.ts\";\n\nconst BASIS_POINTS_PER_WHOLE = 10_000;\n\nfunction assertSafeCents(value: number, message: string) {\n if (!Number.isSafeInteger(value) || value < 0) {\n throw new TypeError(message);\n }\n return value;\n}\n\nfunction addCents(left: number, right: number) {\n return assertSafeCents(\n left + right,\n \"The selected checkout total is too large.\"\n );\n}\n\nfunction multiplyCents(value: number, quantity: number) {\n return assertSafeCents(\n value * quantity,\n \"The selected Product quantity produces an unsafe total.\"\n );\n}\n\nfunction calculateBasisPoints(value: number, basisPoints: number) {\n const rounded =\n (BigInt(value) * BigInt(basisPoints) + BigInt(BASIS_POINTS_PER_WHOLE / 2)) /\n BigInt(BASIS_POINTS_PER_WHOLE);\n if (rounded > BigInt(Number.MAX_SAFE_INTEGER)) {\n throw new TypeError(\"The selected checkout total is too large.\");\n }\n return Number(rounded);\n}\n\nexport function calculateCheckoutPreview(\n catalog: LockerverseCatalog,\n selection: LockerverseSelection,\n input: LockerverseCheckoutPricingInput\n): LockerverseCheckoutPreview {\n let subtotalCents = 0;\n let discountableSubtotalCents = 0;\n\n for (const item of selection.items) {\n const product = catalog.products.find(\n ({ id, slug }) => id === item.productId && slug === item.productSlug\n );\n if (!product) {\n throw new TypeError(\"The selected Product is no longer available.\");\n }\n if (product.paymentOption !== \"one-time\") {\n throw new TypeError(\n \"Recurring Products are not supported by this SDK checkout yet.\"\n );\n }\n const itemSubtotal =\n \"quantity\" in item\n ? multiplyCents(product.amountCents ?? 0, item.quantity)\n : item.amountCents;\n subtotalCents = addCents(subtotalCents, itemSubtotal);\n if (product.acceptsDiscounts) {\n discountableSubtotalCents = addCents(\n discountableSubtotalCents,\n itemSubtotal\n );\n }\n }\n\n const serviceFeeCents = input.includeServiceFee\n ? calculateBasisPoints(\n subtotalCents,\n catalog.pricingPolicy.serviceFeeRateBasisPoints\n )\n : 0;\n const tipCents = input.tipCents ?? 0;\n const amountCents = addCents(subtotalCents, serviceFeeCents);\n\n return {\n amountCents,\n appliedDiscount: null,\n authoritative: false,\n discountableSubtotalCents,\n discountCents: 0,\n serviceFeeCents,\n subtotalCents,\n tipCents,\n totalCents: addCents(amountCents, tipCents),\n };\n}\n","import type { PublicProductListing, PublicWidget } from \"./contracts.ts\";\nimport { deepFreeze } from \"./deep-freeze.ts\";\nimport type {\n LockerverseCatalog,\n LockerverseCheckoutTotal,\n LockerversePaymentResult,\n LockerverseProduct,\n} from \"./types.ts\";\n\nfunction mapProduct(listing: PublicProductListing): LockerverseProduct {\n const { product } = listing;\n\n return {\n acceptsDiscounts: listing.acceptsDiscounts ?? false,\n amountCents: product.amountCents,\n description: product.description ?? null,\n id: product.id,\n inventoryQuantity: product.inventoryQuantity,\n listingId: listing.id,\n maximumQuantity: product.maxQuantity,\n minimumAmountCents: product.minimumAmountCents,\n minimumQuantity: product.minQuantity,\n name: product.name,\n paymentOption: product.paymentOption,\n pricingMode: product.pricingMode,\n slug: listing.slug,\n };\n}\n\nexport function createCatalog(\n widget: PublicWidget,\n publishableKey: string\n): LockerverseCatalog {\n const fields = widget.config?.fields ?? {};\n\n return {\n payment: {\n currency: \"usd\",\n publishableKey,\n },\n pricingPolicy: {\n currency: \"usd\",\n serviceFeeRateBasisPoints:\n widget.pricingPolicy?.serviceFeeRateBasisPoints ?? 0,\n },\n products: (widget.products ?? []).map(mapProduct),\n widget: {\n customFields: widget.config?.customFields ?? [],\n description: widget.description ?? null,\n fields: {\n memberId: fields.memberId ?? false,\n merchSize: fields.merchSize ?? false,\n phone: fields.phone ?? false,\n promoCode: fields.promoCode ?? false,\n serviceFee: fields.serviceFee ?? false,\n shipping: fields.shipping ?? false,\n tipping: fields.tipping ?? false,\n },\n id: widget.id ?? \"\",\n name: widget.name ?? \"Lockerverse widget\",\n showCommunityBranding: widget.showCommunityBranding ?? true,\n title: widget.title ?? null,\n },\n };\n}\n\nexport function cloneCatalog(catalog: LockerverseCatalog): LockerverseCatalog {\n return deepFreeze({\n payment: { ...catalog.payment },\n pricingPolicy: { ...catalog.pricingPolicy },\n products: catalog.products.map((product) => ({ ...product })),\n widget: {\n ...catalog.widget,\n customFields: catalog.widget.customFields.map((field) =>\n \"options\" in field\n ? {\n ...field,\n options: field.options.map((option) => ({ ...option })),\n }\n : { ...field }\n ),\n fields: { ...catalog.widget.fields },\n },\n });\n}\n\nexport function cloneCheckoutTotal(\n total: LockerverseCheckoutTotal\n): LockerverseCheckoutTotal {\n return deepFreeze({\n ...total,\n appliedDiscount: total.appliedDiscount\n ? { ...total.appliedDiscount }\n : null,\n lineItems: total.lineItems.map((lineItem) => ({ ...lineItem })),\n payment: { ...total.payment },\n });\n}\n\nexport function clonePaymentResult(\n paymentResult: LockerversePaymentResult\n): LockerversePaymentResult {\n return deepFreeze({ ...paymentResult });\n}\n","import { resolveWidgetEnvironment } from \"./checkout-environment.ts\";\nimport type { PublicCheckoutQuote } from \"./contracts.ts\";\nimport { deepFreeze } from \"./deep-freeze.ts\";\nimport { createSdkErrorReporter } from \"./error-reporting.ts\";\nimport {\n parseCheckoutQuote,\n parsePaymentResult,\n parsePublicWidget,\n} from \"./parsers.ts\";\nimport { calculateCheckoutPreview } from \"./pricing.ts\";\nimport {\n cloneCatalog,\n cloneCheckoutTotal,\n clonePaymentResult,\n createCatalog,\n} from \"./snapshots.ts\";\nimport { createStateStore } from \"./state.ts\";\nimport { createTransport } from \"./transport.ts\";\nimport {\n type CreateLockerverseWidgetOptions,\n type LockerverseCatalog,\n type LockerverseCheckoutPreview,\n type LockerverseCheckoutPricingInput,\n type LockerverseCheckoutTotal,\n LockerverseSdkError,\n type LockerverseSdkOperation,\n type LockerverseSelection,\n type LockerverseWidget,\n type LockerverseWidgetState,\n} from \"./types.ts\";\n\nexport function createLockerverseCheckout(\n options: CreateLockerverseWidgetOptions\n): LockerverseWidget {\n const {\n apiBaseUrl,\n communitySlug,\n communitySlugValue,\n environment,\n fetchImplementation,\n onError,\n sentryDsn,\n stripePublishableKey,\n widgetSlug,\n widgetSlugValue,\n } = resolveWidgetEnvironment(options);\n let catalog: LockerverseCatalog | null = null;\n let calculatedTotal: LockerverseCheckoutTotal | null = null;\n let calculatedPricingInput: LockerverseCheckoutPricingInput | null = null;\n let latestPaymentReference: string | null = null;\n let latestPreview: LockerverseCheckoutPreview | null = null;\n let quoteGeneration = 0;\n let stateRevision = 0;\n let submitting = false;\n const selection = new Map<\n string,\n { amountCents: number } | { quantity: number }\n >();\n const stateStore = createStateStore<LockerverseWidgetState>({\n phase: \"idle\",\n selection: deepFreeze({ items: [] }),\n });\n\n function getProduct(productSlug: string) {\n const currentCatalog = catalog;\n const product = currentCatalog\n ? currentCatalog.products.find(({ slug }) => slug === productSlug)\n : undefined;\n\n if (!product) {\n throw new Error(`Lockerverse Product \"${productSlug}\" is unavailable.`);\n }\n\n return product;\n }\n\n const reportError = createSdkErrorReporter({\n communitySlug: communitySlugValue,\n environment,\n getContext: () => ({\n paymentReference: latestPaymentReference,\n widgetSlug: widgetSlugValue,\n }),\n onError,\n resourceContextName: \"lockerverse_widget\",\n sentryDsn,\n });\n\n function invalidSelection(\n message: string,\n operation: LockerverseSdkOperation = \"update_selection\"\n ): never {\n throw reportError(\n new LockerverseSdkError({\n code: \"invalid_selection\",\n message,\n operation,\n reportable: false,\n })\n );\n }\n\n const { fetchResponse, parseResponseJson } = createTransport(\n fetchImplementation,\n reportError\n );\n\n function getSelection(): LockerverseSelection {\n const currentCatalog = catalog;\n return deepFreeze({\n items: (currentCatalog ? currentCatalog.products : []).flatMap(\n (product) => {\n const selected = selection.get(product.slug);\n return selected\n ? [\n {\n productId: product.id,\n productSlug: product.slug,\n ...selected,\n },\n ]\n : [];\n }\n ),\n });\n }\n\n function invalidateCalculatedTotal() {\n calculatedTotal = null;\n calculatedPricingInput = null;\n latestPaymentReference = null;\n latestPreview = null;\n }\n\n function ensureSelectionMutable() {\n if (submitting) {\n invalidSelection(\n \"Selection cannot change while a payment is being submitted.\"\n );\n }\n }\n\n function ensureOperationAvailable(operation: LockerverseSdkOperation) {\n if (submitting) {\n invalidSelection(\n \"This operation cannot run while a payment is being submitted.\",\n operation\n );\n }\n }\n\n function reviseState() {\n stateRevision += 1;\n invalidateCalculatedTotal();\n }\n\n function commitReady(preview: LockerverseCheckoutPreview | null = null) {\n if (!catalog) {\n return;\n }\n stateStore.commit({\n catalog,\n phase: \"ready\",\n preview,\n selection: getSelection(),\n });\n }\n\n function commitError(\n error: LockerverseSdkError,\n recoverablePaymentReference: string | null = null\n ) {\n stateStore.commit({\n catalog,\n error,\n phase: \"error\",\n recoverablePaymentReference,\n selection: getSelection(),\n });\n }\n\n function rejectSupersededQuote(\n requestedStateRevision: number,\n requestedQuoteGeneration: number\n ) {\n if (\n requestedStateRevision === stateRevision &&\n requestedQuoteGeneration === quoteGeneration\n ) {\n return;\n }\n\n throw reportError(\n new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message:\n \"This Lockerverse checkout total was superseded. Calculate the total again for the current selection.\",\n operation: \"calculate_total\",\n reportable: false,\n })\n );\n }\n\n function previewTotal(input: LockerverseCheckoutPricingInput = {}) {\n ensureOperationAvailable(\"calculate_total\");\n if (!catalog) {\n throw new Error(\n \"Load the Lockerverse widget before previewing the total.\"\n );\n }\n if (selection.size === 0) {\n invalidSelection(\"Select at least one Product before previewing.\");\n }\n const normalizedInput = normalizePricingInput(catalog, input);\n reviseState();\n\n try {\n const preview = deepFreeze(\n calculateCheckoutPreview(catalog, getSelection(), normalizedInput)\n );\n latestPreview = preview;\n commitReady(preview);\n return preview;\n } catch (error) {\n invalidSelection(\n error instanceof Error ? error.message : \"Unable to preview checkout.\"\n );\n }\n }\n\n function normalizePricingInput(\n currentCatalog: LockerverseCatalog,\n input: LockerverseCheckoutPricingInput\n ): LockerverseCheckoutPricingInput {\n validatePricingInput(currentCatalog, input);\n const tipCents = input.tipCents ?? 0;\n const email = input.email?.trim().toLowerCase();\n const promoCode = input.promoCode?.trim();\n return {\n ...(email ? { email } : {}),\n ...(input.includeServiceFee === undefined\n ? {}\n : { includeServiceFee: input.includeServiceFee }),\n ...(promoCode ? { promoCode } : {}),\n ...(input.tipCents === undefined ? {} : { tipCents }),\n };\n }\n\n function validatePricingInput(\n currentCatalog: LockerverseCatalog,\n input: LockerverseCheckoutPricingInput\n ) {\n const tipCents = input.tipCents ?? 0;\n if (!Number.isSafeInteger(tipCents) || tipCents < 0) {\n invalidSelection(\"Tip must be a non-negative whole number of cents.\");\n }\n if (input.includeServiceFee && !currentCatalog.widget.fields.serviceFee) {\n invalidSelection(\"Service fee is not enabled for this widget.\");\n }\n if (\n input.includeServiceFee &&\n currentCatalog.pricingPolicy.serviceFeeRateBasisPoints === 0\n ) {\n invalidSelection(\n \"Service fee pricing is unavailable. Reload the widget and try again.\"\n );\n }\n if (tipCents > 0 && !currentCatalog.widget.fields.tipping) {\n invalidSelection(\"Tipping is not enabled for this widget.\");\n }\n }\n\n async function calculateTotal(input: LockerverseCheckoutPricingInput = {}) {\n ensureOperationAvailable(\"calculate_total\");\n if (!catalog) {\n throw new Error(\n \"Load the Lockerverse widget before calculating the total.\"\n );\n }\n\n const normalizedInput = normalizePricingInput(catalog, input);\n if (selection.size === 0) {\n invalidSelection(\n \"Select at least one Product before calculating the total.\",\n \"calculate_total\"\n );\n }\n const currentSelection = getSelection();\n const preview = deepFreeze(\n calculateCheckoutPreview(catalog, currentSelection, normalizedInput)\n );\n latestPreview = preview;\n stateStore.commit({\n catalog,\n phase: \"quoting\",\n preview,\n selection: currentSelection,\n });\n const items = currentSelection.items.map(\n ({ productSlug: _productSlug, ...item }) => item\n );\n const requestedStateRevision = stateRevision;\n const requestedQuoteGeneration = quoteGeneration + 1;\n quoteGeneration = requestedQuoteGeneration;\n calculatedTotal = null;\n latestPaymentReference = null;\n let response: Response;\n\n try {\n response = await fetchResponse(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/quote`,\n {\n body: JSON.stringify({ ...normalizedInput, items }),\n headers: { \"Content-Type\": \"application/json\" },\n method: \"POST\",\n },\n {\n code: \"total_calculation_failed\",\n message:\n \"Unable to calculate the Lockerverse checkout total because the request failed.\",\n operation: \"calculate_total\",\n report: false,\n }\n );\n } catch (error) {\n rejectSupersededQuote(requestedStateRevision, requestedQuoteGeneration);\n if (error instanceof LockerverseSdkError) {\n commitError(error);\n throw reportError(error);\n }\n throw error;\n }\n\n rejectSupersededQuote(requestedStateRevision, requestedQuoteGeneration);\n\n if (!response.ok) {\n const error = new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message: `Unable to calculate the Lockerverse checkout total (${response.status}).`,\n operation: \"calculate_total\",\n reportable: response.status >= 500,\n status: response.status,\n });\n commitError(error);\n throw reportError(error);\n }\n\n let serverTotal: PublicCheckoutQuote;\n try {\n serverTotal = await parseResponseJson(response, parseCheckoutQuote, {\n code: \"total_calculation_failed\",\n message: \"Lockerverse returned an invalid checkout total.\",\n operation: \"calculate_total\",\n report: false,\n });\n if (serverTotal.paymentOption !== \"one-time\") {\n throw new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message: \"Lockerverse returned an unsupported checkout cadence.\",\n operation: \"calculate_total\",\n reportable: true,\n });\n }\n } catch (error) {\n rejectSupersededQuote(requestedStateRevision, requestedQuoteGeneration);\n if (error instanceof LockerverseSdkError) {\n commitError(error);\n throw reportError(error);\n }\n throw error;\n }\n rejectSupersededQuote(requestedStateRevision, requestedQuoteGeneration);\n const paymentReference = globalThis.crypto.randomUUID();\n const {\n connectedAccountId,\n paymentOption: _paymentOption,\n ...total\n } = serverTotal;\n const nextCalculatedTotal = deepFreeze({\n ...total,\n authoritative: true as const,\n payment: {\n ...catalog.payment,\n connectedAccountId,\n },\n paymentOption: \"one-time\" as const,\n paymentReference,\n });\n calculatedTotal = nextCalculatedTotal;\n calculatedPricingInput = deepFreeze({ ...normalizedInput });\n latestPaymentReference = paymentReference;\n stateStore.commit({\n catalog,\n phase: \"quoted\",\n preview,\n quote: nextCalculatedTotal,\n selection: currentSelection,\n });\n return cloneCheckoutTotal(nextCalculatedTotal);\n }\n\n return {\n calculateTotal,\n clear() {\n ensureSelectionMutable();\n selection.clear();\n reviseState();\n commitReady();\n },\n async getPaymentStatus(paymentReference = latestPaymentReference ?? \"\") {\n ensureOperationAvailable(\"get_payment_status\");\n if (!paymentReference) {\n invalidSelection(\n \"Provide a payment reference to recover its status.\",\n \"get_payment_status\"\n );\n }\n latestPaymentReference = paymentReference;\n const currentSelection = getSelection();\n stateStore.commit({\n catalog,\n paymentReference,\n phase: \"recovering\",\n selection: currentSelection,\n });\n try {\n const response = await fetchResponse(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/${encodeURIComponent(paymentReference)}/status`,\n undefined,\n {\n code: \"payment_status_failed\",\n message:\n \"Unable to recover the Lockerverse payment status because the request failed.\",\n operation: \"get_payment_status\",\n }\n );\n\n if (!response.ok) {\n throw reportError(\n new LockerverseSdkError({\n code: \"payment_status_failed\",\n message: `Unable to recover the Lockerverse payment status (${response.status}).`,\n operation: \"get_payment_status\",\n reportable: response.status >= 500,\n status: response.status,\n })\n );\n }\n\n const payment = clonePaymentResult(\n await parseResponseJson(response, parsePaymentResult, {\n code: \"payment_status_failed\",\n message: \"Lockerverse returned an invalid payment status.\",\n operation: \"get_payment_status\",\n })\n );\n stateStore.commit({\n catalog,\n payment,\n phase: \"payment\",\n quote:\n calculatedTotal?.paymentReference === paymentReference\n ? calculatedTotal\n : null,\n selection: currentSelection,\n });\n return clonePaymentResult(payment);\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n commitError(error, paymentReference);\n }\n throw error;\n }\n },\n getSelection,\n getState: stateStore.getState,\n async load() {\n ensureOperationAvailable(\"load_widget\");\n reviseState();\n stateStore.commit({ phase: \"loading\", selection: getSelection() });\n const requestContext = {\n code: \"widget_load_failed\" as const,\n message:\n \"Unable to load Lockerverse widget because the request failed.\",\n operation: \"load_widget\" as const,\n report: false,\n };\n let widgetResponse: Response;\n\n try {\n widgetResponse = await fetchResponse(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}`,\n undefined,\n requestContext\n );\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n commitError(error);\n throw reportError(error);\n }\n throw error;\n }\n\n if (!widgetResponse.ok) {\n const error = new LockerverseSdkError({\n code: \"widget_load_failed\",\n message: `Unable to load Lockerverse widget (${widgetResponse.status}).`,\n operation: \"load_widget\",\n reportable: widgetResponse.status >= 500,\n status: widgetResponse.status,\n });\n commitError(error);\n throw reportError(error);\n }\n\n const widget = await parseResponseJson(\n widgetResponse,\n parsePublicWidget,\n {\n code: \"widget_load_failed\",\n message: \"Lockerverse returned an invalid widget catalog.\",\n operation: \"load_widget\",\n }\n );\n\n selection.clear();\n catalog = deepFreeze(createCatalog(widget, stripePublishableKey));\n commitReady();\n\n return cloneCatalog(catalog);\n },\n previewTotal,\n remove(productSlug) {\n ensureSelectionMutable();\n selection.delete(productSlug);\n reviseState();\n commitReady();\n },\n setAmount(productSlug, amountCents) {\n ensureSelectionMutable();\n const product = getProduct(productSlug);\n\n if (product.pricingMode !== \"custom\") {\n invalidSelection(\"Fixed-price Products do not accept custom amounts.\");\n }\n if (!Number.isSafeInteger(amountCents) || amountCents <= 0) {\n invalidSelection(\"Product amount must be a positive integer in cents.\");\n }\n if (\n product.minimumAmountCents !== null &&\n amountCents < product.minimumAmountCents\n ) {\n invalidSelection(\n `Product amount must be at least ${product.minimumAmountCents} cents.`\n );\n }\n\n selection.set(productSlug, { amountCents });\n reviseState();\n commitReady();\n },\n setQuantity(productSlug, quantity) {\n ensureSelectionMutable();\n const product = getProduct(productSlug);\n\n if (product.pricingMode !== \"fixed\") {\n invalidSelection(\"Custom-amount Products do not accept quantities.\");\n }\n if (!Number.isSafeInteger(quantity) || quantity <= 0) {\n invalidSelection(\"Product quantity must be a positive integer.\");\n }\n if (\n product.minimumQuantity !== null &&\n quantity < product.minimumQuantity\n ) {\n invalidSelection(\n `Product quantity must be at least ${product.minimumQuantity}.`\n );\n }\n if (\n product.maximumQuantity !== null &&\n quantity > product.maximumQuantity\n ) {\n invalidSelection(\n `Product quantity must not exceed ${product.maximumQuantity}.`\n );\n }\n if (\n product.inventoryQuantity !== null &&\n quantity > product.inventoryQuantity\n ) {\n invalidSelection(\"Requested Product quantity is unavailable.\");\n }\n\n selection.set(productSlug, { quantity });\n reviseState();\n commitReady();\n },\n async submitPayment(submission) {\n if (!(catalog && calculatedTotal && calculatedPricingInput)) {\n invalidSelection(\n \"Calculate the current total before submitting a payment.\",\n \"submit_payment\"\n );\n }\n if (submitting) {\n invalidSelection(\n \"A Lockerverse payment is already being submitted.\",\n \"submit_payment\"\n );\n }\n\n const transactionCatalog = catalog;\n const transactionQuote = calculatedTotal;\n const transactionPricingInput = calculatedPricingInput;\n const transactionSelection = getSelection();\n const transactionPreview =\n latestPreview ??\n calculateCheckoutPreview(\n transactionCatalog,\n transactionSelection,\n transactionPricingInput\n );\n const normalizedEmail = submission.email.trim().toLowerCase();\n if (\n !normalizedEmail ||\n normalizedEmail !== transactionPricingInput.email\n ) {\n invalidSelection(\n \"Payment email must match the current checkout quote.\",\n \"submit_payment\"\n );\n }\n\n const items = transactionSelection.items.map(\n ({ productSlug: _productSlug, ...item }) => item\n );\n submitting = true;\n stateStore.commit({\n catalog: transactionCatalog,\n phase: \"submitting\",\n preview: transactionPreview,\n quote: transactionQuote,\n selection: transactionSelection,\n });\n try {\n const response = await fetchResponse(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/confirm`,\n {\n body: JSON.stringify({\n confirmationToken: submission.confirmationToken,\n customFieldAnswers: submission.customFieldAnswers,\n email: normalizedEmail,\n expectedAmountCents: transactionQuote.amountCents,\n expectedAppliedDiscount: transactionQuote.appliedDiscount,\n expectedConnectedAccountId:\n transactionQuote.payment.connectedAccountId,\n expectedDiscountableSubtotalCents:\n transactionQuote.discountableSubtotalCents,\n expectedDiscountCents: transactionQuote.discountCents,\n expectedServiceFeeCents: transactionQuote.serviceFeeCents,\n expectedSubtotalCents: transactionQuote.subtotalCents,\n expectedTipCents: transactionQuote.tipCents,\n expectedTotalCents: transactionQuote.totalCents,\n ...transactionPricingInput,\n items,\n memberId: submission.memberId,\n merchSize: submission.merchSize,\n metadata: submission.metadata,\n paymentReference: transactionQuote.paymentReference,\n phone: submission.phone,\n quoteContractVersion: 1,\n }),\n headers: { \"Content-Type\": \"application/json\" },\n method: \"POST\",\n },\n {\n code: \"payment_submit_failed\",\n message:\n \"Unable to submit the Lockerverse payment because the request failed.\",\n operation: \"submit_payment\",\n }\n );\n\n if (!response.ok) {\n throw reportError(\n new LockerverseSdkError({\n code: \"payment_submit_failed\",\n message: `Unable to submit the Lockerverse payment (${response.status}).`,\n operation: \"submit_payment\",\n reportable: response.status >= 500,\n status: response.status,\n })\n );\n }\n\n const payment = clonePaymentResult(\n await parseResponseJson(response, parsePaymentResult, {\n code: \"payment_submit_failed\",\n message: \"Lockerverse returned an invalid payment confirmation.\",\n operation: \"submit_payment\",\n })\n );\n stateStore.commit({\n catalog: transactionCatalog,\n payment,\n phase: \"payment\",\n quote: transactionQuote,\n selection: transactionSelection,\n });\n return clonePaymentResult(payment);\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n commitError(error, transactionQuote.paymentReference);\n }\n throw error;\n } finally {\n submitting = false;\n }\n },\n subscribe: stateStore.subscribe,\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"checkout.js","names":[],"sources":["../src/checkout-environment.ts","../src/parsers.ts","../src/pricing.ts","../src/snapshots.ts","../src/checkout.ts"],"sourcesContent":["import { resolveResourceEnvironment } from \"./environment.ts\";\nimport type {\n CreateLockerverseWidgetOptions,\n LockerverseEnvironment,\n} from \"./types.ts\";\n\nconst STRIPE_PUBLISHABLE_KEYS: Record<LockerverseEnvironment, string> = {\n development:\n \"pk_test_51O7FkjDHAhgRuLtFHdkXdIe8T5i7rOVaG9PCtDetK3UUVKojVUEKHmQacGzigf9mOX1wz3zSOKoYwFjRcTfML9PU00OjJko2lk\",\n production:\n \"pk_live_51O7FkjDHAhgRuLtFlzLdxJrwo7F09WCKTlzT9lnBePjOGizWnuijkH9oCkoAddkmBT8ngIuqAPkDiHlPEAH4KXbz00Tm0DaPT4\",\n};\n\nexport function resolveWidgetEnvironment(\n options: CreateLockerverseWidgetOptions\n) {\n const runtime = resolveResourceEnvironment(options, \"widgetSlug\");\n return {\n ...runtime,\n stripePublishableKey: STRIPE_PUBLISHABLE_KEYS[runtime.environment],\n widgetSlug: runtime.resourceSlug,\n widgetSlugValue: runtime.resourceSlugValue,\n };\n}\n","import type {\n PublicCheckoutQuote,\n PublicProduct,\n PublicProductListing,\n PublicWidget,\n} from \"./contracts.ts\";\nimport {\n parseBoolean,\n parseCustomFields,\n parseNonEmptyString,\n parseNullableString,\n parseOptionalBoolean,\n parseOptionalNullableString,\n parseOptionalString,\n parseRecord,\n} from \"./parsing.ts\";\nimport type {\n LockerverseAppliedDiscount,\n LockerverseCheckoutLineItem,\n LockerversePaymentOption,\n LockerversePaymentResult,\n LockerversePaymentStatus,\n LockerverseWidgetFields,\n} from \"./types.ts\";\n\nfunction parseSafeInteger(value: unknown, minimum: number): number {\n if (!Number.isSafeInteger(value) || (value as number) < minimum) {\n throw new TypeError(\"Expected a safe integer.\");\n }\n\n return value as number;\n}\n\nfunction parseFiniteNumber(\n value: unknown,\n minimum: number,\n maximum: number\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isFinite(value) ||\n value < minimum ||\n value > maximum\n ) {\n throw new TypeError(\"Expected a bounded finite number.\");\n }\n return value;\n}\n\nfunction parseNullableSafeInteger(\n value: unknown,\n minimum: number\n): number | null {\n return value === null ? null : parseSafeInteger(value, minimum);\n}\n\nfunction parsePaymentOption(value: unknown): LockerversePaymentOption {\n if (value === \"one-time\" || value === \"monthly\" || value === \"annually\") {\n return value;\n }\n\n throw new TypeError(\"Expected a supported payment option.\");\n}\n\nfunction parsePricingMode(value: unknown): \"fixed\" | \"custom\" {\n if (value === \"fixed\" || value === \"custom\") {\n return value;\n }\n\n throw new TypeError(\"Expected a supported pricing mode.\");\n}\n\nfunction parsePaymentStatus(value: unknown): LockerversePaymentStatus {\n if (\n value === \"action_required\" ||\n value === \"failed\" ||\n value === \"pending\" ||\n value === \"success\"\n ) {\n return value;\n }\n\n throw new TypeError(\"Expected a supported payment status.\");\n}\n\nfunction parseAppliedDiscount(\n value: unknown\n): LockerverseAppliedDiscount | null {\n if (value === null) {\n return null;\n }\n const discount = parseRecord(value);\n if (discount.source !== \"email_list\" && discount.source !== \"promo_code\") {\n throw new TypeError(\"Expected a supported discount source.\");\n }\n const source = discount.source as LockerverseAppliedDiscount[\"source\"];\n return {\n percentageOff: parseFiniteNumber(discount.percentageOff, 0, 100),\n source,\n };\n}\n\nfunction parseWidgetFields(value: unknown): LockerverseWidgetFields {\n const fields = value === undefined ? {} : parseRecord(value);\n\n return {\n memberId: parseOptionalBoolean(fields.memberId, false),\n merchSize: parseOptionalBoolean(fields.merchSize, false),\n phone: parseOptionalBoolean(fields.phone, false),\n promoCode: parseOptionalBoolean(fields.promoCode, false),\n serviceFee: parseOptionalBoolean(fields.serviceFee, false),\n shipping: parseOptionalBoolean(fields.shipping, false),\n tipping: parseOptionalBoolean(fields.tipping, false),\n };\n}\n\nfunction parsePublicProduct(value: unknown): PublicProduct {\n const product = parseRecord(value);\n\n return {\n amountCents: parseNullableSafeInteger(product.amountCents, 0),\n description: parseOptionalNullableString(product.description, null),\n id: parseNonEmptyString(product.id),\n inventoryQuantity: parseNullableSafeInteger(product.inventoryQuantity, 0),\n maxQuantity: parseNullableSafeInteger(product.maxQuantity, 0),\n minimumAmountCents: parseNullableSafeInteger(product.minimumAmountCents, 0),\n minQuantity: parseNullableSafeInteger(product.minQuantity, 0),\n name: parseNonEmptyString(product.name),\n paymentOption: parsePaymentOption(product.paymentOption),\n pricingMode: parsePricingMode(product.pricingMode),\n };\n}\n\nfunction parseProductListing(value: unknown): PublicProductListing {\n const listing = parseRecord(value);\n\n return {\n acceptsDiscounts: parseOptionalBoolean(listing.acceptsDiscounts, false),\n id: parseNonEmptyString(listing.id),\n product: parsePublicProduct(listing.product),\n productId: parseNonEmptyString(listing.productId),\n slug: parseNonEmptyString(listing.slug),\n };\n}\n\nexport function parsePublicWidget(value: unknown): PublicWidget {\n const widget = parseRecord(value);\n const config = widget.config === undefined ? {} : parseRecord(widget.config);\n const pricingPolicy =\n widget.pricingPolicy === undefined\n ? { currency: \"usd\", serviceFeeRateBasisPoints: 0 }\n : parseRecord(widget.pricingPolicy);\n const products = widget.products === undefined ? [] : widget.products;\n if (!Array.isArray(products)) {\n throw new TypeError(\"Expected a Product array.\");\n }\n if (pricingPolicy.currency !== \"usd\") {\n throw new TypeError(\"Expected USD checkout pricing policy.\");\n }\n\n return {\n config: {\n customFields: parseCustomFields(config.customFields),\n fields: parseWidgetFields(config.fields),\n },\n description: parseOptionalNullableString(widget.description, null),\n id: parseOptionalString(widget.id, \"\"),\n name: parseOptionalString(widget.name, \"Lockerverse widget\"),\n pricingPolicy: {\n currency: \"usd\",\n serviceFeeRateBasisPoints: parseSafeInteger(\n pricingPolicy.serviceFeeRateBasisPoints,\n 0\n ),\n },\n products: products.map(parseProductListing),\n showCommunityBranding: parseOptionalBoolean(\n widget.showCommunityBranding,\n true\n ),\n title: parseOptionalNullableString(widget.title, null),\n };\n}\n\nfunction parseCheckoutLineItem(value: unknown): LockerverseCheckoutLineItem {\n const lineItem = parseRecord(value);\n\n return {\n acceptsDiscounts: parseBoolean(lineItem.acceptsDiscounts),\n listingId: parseNonEmptyString(lineItem.listingId),\n listingSlug: parseNonEmptyString(lineItem.listingSlug),\n paymentOption: parsePaymentOption(lineItem.paymentOption),\n pricingMode: parsePricingMode(lineItem.pricingMode),\n productId: parseNonEmptyString(lineItem.productId),\n productName: parseNonEmptyString(lineItem.productName),\n quantity: parseSafeInteger(lineItem.quantity, 1),\n subtotalCents: parseSafeInteger(lineItem.subtotalCents, 0),\n unitAmountCents: parseSafeInteger(lineItem.unitAmountCents, 0),\n };\n}\n\nexport function parseCheckoutQuote(value: unknown): PublicCheckoutQuote {\n const quote = parseRecord(value);\n if (!Array.isArray(quote.lineItems)) {\n throw new TypeError(\"Expected a line item array.\");\n }\n\n return {\n amountCents: parseSafeInteger(quote.amountCents, 0),\n appliedDiscount: parseAppliedDiscount(quote.appliedDiscount),\n connectedAccountId:\n quote.connectedAccountId === null\n ? null\n : parseNonEmptyString(quote.connectedAccountId),\n discountableSubtotalCents: parseSafeInteger(\n quote.discountableSubtotalCents,\n 0\n ),\n discountCents: parseSafeInteger(quote.discountCents, 0),\n lineItems: quote.lineItems.map(parseCheckoutLineItem),\n paymentOption: parsePaymentOption(quote.paymentOption),\n serviceFeeCents: parseSafeInteger(quote.serviceFeeCents, 0),\n subtotalCents: parseSafeInteger(quote.subtotalCents, 0),\n tipCents: parseSafeInteger(quote.tipCents, 0),\n totalCents: parseSafeInteger(quote.totalCents, 0),\n };\n}\n\nexport function parsePaymentResult(value: unknown): LockerversePaymentResult {\n const paymentResult = parseRecord(value);\n\n return {\n checkoutId: parseNonEmptyString(paymentResult.checkoutId),\n checkoutStatus: parsePaymentStatus(paymentResult.checkoutStatus),\n clientSecret: parseNullableString(paymentResult.clientSecret),\n paymentReference: parseNonEmptyString(paymentResult.paymentReference),\n requiresAction: parseBoolean(paymentResult.requiresAction),\n status: parseNullableString(paymentResult.status),\n };\n}\n","import type {\n LockerverseCatalog,\n LockerverseCheckoutPreview,\n LockerverseCheckoutPricingInput,\n LockerverseSelection,\n} from \"./types.ts\";\n\nconst BASIS_POINTS_PER_WHOLE = 10_000;\n\nfunction assertSafeCents(value: number, message: string) {\n if (!Number.isSafeInteger(value) || value < 0) {\n throw new TypeError(message);\n }\n return value;\n}\n\nfunction addCents(left: number, right: number) {\n return assertSafeCents(\n left + right,\n \"The selected checkout total is too large.\"\n );\n}\n\nfunction multiplyCents(value: number, quantity: number) {\n return assertSafeCents(\n value * quantity,\n \"The selected Product quantity produces an unsafe total.\"\n );\n}\n\nfunction calculateBasisPoints(value: number, basisPoints: number) {\n const rounded =\n (BigInt(value) * BigInt(basisPoints) + BigInt(BASIS_POINTS_PER_WHOLE / 2)) /\n BigInt(BASIS_POINTS_PER_WHOLE);\n if (rounded > BigInt(Number.MAX_SAFE_INTEGER)) {\n throw new TypeError(\"The selected checkout total is too large.\");\n }\n return Number(rounded);\n}\n\nexport function calculateCheckoutPreview(\n catalog: LockerverseCatalog,\n selection: LockerverseSelection,\n input: LockerverseCheckoutPricingInput\n): LockerverseCheckoutPreview {\n let subtotalCents = 0;\n let discountableSubtotalCents = 0;\n\n for (const item of selection.items) {\n const product = catalog.products.find(\n ({ id, slug }) => id === item.productId && slug === item.productSlug\n );\n if (!product) {\n throw new TypeError(\"The selected Product is no longer available.\");\n }\n if (product.paymentOption !== \"one-time\") {\n throw new TypeError(\n \"Recurring Products are not supported by this SDK checkout yet.\"\n );\n }\n const itemSubtotal =\n \"quantity\" in item\n ? multiplyCents(product.amountCents ?? 0, item.quantity)\n : item.amountCents;\n subtotalCents = addCents(subtotalCents, itemSubtotal);\n if (product.acceptsDiscounts) {\n discountableSubtotalCents = addCents(\n discountableSubtotalCents,\n itemSubtotal\n );\n }\n }\n\n const serviceFeeCents = input.includeServiceFee\n ? calculateBasisPoints(\n subtotalCents,\n catalog.pricingPolicy.serviceFeeRateBasisPoints\n )\n : 0;\n const tipCents = input.tipCents ?? 0;\n const amountCents = addCents(subtotalCents, serviceFeeCents);\n\n return {\n amountCents,\n appliedDiscount: null,\n authoritative: false,\n discountableSubtotalCents,\n discountCents: 0,\n serviceFeeCents,\n subtotalCents,\n tipCents,\n totalCents: addCents(amountCents, tipCents),\n };\n}\n","import type { PublicProductListing, PublicWidget } from \"./contracts.ts\";\nimport { deepFreeze } from \"./deep-freeze.ts\";\nimport type {\n LockerverseCatalog,\n LockerverseCheckoutTotal,\n LockerversePaymentResult,\n LockerverseProduct,\n} from \"./types.ts\";\n\nfunction mapProduct(listing: PublicProductListing): LockerverseProduct {\n const { product } = listing;\n\n return {\n acceptsDiscounts: listing.acceptsDiscounts ?? false,\n amountCents: product.amountCents,\n description: product.description ?? null,\n id: product.id,\n inventoryQuantity: product.inventoryQuantity,\n listingId: listing.id,\n maximumQuantity: product.maxQuantity,\n minimumAmountCents: product.minimumAmountCents,\n minimumQuantity: product.minQuantity,\n name: product.name,\n paymentOption: product.paymentOption,\n pricingMode: product.pricingMode,\n slug: listing.slug,\n };\n}\n\nexport function createCatalog(\n widget: PublicWidget,\n publishableKey: string\n): LockerverseCatalog {\n const fields = widget.config?.fields ?? {};\n\n return {\n payment: {\n currency: \"usd\",\n publishableKey,\n },\n pricingPolicy: {\n currency: \"usd\",\n serviceFeeRateBasisPoints:\n widget.pricingPolicy?.serviceFeeRateBasisPoints ?? 0,\n },\n products: (widget.products ?? []).map(mapProduct),\n widget: {\n customFields: widget.config?.customFields ?? [],\n description: widget.description ?? null,\n fields: {\n memberId: fields.memberId ?? false,\n merchSize: fields.merchSize ?? false,\n phone: fields.phone ?? false,\n promoCode: fields.promoCode ?? false,\n serviceFee: fields.serviceFee ?? false,\n shipping: fields.shipping ?? false,\n tipping: fields.tipping ?? false,\n },\n id: widget.id ?? \"\",\n name: widget.name ?? \"Lockerverse widget\",\n showCommunityBranding: widget.showCommunityBranding ?? true,\n title: widget.title ?? null,\n },\n };\n}\n\nexport function cloneCatalog(catalog: LockerverseCatalog): LockerverseCatalog {\n return deepFreeze({\n payment: { ...catalog.payment },\n pricingPolicy: { ...catalog.pricingPolicy },\n products: catalog.products.map((product) => ({ ...product })),\n widget: {\n ...catalog.widget,\n customFields: catalog.widget.customFields.map((field) =>\n \"options\" in field\n ? {\n ...field,\n options: field.options.map((option) => ({ ...option })),\n }\n : { ...field }\n ),\n fields: { ...catalog.widget.fields },\n },\n });\n}\n\nexport function cloneCheckoutTotal(\n total: LockerverseCheckoutTotal\n): LockerverseCheckoutTotal {\n return deepFreeze({\n ...total,\n appliedDiscount: total.appliedDiscount\n ? { ...total.appliedDiscount }\n : null,\n lineItems: total.lineItems.map((lineItem) => ({ ...lineItem })),\n payment: { ...total.payment },\n });\n}\n\nexport function clonePaymentResult(\n paymentResult: LockerversePaymentResult\n): LockerversePaymentResult {\n return deepFreeze({ ...paymentResult });\n}\n","import { resolveWidgetEnvironment } from \"./checkout-environment.ts\";\nimport type { PublicCheckoutQuote } from \"./contracts.ts\";\nimport { deepFreeze } from \"./deep-freeze.ts\";\nimport { createSdkErrorReporter } from \"./error-reporting.ts\";\nimport {\n parseCheckoutQuote,\n parsePaymentResult,\n parsePublicWidget,\n} from \"./parsers.ts\";\nimport { calculateCheckoutPreview } from \"./pricing.ts\";\nimport {\n cloneCatalog,\n cloneCheckoutTotal,\n clonePaymentResult,\n createCatalog,\n} from \"./snapshots.ts\";\nimport { createStateStore } from \"./state.ts\";\nimport { createTransport } from \"./transport.ts\";\nimport {\n type CreateLockerverseWidgetOptions,\n type LockerverseCatalog,\n type LockerverseCheckoutPreview,\n type LockerverseCheckoutPricingInput,\n type LockerverseCheckoutTotal,\n LockerverseSdkError,\n type LockerverseSdkOperation,\n type LockerverseSelection,\n type LockerverseWidget,\n type LockerverseWidgetState,\n} from \"./types.ts\";\n\nexport function createLockerverseCheckout(\n options: CreateLockerverseWidgetOptions\n): LockerverseWidget {\n const {\n apiBaseUrl,\n communitySlug,\n communitySlugValue,\n environment,\n fetchImplementation,\n onError,\n requestTimeoutMs,\n sentryDsn,\n stripePublishableKey,\n widgetSlug,\n widgetSlugValue,\n } = resolveWidgetEnvironment(options);\n let catalog: LockerverseCatalog | null = null;\n let calculatedTotal: LockerverseCheckoutTotal | null = null;\n let calculatedPricingInput: LockerverseCheckoutPricingInput | null = null;\n let latestPaymentReference: string | null = null;\n let latestPreview: LockerverseCheckoutPreview | null = null;\n let remoteOperationGeneration = 0;\n let stateRevision = 0;\n let submitting = false;\n const selection = new Map<\n string,\n { amountCents: number } | { quantity: number }\n >();\n const stateStore = createStateStore<LockerverseWidgetState>({\n phase: \"idle\",\n selection: deepFreeze({ items: [] }),\n });\n\n function getProduct(productSlug: string) {\n const currentCatalog = catalog;\n const product = currentCatalog\n ? currentCatalog.products.find(({ slug }) => slug === productSlug)\n : undefined;\n\n if (!product) {\n throw new Error(`Lockerverse Product \"${productSlug}\" is unavailable.`);\n }\n\n return product;\n }\n\n const reportError = createSdkErrorReporter({\n communitySlug: communitySlugValue,\n environment,\n getContext: () => ({\n paymentReference: latestPaymentReference,\n widgetSlug: widgetSlugValue,\n }),\n onError,\n resourceContextName: \"lockerverse_widget\",\n sentryDsn,\n });\n\n function invalidSelection(\n message: string,\n operation: LockerverseSdkOperation = \"update_selection\"\n ): never {\n throw reportError(\n new LockerverseSdkError({\n code: \"invalid_selection\",\n message,\n operation,\n reportable: false,\n })\n );\n }\n\n const { requestJson } = createTransport(\n fetchImplementation,\n reportError,\n requestTimeoutMs\n );\n\n function getSelection(): LockerverseSelection {\n const currentCatalog = catalog;\n return deepFreeze({\n items: (currentCatalog ? currentCatalog.products : []).flatMap(\n (product) => {\n const selected = selection.get(product.slug);\n return selected\n ? [\n {\n productId: product.id,\n productSlug: product.slug,\n ...selected,\n },\n ]\n : [];\n }\n ),\n });\n }\n\n function invalidateCalculatedTotal() {\n calculatedTotal = null;\n calculatedPricingInput = null;\n latestPaymentReference = null;\n latestPreview = null;\n }\n\n function ensureSelectionMutable() {\n if (submitting) {\n invalidSelection(\n \"Selection cannot change while a payment is being submitted.\"\n );\n }\n }\n\n function ensureOperationAvailable(operation: LockerverseSdkOperation) {\n if (submitting) {\n invalidSelection(\n \"This operation cannot run while a payment is being submitted.\",\n operation\n );\n }\n }\n\n function reviseState() {\n stateRevision += 1;\n invalidateCalculatedTotal();\n }\n\n function commitReady(preview: LockerverseCheckoutPreview | null = null) {\n if (!catalog) {\n return;\n }\n stateStore.commit({\n catalog,\n phase: \"ready\",\n preview,\n selection: getSelection(),\n });\n }\n\n function commitError(\n error: LockerverseSdkError,\n recoverablePaymentReference: string | null = null\n ) {\n stateStore.commit({\n catalog,\n error,\n phase: \"error\",\n recoverablePaymentReference,\n selection: getSelection(),\n });\n }\n\n function normalizeOperationError(\n error: unknown,\n context: {\n code:\n | \"payment_status_failed\"\n | \"payment_submit_failed\"\n | \"widget_load_failed\";\n message: string;\n operation: \"get_payment_status\" | \"load_widget\" | \"submit_payment\";\n }\n ) {\n return error instanceof LockerverseSdkError\n ? error\n : new LockerverseSdkError({\n ...context,\n reportable: true,\n });\n }\n\n function startRemoteOperation() {\n remoteOperationGeneration += 1;\n return remoteOperationGeneration;\n }\n\n function rejectSupersededRemoteOperation(\n requestedGeneration: number,\n context: {\n code:\n | \"payment_status_failed\"\n | \"total_calculation_failed\"\n | \"widget_load_failed\";\n message: string;\n operation: \"calculate_total\" | \"get_payment_status\" | \"load_widget\";\n },\n shouldReport = true\n ) {\n if (requestedGeneration === remoteOperationGeneration) {\n return;\n }\n\n const error = new LockerverseSdkError({\n ...context,\n reportable: false,\n });\n throw shouldReport ? reportError(error) : error;\n }\n\n function rejectSupersededQuote(\n requestedStateRevision: number,\n requestedRemoteOperationGeneration: number\n ) {\n if (\n requestedStateRevision === stateRevision &&\n requestedRemoteOperationGeneration === remoteOperationGeneration\n ) {\n return;\n }\n\n throw reportError(\n new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message:\n \"This Lockerverse checkout total was superseded. Calculate the total again for the current selection.\",\n operation: \"calculate_total\",\n reportable: false,\n })\n );\n }\n\n function previewTotal(input: LockerverseCheckoutPricingInput = {}) {\n ensureOperationAvailable(\"calculate_total\");\n if (!catalog) {\n throw new Error(\n \"Load the Lockerverse widget before previewing the total.\"\n );\n }\n if (selection.size === 0) {\n invalidSelection(\"Select at least one Product before previewing.\");\n }\n const normalizedInput = normalizePricingInput(catalog, input);\n reviseState();\n\n try {\n const preview = deepFreeze(\n calculateCheckoutPreview(catalog, getSelection(), normalizedInput)\n );\n latestPreview = preview;\n commitReady(preview);\n return preview;\n } catch (error) {\n invalidSelection(\n error instanceof Error ? error.message : \"Unable to preview checkout.\"\n );\n }\n }\n\n function normalizePricingInput(\n currentCatalog: LockerverseCatalog,\n input: LockerverseCheckoutPricingInput\n ): LockerverseCheckoutPricingInput {\n validatePricingInput(currentCatalog, input);\n const tipCents = input.tipCents ?? 0;\n const email = input.email?.trim().toLowerCase();\n const promoCode = input.promoCode?.trim();\n return {\n ...(email ? { email } : {}),\n ...(input.includeServiceFee === undefined\n ? {}\n : { includeServiceFee: input.includeServiceFee }),\n ...(promoCode ? { promoCode } : {}),\n ...(input.tipCents === undefined ? {} : { tipCents }),\n };\n }\n\n function validatePricingInput(\n currentCatalog: LockerverseCatalog,\n input: LockerverseCheckoutPricingInput\n ) {\n const tipCents = input.tipCents ?? 0;\n if (!Number.isSafeInteger(tipCents) || tipCents < 0) {\n invalidSelection(\"Tip must be a non-negative whole number of cents.\");\n }\n if (input.includeServiceFee && !currentCatalog.widget.fields.serviceFee) {\n invalidSelection(\"Service fee is not enabled for this widget.\");\n }\n if (\n input.includeServiceFee &&\n currentCatalog.pricingPolicy.serviceFeeRateBasisPoints === 0\n ) {\n invalidSelection(\n \"Service fee pricing is unavailable. Reload the widget and try again.\"\n );\n }\n if (tipCents > 0 && !currentCatalog.widget.fields.tipping) {\n invalidSelection(\"Tipping is not enabled for this widget.\");\n }\n }\n\n async function calculateTotal(input: LockerverseCheckoutPricingInput = {}) {\n ensureOperationAvailable(\"calculate_total\");\n if (!catalog) {\n throw new Error(\n \"Load the Lockerverse widget before calculating the total.\"\n );\n }\n\n const normalizedInput = normalizePricingInput(catalog, input);\n if (selection.size === 0) {\n invalidSelection(\n \"Select at least one Product before calculating the total.\",\n \"calculate_total\"\n );\n }\n const currentSelection = getSelection();\n const requestedRemoteOperationGeneration = startRemoteOperation();\n const preview = deepFreeze(\n calculateCheckoutPreview(catalog, currentSelection, normalizedInput)\n );\n latestPreview = preview;\n stateStore.commit({\n catalog,\n phase: \"quoting\",\n preview,\n selection: currentSelection,\n });\n const items = currentSelection.items.map(\n ({ productSlug: _productSlug, ...item }) => item\n );\n const requestedStateRevision = stateRevision;\n calculatedTotal = null;\n latestPaymentReference = null;\n const quoteRequest = requestJson(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/quote`,\n {\n body: JSON.stringify({ ...normalizedInput, items }),\n headers: { \"Content-Type\": \"application/json\" },\n method: \"POST\",\n },\n parseCheckoutQuote,\n {\n code: \"total_calculation_failed\",\n message:\n \"Unable to calculate the Lockerverse checkout total because the request failed.\",\n operation: \"calculate_total\",\n report: false,\n },\n {\n code: \"total_calculation_failed\",\n message: \"Lockerverse returned an invalid checkout total.\",\n operation: \"calculate_total\",\n report: false,\n }\n );\n let quoteResponse: Awaited<typeof quoteRequest>;\n\n try {\n quoteResponse = await quoteRequest;\n } catch (error) {\n rejectSupersededQuote(\n requestedStateRevision,\n requestedRemoteOperationGeneration\n );\n if (error instanceof LockerverseSdkError) {\n commitError(error);\n throw reportError(error);\n }\n throw error;\n }\n\n rejectSupersededQuote(\n requestedStateRevision,\n requestedRemoteOperationGeneration\n );\n\n if (!quoteResponse.ok) {\n const error = new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message: `Unable to calculate the Lockerverse checkout total (${quoteResponse.response.status}).`,\n operation: \"calculate_total\",\n reportable: quoteResponse.response.status >= 500,\n status: quoteResponse.response.status,\n });\n commitError(error);\n throw reportError(error);\n }\n\n let serverTotal: PublicCheckoutQuote;\n try {\n serverTotal = quoteResponse.value;\n if (serverTotal.paymentOption !== \"one-time\") {\n throw new LockerverseSdkError({\n code: \"total_calculation_failed\",\n message: \"Lockerverse returned an unsupported checkout cadence.\",\n operation: \"calculate_total\",\n reportable: true,\n });\n }\n } catch (error) {\n rejectSupersededQuote(\n requestedStateRevision,\n requestedRemoteOperationGeneration\n );\n if (error instanceof LockerverseSdkError) {\n commitError(error);\n throw reportError(error);\n }\n throw error;\n }\n rejectSupersededQuote(\n requestedStateRevision,\n requestedRemoteOperationGeneration\n );\n const paymentReference = globalThis.crypto.randomUUID();\n const {\n connectedAccountId,\n paymentOption: _paymentOption,\n ...total\n } = serverTotal;\n const nextCalculatedTotal = deepFreeze({\n ...total,\n authoritative: true as const,\n payment: {\n ...catalog.payment,\n connectedAccountId,\n },\n paymentOption: \"one-time\" as const,\n paymentReference,\n });\n calculatedTotal = nextCalculatedTotal;\n calculatedPricingInput = deepFreeze({ ...normalizedInput });\n latestPaymentReference = paymentReference;\n stateStore.commit({\n catalog,\n phase: \"quoted\",\n preview,\n quote: nextCalculatedTotal,\n selection: currentSelection,\n });\n return cloneCheckoutTotal(nextCalculatedTotal);\n }\n\n return {\n calculateTotal,\n clear() {\n ensureSelectionMutable();\n selection.clear();\n reviseState();\n commitReady();\n },\n async getPaymentStatus(paymentReference = latestPaymentReference ?? \"\") {\n ensureOperationAvailable(\"get_payment_status\");\n if (!paymentReference) {\n invalidSelection(\n \"Provide a payment reference to recover its status.\",\n \"get_payment_status\"\n );\n }\n const requestedRemoteOperationGeneration = startRemoteOperation();\n const supersededContext = {\n code: \"payment_status_failed\" as const,\n message: \"This Lockerverse payment status request was superseded.\",\n operation: \"get_payment_status\" as const,\n };\n latestPaymentReference = paymentReference;\n const currentSelection = getSelection();\n stateStore.commit({\n catalog,\n paymentReference,\n phase: \"recovering\",\n selection: currentSelection,\n });\n try {\n const statusResponse = await requestJson(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/${encodeURIComponent(paymentReference)}/status`,\n undefined,\n parsePaymentResult,\n {\n code: \"payment_status_failed\",\n message:\n \"Unable to recover the Lockerverse payment status because the request failed.\",\n operation: \"get_payment_status\",\n report: false,\n },\n {\n code: \"payment_status_failed\",\n message: \"Lockerverse returned an invalid payment status.\",\n operation: \"get_payment_status\",\n report: false,\n }\n );\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext,\n false\n );\n if (!statusResponse.ok) {\n throw new LockerverseSdkError({\n code: \"payment_status_failed\",\n message: `Unable to recover the Lockerverse payment status (${statusResponse.response.status}).`,\n operation: \"get_payment_status\",\n reportable: statusResponse.response.status >= 500,\n status: statusResponse.response.status,\n });\n }\n\n const payment = clonePaymentResult(statusResponse.value);\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext,\n false\n );\n if (payment.paymentReference !== paymentReference) {\n throw new LockerverseSdkError({\n code: \"payment_status_failed\",\n message: \"Lockerverse returned an invalid payment status.\",\n operation: \"get_payment_status\",\n reportable: true,\n });\n }\n stateStore.commit({\n catalog,\n payment,\n phase: \"payment\",\n quote:\n calculatedTotal?.paymentReference === paymentReference\n ? calculatedTotal\n : null,\n selection: currentSelection,\n });\n return clonePaymentResult(payment);\n } catch (error) {\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext\n );\n const sdkError = normalizeOperationError(error, {\n code: \"payment_status_failed\",\n message: \"Lockerverse returned an invalid payment status.\",\n operation: \"get_payment_status\",\n });\n commitError(sdkError, paymentReference);\n throw reportError(sdkError);\n }\n },\n getSelection,\n getState: stateStore.getState,\n async load() {\n ensureOperationAvailable(\"load_widget\");\n const requestedRemoteOperationGeneration = startRemoteOperation();\n const supersededContext = {\n code: \"widget_load_failed\" as const,\n message: \"This Lockerverse widget load was superseded.\",\n operation: \"load_widget\" as const,\n };\n reviseState();\n stateStore.commit({ phase: \"loading\", selection: getSelection() });\n const requestContext = {\n code: \"widget_load_failed\" as const,\n message:\n \"Unable to load Lockerverse widget because the request failed.\",\n operation: \"load_widget\" as const,\n report: false,\n };\n try {\n const widgetResponse = await requestJson(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}`,\n undefined,\n parsePublicWidget,\n requestContext,\n {\n code: \"widget_load_failed\",\n message: \"Lockerverse returned an invalid widget catalog.\",\n operation: \"load_widget\",\n report: false,\n }\n );\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext,\n false\n );\n if (!widgetResponse.ok) {\n throw new LockerverseSdkError({\n code: \"widget_load_failed\",\n message: `Unable to load Lockerverse widget (${widgetResponse.response.status}).`,\n operation: \"load_widget\",\n reportable: widgetResponse.response.status >= 500,\n status: widgetResponse.response.status,\n });\n }\n\n const widget = widgetResponse.value;\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext,\n false\n );\n const nextCatalog = deepFreeze(\n createCatalog(widget, stripePublishableKey)\n );\n const catalogResult = cloneCatalog(nextCatalog);\n selection.clear();\n catalog = nextCatalog;\n commitReady();\n\n return catalogResult;\n } catch (error) {\n rejectSupersededRemoteOperation(\n requestedRemoteOperationGeneration,\n supersededContext\n );\n const sdkError = normalizeOperationError(error, {\n code: \"widget_load_failed\",\n message: \"Lockerverse returned an invalid widget catalog.\",\n operation: \"load_widget\",\n });\n commitError(sdkError);\n throw reportError(sdkError);\n }\n },\n previewTotal,\n remove(productSlug) {\n ensureSelectionMutable();\n selection.delete(productSlug);\n reviseState();\n commitReady();\n },\n setAmount(productSlug, amountCents) {\n ensureSelectionMutable();\n const product = getProduct(productSlug);\n\n if (product.pricingMode !== \"custom\") {\n invalidSelection(\"Fixed-price Products do not accept custom amounts.\");\n }\n if (!Number.isSafeInteger(amountCents) || amountCents <= 0) {\n invalidSelection(\"Product amount must be a positive integer in cents.\");\n }\n if (\n product.minimumAmountCents !== null &&\n amountCents < product.minimumAmountCents\n ) {\n invalidSelection(\n `Product amount must be at least ${product.minimumAmountCents} cents.`\n );\n }\n\n selection.set(productSlug, { amountCents });\n reviseState();\n commitReady();\n },\n setQuantity(productSlug, quantity) {\n ensureSelectionMutable();\n const product = getProduct(productSlug);\n\n if (product.pricingMode !== \"fixed\") {\n invalidSelection(\"Custom-amount Products do not accept quantities.\");\n }\n if (!Number.isSafeInteger(quantity) || quantity <= 0) {\n invalidSelection(\"Product quantity must be a positive integer.\");\n }\n if (\n product.minimumQuantity !== null &&\n quantity < product.minimumQuantity\n ) {\n invalidSelection(\n `Product quantity must be at least ${product.minimumQuantity}.`\n );\n }\n if (\n product.maximumQuantity !== null &&\n quantity > product.maximumQuantity\n ) {\n invalidSelection(\n `Product quantity must not exceed ${product.maximumQuantity}.`\n );\n }\n if (\n product.inventoryQuantity !== null &&\n quantity > product.inventoryQuantity\n ) {\n invalidSelection(\"Requested Product quantity is unavailable.\");\n }\n\n selection.set(productSlug, { quantity });\n reviseState();\n commitReady();\n },\n async submitPayment(submission) {\n if (!(catalog && calculatedTotal && calculatedPricingInput)) {\n invalidSelection(\n \"Calculate the current total before submitting a payment.\",\n \"submit_payment\"\n );\n }\n if (submitting) {\n invalidSelection(\n \"A Lockerverse payment is already being submitted.\",\n \"submit_payment\"\n );\n }\n\n const transactionCatalog = catalog;\n const transactionQuote = calculatedTotal;\n const transactionPricingInput = calculatedPricingInput;\n const transactionSelection = getSelection();\n const transactionPreview =\n latestPreview ??\n calculateCheckoutPreview(\n transactionCatalog,\n transactionSelection,\n transactionPricingInput\n );\n const normalizedEmail = submission.email.trim().toLowerCase();\n if (\n !normalizedEmail ||\n normalizedEmail !== transactionPricingInput.email\n ) {\n invalidSelection(\n \"Payment email must match the current checkout quote.\",\n \"submit_payment\"\n );\n }\n\n const items = transactionSelection.items.map(\n ({ productSlug: _productSlug, ...item }) => item\n );\n startRemoteOperation();\n submitting = true;\n stateStore.commit({\n catalog: transactionCatalog,\n phase: \"submitting\",\n preview: transactionPreview,\n quote: transactionQuote,\n selection: transactionSelection,\n });\n try {\n const confirmationResponse = await requestJson(\n `${apiBaseUrl}/v2/community/${communitySlug}/payment-widgets/${widgetSlug}/checkout/confirm`,\n {\n body: JSON.stringify({\n confirmationToken: submission.confirmationToken,\n customFieldAnswers: submission.customFieldAnswers,\n email: normalizedEmail,\n expectedAmountCents: transactionQuote.amountCents,\n expectedAppliedDiscount: transactionQuote.appliedDiscount,\n expectedConnectedAccountId:\n transactionQuote.payment.connectedAccountId,\n expectedDiscountableSubtotalCents:\n transactionQuote.discountableSubtotalCents,\n expectedDiscountCents: transactionQuote.discountCents,\n expectedServiceFeeCents: transactionQuote.serviceFeeCents,\n expectedSubtotalCents: transactionQuote.subtotalCents,\n expectedTipCents: transactionQuote.tipCents,\n expectedTotalCents: transactionQuote.totalCents,\n ...transactionPricingInput,\n items,\n memberId: submission.memberId,\n merchSize: submission.merchSize,\n metadata: submission.metadata,\n paymentReference: transactionQuote.paymentReference,\n phone: submission.phone,\n quoteContractVersion: 1,\n }),\n headers: { \"Content-Type\": \"application/json\" },\n method: \"POST\",\n },\n parsePaymentResult,\n {\n code: \"payment_submit_failed\",\n message:\n \"Unable to submit the Lockerverse payment because the request failed.\",\n operation: \"submit_payment\",\n report: false,\n },\n {\n code: \"payment_submit_failed\",\n message: \"Lockerverse returned an invalid payment confirmation.\",\n operation: \"submit_payment\",\n report: false,\n }\n );\n\n if (!confirmationResponse.ok) {\n throw new LockerverseSdkError({\n code: \"payment_submit_failed\",\n message: `Unable to submit the Lockerverse payment (${confirmationResponse.response.status}).`,\n operation: \"submit_payment\",\n reportable: confirmationResponse.response.status >= 500,\n status: confirmationResponse.response.status,\n });\n }\n\n const payment = clonePaymentResult(confirmationResponse.value);\n if (payment.paymentReference !== transactionQuote.paymentReference) {\n throw new LockerverseSdkError({\n code: \"payment_submit_failed\",\n message: \"Lockerverse returned an invalid payment confirmation.\",\n operation: \"submit_payment\",\n reportable: true,\n });\n }\n stateStore.commit({\n catalog: transactionCatalog,\n payment,\n phase: \"payment\",\n quote: transactionQuote,\n selection: transactionSelection,\n });\n return clonePaymentResult(payment);\n } catch (error) {\n const sdkError = normalizeOperationError(error, {\n code: \"payment_submit_failed\",\n message: \"Lockerverse returned an invalid payment confirmation.\",\n operation: \"submit_payment\",\n });\n commitError(sdkError, transactionQuote.paymentReference);\n throw reportError(sdkError);\n } finally {\n submitting = false;\n }\n },\n subscribe: stateStore.subscribe,\n };\n}\n"],"mappings":"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"}
|
package/dist/signup.d.ts
CHANGED
|
@@ -43,10 +43,14 @@ type LockerverseSignupSubmissionResult = {
|
|
|
43
43
|
id: string;
|
|
44
44
|
submittedAt: string;
|
|
45
45
|
};
|
|
46
|
+
type LockerverseSignupSubmitOptions = {
|
|
47
|
+
submissionReference?: string;
|
|
48
|
+
};
|
|
46
49
|
type CreateLockerverseSignupBaseOptions = {
|
|
47
50
|
communitySlug: string;
|
|
48
51
|
fetch?: typeof globalThis.fetch;
|
|
49
52
|
onError?: (error: LockerverseSdkError) => void;
|
|
53
|
+
requestTimeoutMs?: number;
|
|
50
54
|
sentryDsn?: string | null;
|
|
51
55
|
signupSlug: string;
|
|
52
56
|
};
|
|
@@ -67,6 +71,7 @@ type LockerverseSignupState = {
|
|
|
67
71
|
} | {
|
|
68
72
|
phase: "submitting";
|
|
69
73
|
signup: LockerverseSignup;
|
|
74
|
+
submissionReference: string;
|
|
70
75
|
} | {
|
|
71
76
|
phase: "submitted";
|
|
72
77
|
signup: LockerverseSignup;
|
|
@@ -74,17 +79,18 @@ type LockerverseSignupState = {
|
|
|
74
79
|
} | {
|
|
75
80
|
phase: "error";
|
|
76
81
|
error: LockerverseSdkError;
|
|
82
|
+
recoverableSubmissionReference: string | null;
|
|
77
83
|
signup: LockerverseSignup | null;
|
|
78
84
|
};
|
|
79
85
|
type LockerverseSignupClient = {
|
|
80
86
|
getState: () => LockerverseSignupState;
|
|
81
87
|
load: () => Promise<LockerverseSignup>;
|
|
82
|
-
submit: (submission: LockerverseSignupSubmission) => Promise<LockerverseSignupSubmissionResult>;
|
|
88
|
+
submit: (submission: LockerverseSignupSubmission, options?: LockerverseSignupSubmitOptions) => Promise<LockerverseSignupSubmissionResult>;
|
|
83
89
|
subscribe: (listener: (state: LockerverseSignupState) => void) => () => void;
|
|
84
90
|
};
|
|
85
91
|
//#endregion
|
|
86
92
|
//#region src/signup.d.ts
|
|
87
93
|
declare function createLockerverseSignup(options: CreateLockerverseSignupOptions): LockerverseSignupClient;
|
|
88
94
|
//#endregion
|
|
89
|
-
export { type CreateLockerverseSignupOptions, type LockerverseCustomField, type LockerverseCustomFieldAnswer, type LockerverseCustomFieldAnswerValue, type LockerverseCustomFieldOption, type LockerverseEnvironment, type LockerverseSignup, type LockerverseSignupAddress, type LockerverseSignupClient, type LockerverseSignupField, type LockerverseSignupFields, type LockerverseSignupState, type LockerverseSignupSubmission, type LockerverseSignupSubmissionResult, createLockerverseSignup };
|
|
95
|
+
export { type CreateLockerverseSignupOptions, type LockerverseCustomField, type LockerverseCustomFieldAnswer, type LockerverseCustomFieldAnswerValue, type LockerverseCustomFieldOption, type LockerverseEnvironment, type LockerverseSignup, type LockerverseSignupAddress, type LockerverseSignupClient, type LockerverseSignupField, type LockerverseSignupFields, type LockerverseSignupState, type LockerverseSignupSubmission, type LockerverseSignupSubmissionResult, type LockerverseSignupSubmitOptions, createLockerverseSignup };
|
|
90
96
|
//# sourceMappingURL=signup.d.ts.map
|
package/dist/signup.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signup.d.ts","names":[],"sources":["../src/signup-types.ts","../src/signup.ts"],"mappings":";;KAOY;EACV;EACA;;KAGU;EACV,SAAS;EACT,OAAO;EACP,MAAM;EACN,kBAAkB;EAClB,OAAO;;KAGG;EACV;EACA,cAAc;EACd;EACA,QAAQ;EACR;EACA;EACA;EACA;EACA;;KAGU;EACV;EACA;EACA;EACA;EACA;EACA;;KAGU;EACV,UAAU;EACV,UAAU;EACV;EACA;EACA;EACA;EACA;;KAGU;EACV;EACA;;KAGG;EACH;EACA,eAAe,WAAW;EAC1B,WAAW,OAAO;EAClB;EACA;;KAGU,iCACV;EAGQ;EACA,aAAa;;EAGb;EACA;;KAIE;EACN;;EACA;;EACA;EAAgB,QAAQ;;
|
|
1
|
+
{"version":3,"file":"signup.d.ts","names":[],"sources":["../src/signup-types.ts","../src/signup.ts"],"mappings":";;KAOY;EACV;EACA;;KAGU;EACV,SAAS;EACT,OAAO;EACP,MAAM;EACN,kBAAkB;EAClB,OAAO;;KAGG;EACV;EACA,cAAc;EACd;EACA,QAAQ;EACR;EACA;EACA;EACA;EACA;;KAGU;EACV;EACA;EACA;EACA;EACA;EACA;;KAGU;EACV,UAAU;EACV,UAAU;EACV;EACA;EACA;EACA;EACA;;KAGU;EACV;EACA;;KAGU;EACV;;KAGG;EACH;EACA,eAAe,WAAW;EAC1B,WAAW,OAAO;EAClB;EACA;EACA;;KAGU,iCACV;EAGQ;EACA,aAAa;;EAGb;EACA;;KAIE;EACN;;EACA;;EACA;EAAgB,QAAQ;;EAExB;EACA,QAAQ;EACR;;EAGA;EACA,QAAQ;EACR,YAAY;;EAGZ;EACA,OAAO;EACP;EACA,QAAQ;;KAGF;EACV,gBAAgB;EAChB,YAAY,QAAQ;EACpB,SACE,YAAY,6BACZ,UAAU,mCACP,QAAQ;EACb,YAAY,WAAW,OAAO;;;;iBC5FhB,wBACd,SAAS,iCACR"}
|
package/dist/signup.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{a as e,c as t,d as n,f as r,i,m as a,n as o,r as s,t as c,u as l}from"./transport.js";import{n as u}from"./types.js";function d(e){let t=l(e);return{enabled:s(t.enabled),required:s(t.required)}}function f(e){let t=l(e);return{address:d(t.address),email:d(t.email),name:d(t.name),participantCount:d(t.participantCount),phone:d(t.phone)}}function p(n){let r=l(n),a=l(r.config);return{coverImageUrl:t(r.coverImageUrl,null),customFields:i(a.customFields),description:t(r.description,null),fields:f(a.builtInFields),id:e(r.id),isActive:s(r.isActive),name:e(r.name),slug:e(r.slug),title:t(r.title,null)}}function m(t){let n=l(t),r=e(n.submittedAt);if(Number.isNaN(Date.parse(r)))throw TypeError(`Expected a submission timestamp.`);return{id:e(n.id),submittedAt:r}}function h(e){let t=a(e),i=o({phase:`idle`}),s=null,l=!1,d=!1,f=n({communitySlug:t.communitySlugValue,environment:t.environment,getContext:()=>({signupSlug:t.signupSlugValue}),onError:t.onError,resourceContextName:`lockerverse_signup`,sentryDsn:t.sentryDsn}),{
|
|
1
|
+
import{a as e,c as t,d as n,f as r,i,m as a,n as o,r as s,t as c,u as l}from"./transport.js";import{n as u}from"./types.js";function d(e){let t=l(e);return{enabled:s(t.enabled),required:s(t.required)}}function f(e){let t=l(e);return{address:d(t.address),email:d(t.email),name:d(t.name),participantCount:d(t.participantCount),phone:d(t.phone)}}function p(n){let r=l(n),a=l(r.config);return{coverImageUrl:t(r.coverImageUrl,null),customFields:i(a.customFields),description:t(r.description,null),fields:f(a.builtInFields),id:e(r.id),isActive:s(r.isActive),name:e(r.name),slug:e(r.slug),title:t(r.title,null)}}function m(t){let n=l(t),r=e(n.submittedAt);if(Number.isNaN(Date.parse(r)))throw TypeError(`Expected a submission timestamp.`);return{id:e(n.id),submittedAt:r}}function h(e){let t=a(e),i=o({phase:`idle`}),s=null,l=!1,d=!1,f=n({communitySlug:t.communitySlugValue,environment:t.environment,getContext:()=>({signupSlug:t.signupSlugValue}),onError:t.onError,resourceContextName:`lockerverse_signup`,sentryDsn:t.sentryDsn}),{requestJson:h}=c(t.fetchImplementation,f,t.requestTimeoutMs);return{getState:i.getState,async load(){let e={code:`signup_load_failed`,message:`Unable to load Lockerverse signup.`,operation:`load_signup`};if(l||d)throw f(new u({...e,reportable:!1}));l=!0,s=null,i.commit({phase:`loading`});try{let n;try{n=await h(`${t.apiBaseUrl}/community/${t.communitySlug}/sign-up-widgets/${t.signupSlug}`,void 0,p,e,e)}catch(e){throw e instanceof u&&i.commit({error:e,phase:`error`,recoverableSubmissionReference:null,signup:null}),e}if(!n.ok){let t=f(new u({...e,reportable:n.response.status>=500,status:n.response.status}));throw i.commit({error:t,phase:`error`,recoverableSubmissionReference:null,signup:null}),t}let a=r(n.value);return s=a,i.commit({phase:`ready`,signup:a}),a}finally{l=!1}},async submit(e,n){let a=s,o=n?.submissionReference??globalThis.crypto.randomUUID(),c={code:`signup_submit_failed`,message:`Unable to submit Lockerverse signup.`,operation:`submit_signup`};if(!a?.isActive||d)throw f(new u({...c,reportable:!1}));d=!0,i.commit({phase:`submitting`,signup:a,submissionReference:o});try{let n=await h(`${t.apiBaseUrl}/community/${t.communitySlug}/sign-up-widgets/${t.signupSlug}/submissions`,{body:JSON.stringify({...e,submissionReference:o}),headers:{"content-type":`application/json`},method:`POST`},m,c,c);if(!n.ok)throw f(new u({...c,reportable:n.response.status>=500,status:n.response.status}));let s=r(n.value);if(s.id!==o)throw f(new u({...c,reportable:!0}));return i.commit({phase:`submitted`,signup:a,submission:s}),s}catch(e){let t=e instanceof u?e:f(new u({...c,reportable:!1}));throw i.commit({error:t,phase:`error`,recoverableSubmissionReference:o,signup:a}),t}finally{d=!1}},subscribe:i.subscribe}}export{h as createLockerverseSignup};
|
|
2
2
|
//# sourceMappingURL=signup.js.map
|
package/dist/signup.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signup.js","names":[],"sources":["../src/signup-parsers.ts","../src/signup.ts"],"sourcesContent":["import {\n parseBoolean,\n parseCustomFields,\n parseNonEmptyString,\n parseOptionalNullableString,\n parseRecord,\n} from \"./parsing.ts\";\nimport type {\n LockerverseSignup,\n LockerverseSignupField,\n LockerverseSignupFields,\n LockerverseSignupSubmissionResult,\n} from \"./signup-types.ts\";\n\nfunction parseSignupField(value: unknown): LockerverseSignupField {\n const field = parseRecord(value);\n return {\n enabled: parseBoolean(field.enabled),\n required: parseBoolean(field.required),\n };\n}\n\nfunction parseSignupFields(value: unknown): LockerverseSignupFields {\n const fields = parseRecord(value);\n return {\n address: parseSignupField(fields.address),\n email: parseSignupField(fields.email),\n name: parseSignupField(fields.name),\n participantCount: parseSignupField(fields.participantCount),\n phone: parseSignupField(fields.phone),\n };\n}\n\nexport function parsePublicSignup(value: unknown): LockerverseSignup {\n const signup = parseRecord(value);\n const config = parseRecord(signup.config);\n\n return {\n coverImageUrl: parseOptionalNullableString(signup.coverImageUrl, null),\n customFields: parseCustomFields(config.customFields),\n description: parseOptionalNullableString(signup.description, null),\n fields: parseSignupFields(config.builtInFields),\n id: parseNonEmptyString(signup.id),\n isActive: parseBoolean(signup.isActive),\n name: parseNonEmptyString(signup.name),\n slug: parseNonEmptyString(signup.slug),\n title: parseOptionalNullableString(signup.title, null),\n };\n}\n\nexport function parseSignupSubmissionResult(\n value: unknown\n): LockerverseSignupSubmissionResult {\n const result = parseRecord(value);\n const submittedAt = parseNonEmptyString(result.submittedAt);\n if (Number.isNaN(Date.parse(submittedAt))) {\n throw new TypeError(\"Expected a submission timestamp.\");\n }\n return {\n id: parseNonEmptyString(result.id),\n submittedAt,\n };\n}\n","import { deepFreeze } from \"./deep-freeze.ts\";\nimport { resolveSignupEnvironment } from \"./environment.ts\";\nimport { createSdkErrorReporter } from \"./error-reporting.ts\";\nimport {\n parsePublicSignup,\n parseSignupSubmissionResult,\n} from \"./signup-parsers.ts\";\nimport type {\n CreateLockerverseSignupOptions,\n LockerverseSignup,\n LockerverseSignupClient,\n LockerverseSignupState,\n LockerverseSignupSubmission,\n} from \"./signup-types.ts\";\nimport { createStateStore } from \"./state.ts\";\nimport { createTransport } from \"./transport.ts\";\nimport { LockerverseSdkError } from \"./types.ts\";\n\nexport function createLockerverseSignup(\n options: CreateLockerverseSignupOptions\n): LockerverseSignupClient {\n const runtime = resolveSignupEnvironment(options);\n const stateStore = createStateStore<LockerverseSignupState>({\n phase: \"idle\",\n });\n let loadedSignup: LockerverseSignup | null = null;\n let loading = false;\n let submitting = false;\n\n const reportError = createSdkErrorReporter({\n communitySlug: runtime.communitySlugValue,\n environment: runtime.environment,\n getContext: () => ({ signupSlug: runtime.signupSlugValue }),\n onError: runtime.onError,\n resourceContextName: \"lockerverse_signup\",\n sentryDsn: runtime.sentryDsn,\n });\n\n const { fetchResponse, parseResponseJson } = createTransport(\n runtime.fetchImplementation,\n reportError\n );\n\n return {\n getState: stateStore.getState,\n async load() {\n const errorContext = {\n code: \"signup_load_failed\" as const,\n message: \"Unable to load Lockerverse signup.\",\n operation: \"load_signup\" as const,\n };\n if (loading || submitting) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n }\n\n loading = true;\n loadedSignup = null;\n stateStore.commit({ phase: \"loading\" });\n try {\n let response: Response;\n try {\n response = await fetchResponse(\n `${runtime.apiBaseUrl}/community/${runtime.communitySlug}/sign-up-widgets/${runtime.signupSlug}`,\n undefined,\n errorContext\n );\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n stateStore.commit({ error, phase: \"error\", signup: null });\n }\n throw error;\n }\n if (!response.ok) {\n const error = reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: response.status >= 500,\n status: response.status,\n })\n );\n stateStore.commit({ error, phase: \"error\", signup: null });\n throw error;\n }\n try {\n const signup = deepFreeze(\n await parseResponseJson(response, parsePublicSignup, errorContext)\n );\n loadedSignup = signup;\n stateStore.commit({ phase: \"ready\", signup });\n return signup;\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n stateStore.commit({ error, phase: \"error\", signup: null });\n }\n throw error;\n }\n } finally {\n loading = false;\n }\n },\n async submit(submission: LockerverseSignupSubmission) {\n const signup = loadedSignup;\n const errorContext = {\n code: \"signup_submit_failed\" as const,\n message: \"Unable to submit Lockerverse signup.\",\n operation: \"submit_signup\" as const,\n };\n if (!signup?.isActive || submitting) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n }\n\n submitting = true;\n stateStore.commit({ phase: \"submitting\", signup });\n try {\n const response = await fetchResponse(\n `${runtime.apiBaseUrl}/community/${runtime.communitySlug}/sign-up-widgets/${runtime.signupSlug}/submissions`,\n {\n body: JSON.stringify(submission),\n headers: { \"content-type\": \"application/json\" },\n method: \"POST\",\n },\n errorContext\n );\n if (!response.ok) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: response.status >= 500,\n status: response.status,\n })\n );\n }\n const result = deepFreeze(\n await parseResponseJson(\n response,\n parseSignupSubmissionResult,\n errorContext\n )\n );\n stateStore.commit({ phase: \"submitted\", signup, submission: result });\n return result;\n } catch (error) {\n const sdkError =\n error instanceof LockerverseSdkError\n ? error\n : reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n stateStore.commit({ error: sdkError, phase: \"error\", signup });\n throw sdkError;\n } finally {\n submitting = false;\n }\n },\n subscribe: stateStore.subscribe,\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"signup.js","names":[],"sources":["../src/signup-parsers.ts","../src/signup.ts"],"sourcesContent":["import {\n parseBoolean,\n parseCustomFields,\n parseNonEmptyString,\n parseOptionalNullableString,\n parseRecord,\n} from \"./parsing.ts\";\nimport type {\n LockerverseSignup,\n LockerverseSignupField,\n LockerverseSignupFields,\n LockerverseSignupSubmissionResult,\n} from \"./signup-types.ts\";\n\nfunction parseSignupField(value: unknown): LockerverseSignupField {\n const field = parseRecord(value);\n return {\n enabled: parseBoolean(field.enabled),\n required: parseBoolean(field.required),\n };\n}\n\nfunction parseSignupFields(value: unknown): LockerverseSignupFields {\n const fields = parseRecord(value);\n return {\n address: parseSignupField(fields.address),\n email: parseSignupField(fields.email),\n name: parseSignupField(fields.name),\n participantCount: parseSignupField(fields.participantCount),\n phone: parseSignupField(fields.phone),\n };\n}\n\nexport function parsePublicSignup(value: unknown): LockerverseSignup {\n const signup = parseRecord(value);\n const config = parseRecord(signup.config);\n\n return {\n coverImageUrl: parseOptionalNullableString(signup.coverImageUrl, null),\n customFields: parseCustomFields(config.customFields),\n description: parseOptionalNullableString(signup.description, null),\n fields: parseSignupFields(config.builtInFields),\n id: parseNonEmptyString(signup.id),\n isActive: parseBoolean(signup.isActive),\n name: parseNonEmptyString(signup.name),\n slug: parseNonEmptyString(signup.slug),\n title: parseOptionalNullableString(signup.title, null),\n };\n}\n\nexport function parseSignupSubmissionResult(\n value: unknown\n): LockerverseSignupSubmissionResult {\n const result = parseRecord(value);\n const submittedAt = parseNonEmptyString(result.submittedAt);\n if (Number.isNaN(Date.parse(submittedAt))) {\n throw new TypeError(\"Expected a submission timestamp.\");\n }\n return {\n id: parseNonEmptyString(result.id),\n submittedAt,\n };\n}\n","import { deepFreeze } from \"./deep-freeze.ts\";\nimport { resolveSignupEnvironment } from \"./environment.ts\";\nimport { createSdkErrorReporter } from \"./error-reporting.ts\";\nimport {\n parsePublicSignup,\n parseSignupSubmissionResult,\n} from \"./signup-parsers.ts\";\nimport type {\n CreateLockerverseSignupOptions,\n LockerverseSignup,\n LockerverseSignupClient,\n LockerverseSignupState,\n LockerverseSignupSubmission,\n} from \"./signup-types.ts\";\nimport { createStateStore } from \"./state.ts\";\nimport { createTransport } from \"./transport.ts\";\nimport { LockerverseSdkError } from \"./types.ts\";\n\nexport function createLockerverseSignup(\n options: CreateLockerverseSignupOptions\n): LockerverseSignupClient {\n const runtime = resolveSignupEnvironment(options);\n const stateStore = createStateStore<LockerverseSignupState>({\n phase: \"idle\",\n });\n let loadedSignup: LockerverseSignup | null = null;\n let loading = false;\n let submitting = false;\n\n const reportError = createSdkErrorReporter({\n communitySlug: runtime.communitySlugValue,\n environment: runtime.environment,\n getContext: () => ({ signupSlug: runtime.signupSlugValue }),\n onError: runtime.onError,\n resourceContextName: \"lockerverse_signup\",\n sentryDsn: runtime.sentryDsn,\n });\n\n const { requestJson } = createTransport(\n runtime.fetchImplementation,\n reportError,\n runtime.requestTimeoutMs\n );\n\n return {\n getState: stateStore.getState,\n async load() {\n const errorContext = {\n code: \"signup_load_failed\" as const,\n message: \"Unable to load Lockerverse signup.\",\n operation: \"load_signup\" as const,\n };\n if (loading || submitting) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n }\n\n loading = true;\n loadedSignup = null;\n stateStore.commit({ phase: \"loading\" });\n try {\n let signupResponse: Awaited<\n ReturnType<typeof requestJson<LockerverseSignup>>\n >;\n try {\n signupResponse = await requestJson(\n `${runtime.apiBaseUrl}/community/${runtime.communitySlug}/sign-up-widgets/${runtime.signupSlug}`,\n undefined,\n parsePublicSignup,\n errorContext,\n errorContext\n );\n } catch (error) {\n if (error instanceof LockerverseSdkError) {\n stateStore.commit({\n error,\n phase: \"error\",\n recoverableSubmissionReference: null,\n signup: null,\n });\n }\n throw error;\n }\n if (!signupResponse.ok) {\n const error = reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: signupResponse.response.status >= 500,\n status: signupResponse.response.status,\n })\n );\n stateStore.commit({\n error,\n phase: \"error\",\n recoverableSubmissionReference: null,\n signup: null,\n });\n throw error;\n }\n const signup = deepFreeze(signupResponse.value);\n loadedSignup = signup;\n stateStore.commit({ phase: \"ready\", signup });\n return signup;\n } finally {\n loading = false;\n }\n },\n async submit(submission: LockerverseSignupSubmission, submitOptions) {\n const signup = loadedSignup;\n const submissionReference =\n submitOptions?.submissionReference ?? globalThis.crypto.randomUUID();\n const errorContext = {\n code: \"signup_submit_failed\" as const,\n message: \"Unable to submit Lockerverse signup.\",\n operation: \"submit_signup\" as const,\n };\n if (!signup?.isActive || submitting) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n }\n\n submitting = true;\n stateStore.commit({ phase: \"submitting\", signup, submissionReference });\n try {\n const submissionResponse = await requestJson(\n `${runtime.apiBaseUrl}/community/${runtime.communitySlug}/sign-up-widgets/${runtime.signupSlug}/submissions`,\n {\n body: JSON.stringify({ ...submission, submissionReference }),\n headers: { \"content-type\": \"application/json\" },\n method: \"POST\",\n },\n parseSignupSubmissionResult,\n errorContext,\n errorContext\n );\n if (!submissionResponse.ok) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: submissionResponse.response.status >= 500,\n status: submissionResponse.response.status,\n })\n );\n }\n const result = deepFreeze(submissionResponse.value);\n if (result.id !== submissionReference) {\n throw reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: true,\n })\n );\n }\n stateStore.commit({ phase: \"submitted\", signup, submission: result });\n return result;\n } catch (error) {\n const sdkError =\n error instanceof LockerverseSdkError\n ? error\n : reportError(\n new LockerverseSdkError({\n ...errorContext,\n reportable: false,\n })\n );\n stateStore.commit({\n error: sdkError,\n phase: \"error\",\n recoverableSubmissionReference: submissionReference,\n signup,\n });\n throw sdkError;\n } finally {\n submitting = false;\n }\n },\n subscribe: stateStore.subscribe,\n };\n}\n"],"mappings":"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"}
|
package/dist/transport.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{n as e}from"./types.js";const t=/\/+$/,n=new Set([`localhost`,`127.0.0.1`,`[::1]`]),r={development:{sentryDsn:`https://1977371f7bc44480935a7bc9726ca296@o1338376.ingest.sentry.io/6631829`},production:{sentryDsn:`https://c87cbc682ff0422eab5a4714acb95fd1@o1338376.ingest.sentry.io/6662564`}};function i(e){if(typeof e!=`object`||!e||Array.isArray(e))throw TypeError(`Expected an object.`);return e}function a(e){if(e===`development`||e===`production`)return e;throw TypeError(`environment must be either development or production.`)}function o(e,r){if(typeof e!=`string`)throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`);let i;try{i=new URL(e)}catch{throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`)}if(i.protocol!==`http:`&&i.protocol!==`https:`)throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`);if(i.username||i.password)throw TypeError(`apiBaseUrl must not include credentials.`);if(i.search||i.hash)throw TypeError(`apiBaseUrl must not include a query or fragment.`);if(i.protocol!==`https:`&&!(r===`development`&&n.has(i.hostname)))throw TypeError(`apiBaseUrl must use HTTPS except for development loopback endpoints.`);return i.pathname=i.pathname.replace(t,``),i.toString().replace(t,``)}function s(e,t){if(typeof e!=`string`||e.trim().length===0)throw TypeError(`${t} must be a non-empty string.`);return e}function c(e,t){let n=i(e),c=n.environment;if(n.apiBaseUrl!==void 0&&c===void 0)throw TypeError(`environment is required when apiBaseUrl is provided.`);if(n.apiBaseUrl===void 0&&c===`development`)throw TypeError(`apiBaseUrl is required when environment is development.`);let l=c===void 0?`production`:a(c),u=s(n.communitySlug,`communitySlug`),d=s(n[t],t);if(n.fetch!==void 0&&typeof n.fetch!=`function`)throw TypeError(`fetch must be a function when provided.`);if(n.onError!==void 0&&typeof n.onError!=`function`)throw TypeError(`onError must be a function when provided.`);if(n.sentryDsn!==void 0&&n.sentryDsn!==null&&typeof n.sentryDsn!=`string`)throw TypeError(`sentryDsn must be a string or null when provided.`);let f=n.fetch??globalThis.fetch,p=n.apiBaseUrl===void 0?`https://portal.lockerverse.com/api`:o(n.apiBaseUrl,l),m=r[l],h=n.sentryDsn,g=h===null?null:h??m.sentryDsn;return{apiBaseUrl:p,communitySlug:encodeURIComponent(u),communitySlugValue:u,environment:l,fetchImplementation:f,onError:n.onError,resourceSlug:encodeURIComponent(d),resourceSlugValue:d,sentryDsn:g}}function l(e){let t=c(e,`signupSlug`);return{...t,signupSlug:t.resourceSlug,signupSlugValue:t.resourceSlugValue}}function u(e){if(typeof e!=`object`||!e||Object.isFrozen(e))return e;for(let t of Object.values(e))u(t);return Object.freeze(e)}function d({communitySlug:e,environment:t,getContext:n,onError:r,resourceContextName:i,sentryDsn:a}){let o=null;return function(s){try{r?.(s)}catch{}if(s.reportable&&a&&typeof window<`u`){let r=o??import(`./telemetry.js`);o=r;let c={communitySlug:e,...n()};s.status!==void 0&&(c.status=s.status),r.then(({captureSdkError:e})=>e({context:c,contextName:i,dsn:a,environment:t,error:s})).catch(()=>{o===r&&(o=null)})}return s}}function f(e){if(typeof e!=`object`||!e||Array.isArray(e))throw TypeError(`Expected an object.`);return e}function p(e){if(typeof e!=`string`)throw TypeError(`Expected a string.`);return e}function m(e){let t=p(e);if(t.trim().length===0)throw TypeError(`Expected a non-empty string.`);return t}function h(e,t){return e===void 0?t:p(e)}function g(e){return e===null?null:p(e)}function _(e,t){return e===void 0?t:g(e)}function v(e){if(typeof e!=`boolean`)throw TypeError(`Expected a boolean.`);return e}function y(e,t){return e===void 0?t:v(e)}function b(e){return e!=null&&m(e).length>0}function x(e){if(!Array.isArray(e))throw TypeError(`Expected a custom field option array.`);let t=new Set,n=[];for(let r of e){let e=f(r);if(b(e.archivedAt))continue;let i=m(e.id);if(t.has(i))throw TypeError(`Expected unique custom field option IDs.`);t.add(i),n.push({id:i,label:m(e.label)})}if(n.length<2)throw TypeError(`Expected at least two active custom field options.`);return n}function S(e){if(e===void 0)return[];if(!Array.isArray(e))throw TypeError(`Expected a custom field array.`);let t=new Set,n=[];for(let r of e){let e=f(r);if(b(e.archivedAt))continue;let i=m(e.id);if(t.has(i))throw TypeError(`Expected unique custom field IDs.`);t.add(i);let a={id:i,label:m(e.label),required:v(e.required)};if(e.type===`text`||e.type===`textarea`)n.push({...a,type:e.type});else if(e.type===`radio`||e.type===`select`)n.push({...a,options:x(e.options),type:e.type});else if(e.type===`checkboxes`||e.type===`multi_select`)n.push({...a,options:x(e.options),type:e.type});else throw TypeError(`Expected a supported custom field type.`)}return n}function C(e){let t=u(e),n=new Set;return{commit(e){t=u(e);for(let e of[...n])try{e(t)}catch{}},getState(){return t},subscribe(e){n.add(e);try{e(t)}catch{}return()=>{n.delete(e)}}}}function w(t,n){
|
|
1
|
+
import{n as e}from"./types.js";const t=/\/+$/,n=new Set([`localhost`,`127.0.0.1`,`[::1]`]),r={development:{sentryDsn:`https://1977371f7bc44480935a7bc9726ca296@o1338376.ingest.sentry.io/6631829`},production:{sentryDsn:`https://c87cbc682ff0422eab5a4714acb95fd1@o1338376.ingest.sentry.io/6662564`}};function i(e){if(typeof e!=`object`||!e||Array.isArray(e))throw TypeError(`Expected an object.`);return e}function a(e){if(e===`development`||e===`production`)return e;throw TypeError(`environment must be either development or production.`)}function o(e,r){if(typeof e!=`string`)throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`);let i;try{i=new URL(e)}catch{throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`)}if(i.protocol!==`http:`&&i.protocol!==`https:`)throw TypeError(`apiBaseUrl must be a valid HTTP or HTTPS URL.`);if(i.username||i.password)throw TypeError(`apiBaseUrl must not include credentials.`);if(i.search||i.hash)throw TypeError(`apiBaseUrl must not include a query or fragment.`);if(i.protocol!==`https:`&&!(r===`development`&&n.has(i.hostname)))throw TypeError(`apiBaseUrl must use HTTPS except for development loopback endpoints.`);return i.pathname=i.pathname.replace(t,``),i.toString().replace(t,``)}function s(e,t){if(typeof e!=`string`||e.trim().length===0)throw TypeError(`${t} must be a non-empty string.`);return e}function c(e,t){let n=i(e),c=n.environment;if(n.apiBaseUrl!==void 0&&c===void 0)throw TypeError(`environment is required when apiBaseUrl is provided.`);if(n.apiBaseUrl===void 0&&c===`development`)throw TypeError(`apiBaseUrl is required when environment is development.`);let l=c===void 0?`production`:a(c),u=s(n.communitySlug,`communitySlug`),d=s(n[t],t);if(n.fetch!==void 0&&typeof n.fetch!=`function`)throw TypeError(`fetch must be a function when provided.`);if(n.onError!==void 0&&typeof n.onError!=`function`)throw TypeError(`onError must be a function when provided.`);if(n.sentryDsn!==void 0&&n.sentryDsn!==null&&typeof n.sentryDsn!=`string`)throw TypeError(`sentryDsn must be a string or null when provided.`);if(n.requestTimeoutMs!==void 0&&(!Number.isSafeInteger(n.requestTimeoutMs)||n.requestTimeoutMs<=0||n.requestTimeoutMs>2147483647))throw TypeError(`requestTimeoutMs must be a positive integer no greater than 2147483647.`);let f=n.fetch??globalThis.fetch,p=n.apiBaseUrl===void 0?`https://portal.lockerverse.com/api`:o(n.apiBaseUrl,l),m=r[l],h=n.sentryDsn,g=h===null?null:h??m.sentryDsn;return{apiBaseUrl:p,communitySlug:encodeURIComponent(u),communitySlugValue:u,environment:l,fetchImplementation:f,onError:n.onError,requestTimeoutMs:n.requestTimeoutMs??2e4,resourceSlug:encodeURIComponent(d),resourceSlugValue:d,sentryDsn:g}}function l(e){let t=c(e,`signupSlug`);return{...t,signupSlug:t.resourceSlug,signupSlugValue:t.resourceSlugValue}}function u(e){if(typeof e!=`object`||!e||Object.isFrozen(e))return e;for(let t of Object.values(e))u(t);return Object.freeze(e)}function d({communitySlug:e,environment:t,getContext:n,onError:r,resourceContextName:i,sentryDsn:a}){let o=null;return function(s){try{r?.(s)}catch{}if(s.reportable&&a&&typeof window<`u`){let r=o??import(`./telemetry.js`);o=r;let c={communitySlug:e,...n()};s.status!==void 0&&(c.status=s.status),r.then(({captureSdkError:e})=>e({context:c,contextName:i,dsn:a,environment:t,error:s})).catch(()=>{o===r&&(o=null)})}return s}}function f(e){if(typeof e!=`object`||!e||Array.isArray(e))throw TypeError(`Expected an object.`);return e}function p(e){if(typeof e!=`string`)throw TypeError(`Expected a string.`);return e}function m(e){let t=p(e);if(t.trim().length===0)throw TypeError(`Expected a non-empty string.`);return t}function h(e,t){return e===void 0?t:p(e)}function g(e){return e===null?null:p(e)}function _(e,t){return e===void 0?t:g(e)}function v(e){if(typeof e!=`boolean`)throw TypeError(`Expected a boolean.`);return e}function y(e,t){return e===void 0?t:v(e)}function b(e){return e!=null&&m(e).length>0}function x(e){if(!Array.isArray(e))throw TypeError(`Expected a custom field option array.`);let t=new Set,n=[];for(let r of e){let e=f(r);if(b(e.archivedAt))continue;let i=m(e.id);if(t.has(i))throw TypeError(`Expected unique custom field option IDs.`);t.add(i),n.push({id:i,label:m(e.label)})}if(n.length<2)throw TypeError(`Expected at least two active custom field options.`);return n}function S(e){if(e===void 0)return[];if(!Array.isArray(e))throw TypeError(`Expected a custom field array.`);let t=new Set,n=[];for(let r of e){let e=f(r);if(b(e.archivedAt))continue;let i=m(e.id);if(t.has(i))throw TypeError(`Expected unique custom field IDs.`);t.add(i);let a={id:i,label:m(e.label),required:v(e.required)};if(e.type===`text`||e.type===`textarea`)n.push({...a,type:e.type});else if(e.type===`radio`||e.type===`select`)n.push({...a,options:x(e.options),type:e.type});else if(e.type===`checkboxes`||e.type===`multi_select`)n.push({...a,options:x(e.options),type:e.type});else throw TypeError(`Expected a supported custom field type.`)}return n}function C(e){let t=u(e),n=new Set;return{commit(e){t=u(e);for(let e of[...n])try{e(t)}catch{}},getState(){return t},subscribe(e){n.add(e);try{e(t)}catch{}return()=>{n.delete(e)}}}}function w(t,n,r){function i(t){let r=new e({code:t.code,message:t.message,operation:t.operation,reportable:!0});return t.report===!1?r:n(r)}async function a(e,n,a,o,s){let c=new AbortController,l=n?.signal??void 0,u=()=>c.abort(l?.reason);l?.aborted?u():l?.addEventListener(`abort`,u,{once:!0});let d,f=new Promise((e,t)=>{d=()=>t(c.signal.reason??new DOMException(`The request was aborted.`,`AbortError`)),c.signal.aborted?d():c.signal.addEventListener(`abort`,d,{once:!0})}),p=setTimeout(()=>{c.abort(new DOMException(`The request timed out.`,`TimeoutError`))},r);try{let r;try{r=await Promise.race([t(e,{...n,signal:c.signal}),f])}catch{throw i(o)}if(!r.ok)return{ok:!1,response:r};try{let e=await Promise.race([r.json(),f]);return{ok:!0,response:r,value:a(e)}}catch{throw i(s)}}finally{clearTimeout(p),l?.removeEventListener(`abort`,u),d&&c.signal.removeEventListener(`abort`,d)}}return{requestJson:a}}export{m as a,_ as c,d,u as f,S as i,h as l,l as m,C as n,g as o,c as p,v as r,y as s,w as t,f as u};
|
|
2
2
|
//# sourceMappingURL=transport.js.map
|
package/dist/transport.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"transport.js","names":["parseRecord"],"sources":["../src/environment.ts","../src/deep-freeze.ts","../src/error-reporting.ts","../src/parsing.ts","../src/state.ts","../src/transport.ts"],"sourcesContent":["import type { CreateLockerverseSignupOptions } from \"./signup-types.ts\";\nimport type { LockerverseEnvironment, LockerverseSdkError } from \"./types.ts\";\n\nconst DEFAULT_API_BASE_URL = \"https://portal.lockerverse.com/api\";\nconst TRAILING_SLASHES = /\\/+$/;\nconst LOOPBACK_HOSTNAMES = new Set([\"localhost\", \"127.0.0.1\", \"[::1]\"]);\nconst ENVIRONMENT_CONFIG = {\n development: {\n sentryDsn:\n \"https://1977371f7bc44480935a7bc9726ca296@o1338376.ingest.sentry.io/6631829\",\n },\n production: {\n sentryDsn:\n \"https://c87cbc682ff0422eab5a4714acb95fd1@o1338376.ingest.sentry.io/6662564\",\n },\n} as const;\n\nfunction parseRecord(value: unknown): Record<string, unknown> {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) {\n throw new TypeError(\"Expected an object.\");\n }\n return value as Record<string, unknown>;\n}\n\nfunction parseEnvironment(value: unknown): LockerverseEnvironment {\n if (value === \"development\" || value === \"production\") {\n return value;\n }\n throw new TypeError(\"environment must be either development or production.\");\n}\n\nfunction parseApiBaseUrl(value: unknown, environment: LockerverseEnvironment) {\n if (typeof value !== \"string\") {\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n let url: URL;\n try {\n url = new URL(value);\n } catch {\n // biome-ignore lint/style/useErrorCause: The URL parser error can contain the rejected endpoint or credentials.\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n if (url.protocol !== \"http:\" && url.protocol !== \"https:\") {\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n if (url.username || url.password) {\n throw new TypeError(\"apiBaseUrl must not include credentials.\");\n }\n if (url.search || url.hash) {\n throw new TypeError(\"apiBaseUrl must not include a query or fragment.\");\n }\n if (\n url.protocol !== \"https:\" &&\n !(environment === \"development\" && LOOPBACK_HOSTNAMES.has(url.hostname))\n ) {\n throw new TypeError(\n \"apiBaseUrl must use HTTPS except for development loopback endpoints.\"\n );\n }\n url.pathname = url.pathname.replace(TRAILING_SLASHES, \"\");\n return url.toString().replace(TRAILING_SLASHES, \"\");\n}\n\nfunction parseSlug(value: unknown, name: string) {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new TypeError(`${name} must be a non-empty string.`);\n }\n return value;\n}\n\nexport function resolveResourceEnvironment(\n options: unknown,\n resourceSlugKey: string\n) {\n const runtimeOptions = parseRecord(options);\n const requestedEnvironment = runtimeOptions.environment;\n if (\n runtimeOptions.apiBaseUrl !== undefined &&\n requestedEnvironment === undefined\n ) {\n throw new TypeError(\"environment is required when apiBaseUrl is provided.\");\n }\n if (\n runtimeOptions.apiBaseUrl === undefined &&\n requestedEnvironment === \"development\"\n ) {\n throw new TypeError(\n \"apiBaseUrl is required when environment is development.\"\n );\n }\n\n const environment =\n requestedEnvironment === undefined\n ? \"production\"\n : parseEnvironment(requestedEnvironment);\n const communitySlugValue = parseSlug(\n runtimeOptions.communitySlug,\n \"communitySlug\"\n );\n const resourceSlugValue = parseSlug(\n runtimeOptions[resourceSlugKey],\n resourceSlugKey\n );\n if (\n runtimeOptions.fetch !== undefined &&\n typeof runtimeOptions.fetch !== \"function\"\n ) {\n throw new TypeError(\"fetch must be a function when provided.\");\n }\n if (\n runtimeOptions.onError !== undefined &&\n typeof runtimeOptions.onError !== \"function\"\n ) {\n throw new TypeError(\"onError must be a function when provided.\");\n }\n if (\n runtimeOptions.sentryDsn !== undefined &&\n runtimeOptions.sentryDsn !== null &&\n typeof runtimeOptions.sentryDsn !== \"string\"\n ) {\n throw new TypeError(\"sentryDsn must be a string or null when provided.\");\n }\n\n const fetchImplementation =\n (runtimeOptions.fetch as typeof globalThis.fetch | undefined) ??\n globalThis.fetch;\n const apiBaseUrl =\n runtimeOptions.apiBaseUrl === undefined\n ? DEFAULT_API_BASE_URL\n : parseApiBaseUrl(runtimeOptions.apiBaseUrl, environment);\n const environmentConfig = ENVIRONMENT_CONFIG[environment];\n const configuredSentryDsn = runtimeOptions.sentryDsn as\n | string\n | null\n | undefined;\n const sentryDsn =\n configuredSentryDsn === null\n ? null\n : (configuredSentryDsn ?? environmentConfig.sentryDsn);\n\n return {\n apiBaseUrl,\n communitySlug: encodeURIComponent(communitySlugValue),\n communitySlugValue,\n environment,\n fetchImplementation,\n onError: runtimeOptions.onError as\n | ((error: LockerverseSdkError) => void)\n | undefined,\n resourceSlug: encodeURIComponent(resourceSlugValue),\n resourceSlugValue,\n sentryDsn,\n };\n}\n\nexport function resolveSignupEnvironment(\n options: CreateLockerverseSignupOptions\n) {\n const runtime = resolveResourceEnvironment(options, \"signupSlug\");\n return {\n ...runtime,\n signupSlug: runtime.resourceSlug,\n signupSlugValue: runtime.resourceSlugValue,\n };\n}\n","export function deepFreeze<T>(value: T): T {\n if (typeof value !== \"object\" || value === null || Object.isFrozen(value)) {\n return value;\n }\n for (const nestedValue of Object.values(value)) {\n deepFreeze(nestedValue);\n }\n return Object.freeze(value);\n}\n","import type { LockerverseEnvironment, LockerverseSdkError } from \"./types.ts\";\n\ntype TelemetryValue = boolean | number | string | null;\n\nexport function createSdkErrorReporter({\n communitySlug,\n environment,\n getContext,\n onError,\n resourceContextName,\n sentryDsn,\n}: {\n communitySlug: string;\n environment: LockerverseEnvironment;\n getContext: () => Record<string, TelemetryValue>;\n onError: ((error: LockerverseSdkError) => void) | undefined;\n resourceContextName: string;\n sentryDsn: string | null;\n}) {\n let telemetryModulePromise: Promise<typeof import(\"./telemetry.ts\")> | null =\n null;\n\n return function reportError(error: LockerverseSdkError) {\n try {\n onError?.(error);\n } catch {\n // Host error reporting must never interrupt an SDK workflow.\n }\n\n if (error.reportable && sentryDsn && typeof window !== \"undefined\") {\n const telemetryPromise =\n telemetryModulePromise ?? import(\"./telemetry.ts\");\n telemetryModulePromise = telemetryPromise;\n const context: Record<string, TelemetryValue> = {\n communitySlug,\n ...getContext(),\n };\n if (error.status !== undefined) {\n context.status = error.status;\n }\n telemetryPromise\n .then(({ captureSdkError }) =>\n captureSdkError({\n context,\n contextName: resourceContextName,\n dsn: sentryDsn,\n environment,\n error,\n })\n )\n .catch(() => {\n if (telemetryModulePromise === telemetryPromise) {\n telemetryModulePromise = null;\n }\n });\n }\n\n return error;\n };\n}\n","import type {\n LockerverseCustomField,\n LockerverseCustomFieldOption,\n} from \"./types.ts\";\n\nexport function parseRecord(value: unknown): Record<string, unknown> {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) {\n throw new TypeError(\"Expected an object.\");\n }\n\n return value as Record<string, unknown>;\n}\n\nfunction parseString(value: unknown): string {\n if (typeof value !== \"string\") {\n throw new TypeError(\"Expected a string.\");\n }\n\n return value;\n}\n\nexport function parseNonEmptyString(value: unknown): string {\n const parsed = parseString(value);\n if (parsed.trim().length === 0) {\n throw new TypeError(\"Expected a non-empty string.\");\n }\n\n return parsed;\n}\n\nexport function parseOptionalString(value: unknown, fallback: string): string {\n return value === undefined ? fallback : parseString(value);\n}\n\nexport function parseNullableString(value: unknown): string | null {\n return value === null ? null : parseString(value);\n}\n\nexport function parseOptionalNullableString(\n value: unknown,\n fallback: string | null\n): string | null {\n if (value === undefined) {\n return fallback;\n }\n return parseNullableString(value);\n}\n\nexport function parseBoolean(value: unknown): boolean {\n if (typeof value !== \"boolean\") {\n throw new TypeError(\"Expected a boolean.\");\n }\n\n return value;\n}\n\nexport function parseOptionalBoolean(\n value: unknown,\n fallback: boolean\n): boolean {\n return value === undefined ? fallback : parseBoolean(value);\n}\n\nfunction parseArchived(value: unknown): boolean {\n if (value === undefined || value === null) {\n return false;\n }\n return parseNonEmptyString(value).length > 0;\n}\n\nfunction parseCustomFieldOptions(\n value: unknown\n): LockerverseCustomFieldOption[] {\n if (!Array.isArray(value)) {\n throw new TypeError(\"Expected a custom field option array.\");\n }\n const optionIds = new Set<string>();\n const options: LockerverseCustomFieldOption[] = [];\n for (const optionValue of value) {\n const option = parseRecord(optionValue);\n if (parseArchived(option.archivedAt)) {\n continue;\n }\n const id = parseNonEmptyString(option.id);\n if (optionIds.has(id)) {\n throw new TypeError(\"Expected unique custom field option IDs.\");\n }\n optionIds.add(id);\n options.push({ id, label: parseNonEmptyString(option.label) });\n }\n if (options.length < 2) {\n throw new TypeError(\"Expected at least two active custom field options.\");\n }\n return options;\n}\n\nexport function parseCustomFields(value: unknown): LockerverseCustomField[] {\n if (value === undefined) {\n return [];\n }\n if (!Array.isArray(value)) {\n throw new TypeError(\"Expected a custom field array.\");\n }\n const fieldIds = new Set<string>();\n const fields: LockerverseCustomField[] = [];\n for (const fieldValue of value) {\n const field = parseRecord(fieldValue);\n if (parseArchived(field.archivedAt)) {\n continue;\n }\n const id = parseNonEmptyString(field.id);\n if (fieldIds.has(id)) {\n throw new TypeError(\"Expected unique custom field IDs.\");\n }\n fieldIds.add(id);\n const base = {\n id,\n label: parseNonEmptyString(field.label),\n required: parseBoolean(field.required),\n };\n if (field.type === \"text\" || field.type === \"textarea\") {\n fields.push({ ...base, type: field.type });\n } else if (field.type === \"radio\" || field.type === \"select\") {\n fields.push({\n ...base,\n options: parseCustomFieldOptions(field.options),\n type: field.type,\n });\n } else if (field.type === \"checkboxes\" || field.type === \"multi_select\") {\n fields.push({\n ...base,\n options: parseCustomFieldOptions(field.options),\n type: field.type,\n });\n } else {\n throw new TypeError(\"Expected a supported custom field type.\");\n }\n }\n return fields;\n}\n","import { deepFreeze } from \"./deep-freeze.ts\";\n\nexport function createStateStore<State>(initialState: State) {\n let state = deepFreeze(initialState);\n const listeners = new Set<(nextState: State) => void>();\n\n return {\n commit(nextState: State) {\n state = deepFreeze(nextState);\n for (const listener of [...listeners]) {\n try {\n listener(state);\n } catch {\n // Host listeners cannot interrupt SDK state transitions.\n }\n }\n },\n getState() {\n return state;\n },\n subscribe(listener: (nextState: State) => void) {\n listeners.add(listener);\n try {\n listener(state);\n } catch {\n // A failing initial render must not prevent subscription or checkout.\n }\n return () => {\n listeners.delete(listener);\n };\n },\n };\n}\n","import {\n LockerverseSdkError,\n type LockerverseSdkErrorCode,\n type LockerverseSdkOperation,\n} from \"./types.ts\";\n\ntype ErrorContext = {\n code: LockerverseSdkErrorCode;\n message: string;\n operation: LockerverseSdkOperation;\n report?: boolean;\n};\n\ntype ReportError = (error: LockerverseSdkError) => LockerverseSdkError;\n\nexport function createTransport(\n fetchImplementation: typeof globalThis.fetch,\n reportError: ReportError\n) {\n async function fetchResponse(\n input: string,\n init: RequestInit | undefined,\n context: ErrorContext\n ) {\n try {\n return await fetchImplementation(input, init);\n } catch {\n const error = new LockerverseSdkError({\n code: context.code,\n message: context.message,\n operation: context.operation,\n reportable: true,\n });\n // biome-ignore lint/style/useErrorCause: Raw host network errors are intentionally excluded from public SDK errors and telemetry.\n throw context.report === false ? error : reportError(error);\n }\n }\n\n async function parseResponseJson<T>(\n response: Response,\n parser: (value: unknown) => T,\n context: ErrorContext\n ) {\n try {\n const value: unknown = await response.json();\n return parser(value);\n } catch {\n const error = new LockerverseSdkError({\n code: context.code,\n message: context.message,\n operation: context.operation,\n reportable: true,\n });\n // biome-ignore lint/style/useErrorCause: Raw parse and validation errors must not escape the SDK boundary.\n throw context.report === false ? error : reportError(error);\n }\n }\n\n return { fetchResponse, parseResponseJson };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"transport.js","names":["parseRecord"],"sources":["../src/environment.ts","../src/deep-freeze.ts","../src/error-reporting.ts","../src/parsing.ts","../src/state.ts","../src/transport.ts"],"sourcesContent":["import type { CreateLockerverseSignupOptions } from \"./signup-types.ts\";\nimport type { LockerverseEnvironment, LockerverseSdkError } from \"./types.ts\";\n\nconst DEFAULT_API_BASE_URL = \"https://portal.lockerverse.com/api\";\nconst DEFAULT_REQUEST_TIMEOUT_MS = 20_000;\nconst MAX_REQUEST_TIMEOUT_MS = 2_147_483_647;\nconst TRAILING_SLASHES = /\\/+$/;\nconst LOOPBACK_HOSTNAMES = new Set([\"localhost\", \"127.0.0.1\", \"[::1]\"]);\nconst ENVIRONMENT_CONFIG = {\n development: {\n sentryDsn:\n \"https://1977371f7bc44480935a7bc9726ca296@o1338376.ingest.sentry.io/6631829\",\n },\n production: {\n sentryDsn:\n \"https://c87cbc682ff0422eab5a4714acb95fd1@o1338376.ingest.sentry.io/6662564\",\n },\n} as const;\n\nfunction parseRecord(value: unknown): Record<string, unknown> {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) {\n throw new TypeError(\"Expected an object.\");\n }\n return value as Record<string, unknown>;\n}\n\nfunction parseEnvironment(value: unknown): LockerverseEnvironment {\n if (value === \"development\" || value === \"production\") {\n return value;\n }\n throw new TypeError(\"environment must be either development or production.\");\n}\n\nfunction parseApiBaseUrl(value: unknown, environment: LockerverseEnvironment) {\n if (typeof value !== \"string\") {\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n let url: URL;\n try {\n url = new URL(value);\n } catch {\n // biome-ignore lint/style/useErrorCause: The URL parser error can contain the rejected endpoint or credentials.\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n if (url.protocol !== \"http:\" && url.protocol !== \"https:\") {\n throw new TypeError(\"apiBaseUrl must be a valid HTTP or HTTPS URL.\");\n }\n if (url.username || url.password) {\n throw new TypeError(\"apiBaseUrl must not include credentials.\");\n }\n if (url.search || url.hash) {\n throw new TypeError(\"apiBaseUrl must not include a query or fragment.\");\n }\n if (\n url.protocol !== \"https:\" &&\n !(environment === \"development\" && LOOPBACK_HOSTNAMES.has(url.hostname))\n ) {\n throw new TypeError(\n \"apiBaseUrl must use HTTPS except for development loopback endpoints.\"\n );\n }\n url.pathname = url.pathname.replace(TRAILING_SLASHES, \"\");\n return url.toString().replace(TRAILING_SLASHES, \"\");\n}\n\nfunction parseSlug(value: unknown, name: string) {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new TypeError(`${name} must be a non-empty string.`);\n }\n return value;\n}\n\nexport function resolveResourceEnvironment(\n options: unknown,\n resourceSlugKey: string\n) {\n const runtimeOptions = parseRecord(options);\n const requestedEnvironment = runtimeOptions.environment;\n if (\n runtimeOptions.apiBaseUrl !== undefined &&\n requestedEnvironment === undefined\n ) {\n throw new TypeError(\"environment is required when apiBaseUrl is provided.\");\n }\n if (\n runtimeOptions.apiBaseUrl === undefined &&\n requestedEnvironment === \"development\"\n ) {\n throw new TypeError(\n \"apiBaseUrl is required when environment is development.\"\n );\n }\n\n const environment =\n requestedEnvironment === undefined\n ? \"production\"\n : parseEnvironment(requestedEnvironment);\n const communitySlugValue = parseSlug(\n runtimeOptions.communitySlug,\n \"communitySlug\"\n );\n const resourceSlugValue = parseSlug(\n runtimeOptions[resourceSlugKey],\n resourceSlugKey\n );\n if (\n runtimeOptions.fetch !== undefined &&\n typeof runtimeOptions.fetch !== \"function\"\n ) {\n throw new TypeError(\"fetch must be a function when provided.\");\n }\n if (\n runtimeOptions.onError !== undefined &&\n typeof runtimeOptions.onError !== \"function\"\n ) {\n throw new TypeError(\"onError must be a function when provided.\");\n }\n if (\n runtimeOptions.sentryDsn !== undefined &&\n runtimeOptions.sentryDsn !== null &&\n typeof runtimeOptions.sentryDsn !== \"string\"\n ) {\n throw new TypeError(\"sentryDsn must be a string or null when provided.\");\n }\n if (\n runtimeOptions.requestTimeoutMs !== undefined &&\n (!Number.isSafeInteger(runtimeOptions.requestTimeoutMs) ||\n (runtimeOptions.requestTimeoutMs as number) <= 0 ||\n (runtimeOptions.requestTimeoutMs as number) > MAX_REQUEST_TIMEOUT_MS)\n ) {\n throw new TypeError(\n \"requestTimeoutMs must be a positive integer no greater than 2147483647.\"\n );\n }\n\n const fetchImplementation =\n (runtimeOptions.fetch as typeof globalThis.fetch | undefined) ??\n globalThis.fetch;\n const apiBaseUrl =\n runtimeOptions.apiBaseUrl === undefined\n ? DEFAULT_API_BASE_URL\n : parseApiBaseUrl(runtimeOptions.apiBaseUrl, environment);\n const environmentConfig = ENVIRONMENT_CONFIG[environment];\n const configuredSentryDsn = runtimeOptions.sentryDsn as\n | string\n | null\n | undefined;\n const sentryDsn =\n configuredSentryDsn === null\n ? null\n : (configuredSentryDsn ?? environmentConfig.sentryDsn);\n\n return {\n apiBaseUrl,\n communitySlug: encodeURIComponent(communitySlugValue),\n communitySlugValue,\n environment,\n fetchImplementation,\n onError: runtimeOptions.onError as\n | ((error: LockerverseSdkError) => void)\n | undefined,\n requestTimeoutMs:\n (runtimeOptions.requestTimeoutMs as number | undefined) ??\n DEFAULT_REQUEST_TIMEOUT_MS,\n resourceSlug: encodeURIComponent(resourceSlugValue),\n resourceSlugValue,\n sentryDsn,\n };\n}\n\nexport function resolveSignupEnvironment(\n options: CreateLockerverseSignupOptions\n) {\n const runtime = resolveResourceEnvironment(options, \"signupSlug\");\n return {\n ...runtime,\n signupSlug: runtime.resourceSlug,\n signupSlugValue: runtime.resourceSlugValue,\n };\n}\n","export function deepFreeze<T>(value: T): T {\n if (typeof value !== \"object\" || value === null || Object.isFrozen(value)) {\n return value;\n }\n for (const nestedValue of Object.values(value)) {\n deepFreeze(nestedValue);\n }\n return Object.freeze(value);\n}\n","import type { LockerverseEnvironment, LockerverseSdkError } from \"./types.ts\";\n\ntype TelemetryValue = boolean | number | string | null;\n\nexport function createSdkErrorReporter({\n communitySlug,\n environment,\n getContext,\n onError,\n resourceContextName,\n sentryDsn,\n}: {\n communitySlug: string;\n environment: LockerverseEnvironment;\n getContext: () => Record<string, TelemetryValue>;\n onError: ((error: LockerverseSdkError) => void) | undefined;\n resourceContextName: string;\n sentryDsn: string | null;\n}) {\n let telemetryModulePromise: Promise<typeof import(\"./telemetry.ts\")> | null =\n null;\n\n return function reportError(error: LockerverseSdkError) {\n try {\n onError?.(error);\n } catch {\n // Host error reporting must never interrupt an SDK workflow.\n }\n\n if (error.reportable && sentryDsn && typeof window !== \"undefined\") {\n const telemetryPromise =\n telemetryModulePromise ?? import(\"./telemetry.ts\");\n telemetryModulePromise = telemetryPromise;\n const context: Record<string, TelemetryValue> = {\n communitySlug,\n ...getContext(),\n };\n if (error.status !== undefined) {\n context.status = error.status;\n }\n telemetryPromise\n .then(({ captureSdkError }) =>\n captureSdkError({\n context,\n contextName: resourceContextName,\n dsn: sentryDsn,\n environment,\n error,\n })\n )\n .catch(() => {\n if (telemetryModulePromise === telemetryPromise) {\n telemetryModulePromise = null;\n }\n });\n }\n\n return error;\n };\n}\n","import type {\n LockerverseCustomField,\n LockerverseCustomFieldOption,\n} from \"./types.ts\";\n\nexport function parseRecord(value: unknown): Record<string, unknown> {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) {\n throw new TypeError(\"Expected an object.\");\n }\n\n return value as Record<string, unknown>;\n}\n\nfunction parseString(value: unknown): string {\n if (typeof value !== \"string\") {\n throw new TypeError(\"Expected a string.\");\n }\n\n return value;\n}\n\nexport function parseNonEmptyString(value: unknown): string {\n const parsed = parseString(value);\n if (parsed.trim().length === 0) {\n throw new TypeError(\"Expected a non-empty string.\");\n }\n\n return parsed;\n}\n\nexport function parseOptionalString(value: unknown, fallback: string): string {\n return value === undefined ? fallback : parseString(value);\n}\n\nexport function parseNullableString(value: unknown): string | null {\n return value === null ? null : parseString(value);\n}\n\nexport function parseOptionalNullableString(\n value: unknown,\n fallback: string | null\n): string | null {\n if (value === undefined) {\n return fallback;\n }\n return parseNullableString(value);\n}\n\nexport function parseBoolean(value: unknown): boolean {\n if (typeof value !== \"boolean\") {\n throw new TypeError(\"Expected a boolean.\");\n }\n\n return value;\n}\n\nexport function parseOptionalBoolean(\n value: unknown,\n fallback: boolean\n): boolean {\n return value === undefined ? fallback : parseBoolean(value);\n}\n\nfunction parseArchived(value: unknown): boolean {\n if (value === undefined || value === null) {\n return false;\n }\n return parseNonEmptyString(value).length > 0;\n}\n\nfunction parseCustomFieldOptions(\n value: unknown\n): LockerverseCustomFieldOption[] {\n if (!Array.isArray(value)) {\n throw new TypeError(\"Expected a custom field option array.\");\n }\n const optionIds = new Set<string>();\n const options: LockerverseCustomFieldOption[] = [];\n for (const optionValue of value) {\n const option = parseRecord(optionValue);\n if (parseArchived(option.archivedAt)) {\n continue;\n }\n const id = parseNonEmptyString(option.id);\n if (optionIds.has(id)) {\n throw new TypeError(\"Expected unique custom field option IDs.\");\n }\n optionIds.add(id);\n options.push({ id, label: parseNonEmptyString(option.label) });\n }\n if (options.length < 2) {\n throw new TypeError(\"Expected at least two active custom field options.\");\n }\n return options;\n}\n\nexport function parseCustomFields(value: unknown): LockerverseCustomField[] {\n if (value === undefined) {\n return [];\n }\n if (!Array.isArray(value)) {\n throw new TypeError(\"Expected a custom field array.\");\n }\n const fieldIds = new Set<string>();\n const fields: LockerverseCustomField[] = [];\n for (const fieldValue of value) {\n const field = parseRecord(fieldValue);\n if (parseArchived(field.archivedAt)) {\n continue;\n }\n const id = parseNonEmptyString(field.id);\n if (fieldIds.has(id)) {\n throw new TypeError(\"Expected unique custom field IDs.\");\n }\n fieldIds.add(id);\n const base = {\n id,\n label: parseNonEmptyString(field.label),\n required: parseBoolean(field.required),\n };\n if (field.type === \"text\" || field.type === \"textarea\") {\n fields.push({ ...base, type: field.type });\n } else if (field.type === \"radio\" || field.type === \"select\") {\n fields.push({\n ...base,\n options: parseCustomFieldOptions(field.options),\n type: field.type,\n });\n } else if (field.type === \"checkboxes\" || field.type === \"multi_select\") {\n fields.push({\n ...base,\n options: parseCustomFieldOptions(field.options),\n type: field.type,\n });\n } else {\n throw new TypeError(\"Expected a supported custom field type.\");\n }\n }\n return fields;\n}\n","import { deepFreeze } from \"./deep-freeze.ts\";\n\nexport function createStateStore<State>(initialState: State) {\n let state = deepFreeze(initialState);\n const listeners = new Set<(nextState: State) => void>();\n\n return {\n commit(nextState: State) {\n state = deepFreeze(nextState);\n for (const listener of [...listeners]) {\n try {\n listener(state);\n } catch {\n // Host listeners cannot interrupt SDK state transitions.\n }\n }\n },\n getState() {\n return state;\n },\n subscribe(listener: (nextState: State) => void) {\n listeners.add(listener);\n try {\n listener(state);\n } catch {\n // A failing initial render must not prevent subscription or checkout.\n }\n return () => {\n listeners.delete(listener);\n };\n },\n };\n}\n","import {\n LockerverseSdkError,\n type LockerverseSdkErrorCode,\n type LockerverseSdkOperation,\n} from \"./types.ts\";\n\ntype ErrorContext = {\n code: LockerverseSdkErrorCode;\n message: string;\n operation: LockerverseSdkOperation;\n report?: boolean;\n};\n\ntype ReportError = (error: LockerverseSdkError) => LockerverseSdkError;\n\ntype JsonResponse<T> =\n | { ok: false; response: Response }\n | { ok: true; response: Response; value: T };\n\nexport function createTransport(\n fetchImplementation: typeof globalThis.fetch,\n reportError: ReportError,\n requestTimeoutMs: number\n) {\n function createBoundaryError(context: ErrorContext) {\n const error = new LockerverseSdkError({\n code: context.code,\n message: context.message,\n operation: context.operation,\n reportable: true,\n });\n return context.report === false ? error : reportError(error);\n }\n\n async function requestJson<T>(\n input: string,\n init: RequestInit | undefined,\n parser: (value: unknown) => T,\n requestContext: ErrorContext,\n responseContext: ErrorContext\n ): Promise<JsonResponse<T>> {\n const controller = new AbortController();\n const callerSignal = init?.signal ?? undefined;\n const abortFromCaller = () => controller.abort(callerSignal?.reason);\n if (callerSignal?.aborted) {\n abortFromCaller();\n } else {\n callerSignal?.addEventListener(\"abort\", abortFromCaller, { once: true });\n }\n\n let rejectWhenAborted: (() => void) | undefined;\n const aborted = new Promise<never>((_resolve, reject) => {\n rejectWhenAborted = () =>\n reject(\n controller.signal.reason ??\n new DOMException(\"The request was aborted.\", \"AbortError\")\n );\n if (controller.signal.aborted) {\n rejectWhenAborted();\n } else {\n controller.signal.addEventListener(\"abort\", rejectWhenAborted, {\n once: true,\n });\n }\n });\n const timeout = setTimeout(() => {\n controller.abort(\n new DOMException(\"The request timed out.\", \"TimeoutError\")\n );\n }, requestTimeoutMs);\n\n try {\n let response: Response;\n try {\n response = await Promise.race([\n fetchImplementation(input, { ...init, signal: controller.signal }),\n aborted,\n ]);\n } catch {\n // biome-ignore lint/style/useErrorCause: Raw host network errors are intentionally excluded from public SDK errors and telemetry.\n throw createBoundaryError(requestContext);\n }\n\n if (!response.ok) {\n return { ok: false, response };\n }\n\n try {\n const value = await Promise.race([response.json(), aborted]);\n return { ok: true, response, value: parser(value) };\n } catch {\n // biome-ignore lint/style/useErrorCause: Raw parse and validation errors must not escape the SDK boundary.\n throw createBoundaryError(responseContext);\n }\n } finally {\n clearTimeout(timeout);\n callerSignal?.removeEventListener(\"abort\", abortFromCaller);\n if (rejectWhenAborted) {\n controller.signal.removeEventListener(\"abort\", rejectWhenAborted);\n }\n }\n }\n\n return { requestJson };\n}\n"],"mappings":"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"}
|
package/dist/types.d.ts
CHANGED
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","names":[],"sources":["../src/types.ts"],"mappings":";KAEY;KACA;cAEC;KAED;EACV;EACA;EACA;EACA;EACA;EACA;EACA,eAAe;EACf;EACA;EACA;EACA;EACA;EACA;;KAGU;EACV,SAAS;EACT,eAAe;EACf,UAAU;EACV,QAAQ;;KAGE;EACV;EACA;;KAGU;EACV;EACA;;KAGU,0CACV;EACE;;KAGQ;EACV;EACA;EACA;EACA;EACA;EACA;EACA;;KAGU;EAAiC;EAAY;;KAEpD;EACH;EACA;EACA;;KAGU,6BAA6B;EACvC;;KAGU,qCAAqC;EAC/C,SAAS;EACT;;KAGU,oCAAoC;EAC9C,SAAS;EACT;;KAGU,yBACR,6BACA,qCACA;KAEQ,kCACV,cAAc,0BACZ,cAAc;KAEN,6BACV,cAAc,yBAAyB,0BACrC,cAAc;EACZ,SAAS;EAAa,OAAO,kCAAkC;;KAGzD;EACV,cAAc;EACd;EACA,QAAQ;EACR;EACA;EACA;EACA;;KAGU;KASA;cASC,4BAA4B;WAC9B,MAAM;WACN,WAAW;WACX;WACA;WACA;EAEG,cACV,MACA,SACA,WACA,YACA;IAEA,MAAM;IACN;IACA,WAAW;IACX;IACA;;;KAYQ;EACV;EACA;EACA;EACA;EACA;EACA;EACA,eAAe;EACf;EACA;EACA;;KAGU;EACV;EACA;;KAGU;EACV;EACA;EACA;EACA;EACA;EACA;EACA;;KAGU,2BAA2B;EACrC,iBAAiB;EACjB;EACA;EACA,SAAS;EACT;EACA,WAAW;;KAGD,2BAA2B;KAE3B;EACV;EACA;EACA;EACA;;KAGU,6BAA6B;EACvC;EACA;;KAGU;KAMA;EACV;EACA;EACA,gBAAgB;EAChB;EACA;EACA;;KAGU;EACV;EACA,qBAAqB;EACrB;EACA;EACA;EACA,WAAW;EACX;;KAGU;EACN;EAAe,WAAW;;EAC1B;EAAkB,WAAW;;EAE7B;EACA,SAAS;EACT,WAAW;EACX,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,SAAS;EACT,OAAO;;EAGP;EACA,SAAS;EACT,WAAW;EACX,SAAS;EACT,OAAO;;EAGP;EACA,SAAS;EACT,WAAW;EACX;;EAGA;EACA,SAAS;EACT,WAAW;EACX,OAAO;EACP,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,OAAO;EACP;;KAGM;EACN;EAAmB;EAAqB;;EACxC;EAAmB;EAAqB;;KAElC;EACV,OAAO;;KAGJ;EACH;EACA,eAAe,WAAW;EAC1B,WAAW,OAAO;EAClB;EACA;;KAGU,iCACV;EAGQ;EACA,aAAa;;EAGb;EACA;;KAIE;EACV,iBACE,QAAQ,oCACL,QAAQ;EACb;EACA,oBAAoB;EACpB,gBAAgB;EAChB,mBACE,8BACG,QAAQ;EACb,YAAY,QAAQ;EACpB,eACE,QAAQ,oCACL;EACL,SAAS;EACT,YAAY,qBAAqB;EACjC,cAAc,qBAAqB;EACnC,gBACE,YAAY,iCACT,QAAQ;EACb,YAAY,WAAW,OAAO"}
|
|
1
|
+
{"version":3,"file":"types.d.ts","names":[],"sources":["../src/types.ts"],"mappings":";KAEY;KACA;cAEC;KAED;EACV;EACA;EACA;EACA;EACA;EACA;EACA,eAAe;EACf;EACA;EACA;EACA;EACA;EACA;;KAGU;EACV,SAAS;EACT,eAAe;EACf,UAAU;EACV,QAAQ;;KAGE;EACV;EACA;;KAGU;EACV;EACA;;KAGU,0CACV;EACE;;KAGQ;EACV;EACA;EACA;EACA;EACA;EACA;EACA;;KAGU;EAAiC;EAAY;;KAEpD;EACH;EACA;EACA;;KAGU,6BAA6B;EACvC;;KAGU,qCAAqC;EAC/C,SAAS;EACT;;KAGU,oCAAoC;EAC9C,SAAS;EACT;;KAGU,yBACR,6BACA,qCACA;KAEQ,kCACV,cAAc,0BACZ,cAAc;KAEN,6BACV,cAAc,yBAAyB,0BACrC,cAAc;EACZ,SAAS;EAAa,OAAO,kCAAkC;;KAGzD;EACV,cAAc;EACd;EACA,QAAQ;EACR;EACA;EACA;EACA;;KAGU;KASA;cASC,4BAA4B;WAC9B,MAAM;WACN,WAAW;WACX;WACA;WACA;EAEG,cACV,MACA,SACA,WACA,YACA;IAEA,MAAM;IACN;IACA,WAAW;IACX;IACA;;;KAYQ;EACV;EACA;EACA;EACA;EACA;EACA;EACA,eAAe;EACf;EACA;EACA;;KAGU;EACV;EACA;;KAGU;EACV;EACA;EACA;EACA;EACA;EACA;EACA;;KAGU,2BAA2B;EACrC,iBAAiB;EACjB;EACA;EACA,SAAS;EACT;EACA,WAAW;;KAGD,2BAA2B;KAE3B;EACV;EACA;EACA;EACA;;KAGU,6BAA6B;EACvC;EACA;;KAGU;KAMA;EACV;EACA;EACA,gBAAgB;EAChB;EACA;EACA;;KAGU;EACV;EACA,qBAAqB;EACrB;EACA;EACA;EACA,WAAW;EACX;;KAGU;EACN;EAAe,WAAW;;EAC1B;EAAkB,WAAW;;EAE7B;EACA,SAAS;EACT,WAAW;EACX,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,SAAS;EACT,OAAO;;EAGP;EACA,SAAS;EACT,WAAW;EACX,SAAS;EACT,OAAO;;EAGP;EACA,SAAS;EACT,WAAW;EACX;;EAGA;EACA,SAAS;EACT,WAAW;EACX,OAAO;EACP,SAAS;;EAGT;EACA,SAAS;EACT,WAAW;EACX,OAAO;EACP;;KAGM;EACN;EAAmB;EAAqB;;EACxC;EAAmB;EAAqB;;KAElC;EACV,OAAO;;KAGJ;EACH;EACA,eAAe,WAAW;EAC1B,WAAW,OAAO;EAClB;EACA;EACA;;KAGU,iCACV;EAGQ;EACA,aAAa;;EAGb;EACA;;KAIE;EACV,iBACE,QAAQ,oCACL,QAAQ;EACb;EACA,oBAAoB;EACpB,gBAAgB;EAChB,mBACE,8BACG,QAAQ;EACb,YAAY,QAAQ;EACpB,eACE,QAAQ,oCACL;EACL,SAAS;EACT,YAAY,qBAAqB;EACjC,cAAc,qBAAqB;EACnC,gBACE,YAAY,iCACT,QAAQ;EACb,YAAY,WAAW,OAAO"}
|
package/dist/types.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
const e=`0.1.0-alpha.
|
|
1
|
+
const e=`0.1.0-alpha.3`;var t=class extends Error{code;operation;reportable;sdkVersion;status;constructor({code:t,message:n,operation:r,reportable:i,status:a}){super(n),this.name=`LockerverseSdkError`,this.code=t,this.operation=r,this.reportable=i,this.sdkVersion=e,this.status=a}};export{t as n,e as t};
|
|
2
2
|
//# sourceMappingURL=types.js.map
|
package/dist/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","names":["packageMetadata.version"],"sources":["../package.json","../src/types.ts"],"sourcesContent":["","import packageMetadata from \"../package.json\" with { type: \"json\" };\n\nexport type LockerversePaymentOption = \"one-time\" | \"monthly\" | \"annually\";\nexport type LockerverseEnvironment = \"development\" | \"production\";\n\nexport const LOCKERVERSE_SDK_VERSION = packageMetadata.version;\n\nexport type LockerverseProduct = {\n id: string;\n listingId: string;\n slug: string;\n name: string;\n description: string | null;\n pricingMode: \"fixed\" | \"custom\";\n paymentOption: LockerversePaymentOption;\n amountCents: number | null;\n minimumAmountCents: number | null;\n minimumQuantity: number | null;\n maximumQuantity: number | null;\n inventoryQuantity: number | null;\n acceptsDiscounts: boolean;\n};\n\nexport type LockerverseCatalog = {\n payment: LockerversePaymentConfiguration;\n pricingPolicy: LockerverseCheckoutPricingPolicy;\n products: LockerverseProduct[];\n widget: LockerverseWidgetConfiguration;\n};\n\nexport type LockerverseCheckoutPricingPolicy = {\n currency: \"usd\";\n serviceFeeRateBasisPoints: number;\n};\n\nexport type LockerversePaymentConfiguration = {\n currency: \"usd\";\n publishableKey: string;\n};\n\nexport type LockerverseCheckoutPaymentConfiguration =\n LockerversePaymentConfiguration & {\n connectedAccountId: string | null;\n };\n\nexport type LockerverseWidgetFields = {\n memberId: boolean;\n merchSize: boolean;\n phone: boolean;\n promoCode: boolean;\n serviceFee: boolean;\n shipping: boolean;\n tipping: boolean;\n};\n\nexport type LockerverseCustomFieldOption = { id: string; label: string };\n\ntype LockerverseCustomFieldBase = {\n id: string;\n label: string;\n required: boolean;\n};\n\nexport type LockerverseTextCustomField = LockerverseCustomFieldBase & {\n type: \"text\" | \"textarea\";\n};\n\nexport type LockerverseSingleOptionCustomField = LockerverseCustomFieldBase & {\n options: LockerverseCustomFieldOption[];\n type: \"radio\" | \"select\";\n};\n\nexport type LockerverseMultiOptionCustomField = LockerverseCustomFieldBase & {\n options: LockerverseCustomFieldOption[];\n type: \"checkboxes\" | \"multi_select\";\n};\n\nexport type LockerverseCustomField =\n | LockerverseTextCustomField\n | LockerverseSingleOptionCustomField\n | LockerverseMultiOptionCustomField;\n\nexport type LockerverseCustomFieldAnswerValue<\n Field extends LockerverseCustomField,\n> = Field extends LockerverseMultiOptionCustomField ? string[] : string;\n\nexport type LockerverseCustomFieldAnswer<\n Field extends LockerverseCustomField = LockerverseCustomField,\n> = Field extends LockerverseCustomField\n ? { fieldId: Field[\"id\"]; value: LockerverseCustomFieldAnswerValue<Field> }\n : never;\n\nexport type LockerverseWidgetConfiguration = {\n customFields: LockerverseCustomField[];\n description: string | null;\n fields: LockerverseWidgetFields;\n id: string;\n name: string;\n showCommunityBranding: boolean;\n title: string | null;\n};\n\nexport type LockerverseSdkErrorCode =\n | \"widget_load_failed\"\n | \"signup_load_failed\"\n | \"signup_submit_failed\"\n | \"total_calculation_failed\"\n | \"payment_submit_failed\"\n | \"payment_status_failed\"\n | \"invalid_selection\";\n\nexport type LockerverseSdkOperation =\n | \"load_widget\"\n | \"load_signup\"\n | \"submit_signup\"\n | \"calculate_total\"\n | \"submit_payment\"\n | \"get_payment_status\"\n | \"update_selection\";\n\nexport class LockerverseSdkError extends Error {\n readonly code: LockerverseSdkErrorCode;\n readonly operation: LockerverseSdkOperation;\n readonly reportable: boolean;\n readonly sdkVersion: string;\n readonly status: number | undefined;\n\n constructor({\n code,\n message,\n operation,\n reportable,\n status,\n }: {\n code: LockerverseSdkErrorCode;\n message: string;\n operation: LockerverseSdkOperation;\n reportable: boolean;\n status?: number;\n }) {\n super(message);\n this.name = \"LockerverseSdkError\";\n this.code = code;\n this.operation = operation;\n this.reportable = reportable;\n this.sdkVersion = LOCKERVERSE_SDK_VERSION;\n this.status = status;\n }\n}\n\nexport type LockerverseCheckoutLineItem = {\n productId: string;\n productName: string;\n listingId: string;\n listingSlug: string;\n acceptsDiscounts: boolean;\n pricingMode: \"fixed\" | \"custom\";\n paymentOption: LockerversePaymentOption;\n quantity: number;\n unitAmountCents: number;\n subtotalCents: number;\n};\n\nexport type LockerverseAppliedDiscount = {\n percentageOff: number;\n source: \"email_list\" | \"promo_code\";\n};\n\nexport type LockerverseCheckoutAmounts = {\n amountCents: number;\n discountableSubtotalCents: number;\n discountCents: number;\n serviceFeeCents: number;\n subtotalCents: number;\n tipCents: number;\n totalCents: number;\n};\n\nexport type LockerverseCheckoutQuote = LockerverseCheckoutAmounts & {\n appliedDiscount: LockerverseAppliedDiscount | null;\n authoritative: true;\n paymentReference: string;\n payment: LockerverseCheckoutPaymentConfiguration;\n paymentOption: \"one-time\";\n lineItems: LockerverseCheckoutLineItem[];\n};\n\nexport type LockerverseCheckoutTotal = LockerverseCheckoutQuote;\n\nexport type LockerverseCheckoutPricingInput = {\n email?: string;\n includeServiceFee?: boolean;\n promoCode?: string;\n tipCents?: number;\n};\n\nexport type LockerverseCheckoutPreview = LockerverseCheckoutAmounts & {\n appliedDiscount: null;\n authoritative: false;\n};\n\nexport type LockerversePaymentStatus =\n | \"action_required\"\n | \"failed\"\n | \"pending\"\n | \"success\";\n\nexport type LockerversePaymentResult = {\n checkoutId: string;\n paymentReference: string;\n checkoutStatus: LockerversePaymentStatus;\n clientSecret: string | null;\n requiresAction: boolean;\n status: string | null;\n};\n\nexport type LockerversePaymentSubmission = {\n confirmationToken: string;\n customFieldAnswers?: LockerverseCustomFieldAnswer[];\n email: string;\n memberId?: string;\n merchSize?: \"XS\" | \"S\" | \"M\" | \"L\" | \"XL\" | \"XXL\" | \"XXXL\";\n metadata?: Record<string, string>;\n phone?: string;\n};\n\nexport type LockerverseWidgetState =\n | { phase: \"idle\"; selection: LockerverseSelection }\n | { phase: \"loading\"; selection: LockerverseSelection }\n | {\n phase: \"ready\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview | null;\n }\n | {\n phase: \"quoting\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n }\n | {\n phase: \"quoted\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n quote: LockerverseCheckoutTotal;\n }\n | {\n phase: \"submitting\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n quote: LockerverseCheckoutTotal;\n }\n | {\n phase: \"recovering\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n paymentReference: string;\n }\n | {\n phase: \"payment\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n quote: LockerverseCheckoutTotal | null;\n payment: LockerversePaymentResult;\n }\n | {\n phase: \"error\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n error: LockerverseSdkError;\n recoverablePaymentReference: string | null;\n };\n\nexport type LockerverseSelectionItem =\n | { productId: string; productSlug: string; quantity: number }\n | { productId: string; productSlug: string; amountCents: number };\n\nexport type LockerverseSelection = {\n items: LockerverseSelectionItem[];\n};\n\ntype CreateLockerverseWidgetBaseOptions = {\n communitySlug: string;\n fetch?: typeof globalThis.fetch;\n onError?: (error: LockerverseSdkError) => void;\n sentryDsn?: string | null;\n widgetSlug: string;\n};\n\nexport type CreateLockerverseWidgetOptions =\n CreateLockerverseWidgetBaseOptions &\n (\n | {\n apiBaseUrl: string;\n environment: LockerverseEnvironment;\n }\n | {\n apiBaseUrl?: undefined;\n environment?: \"production\";\n }\n );\n\nexport type LockerverseWidget = {\n calculateTotal: (\n input?: LockerverseCheckoutPricingInput\n ) => Promise<LockerverseCheckoutQuote>;\n clear: () => void;\n getSelection: () => LockerverseSelection;\n getState: () => LockerverseWidgetState;\n getPaymentStatus: (\n paymentReference?: string\n ) => Promise<LockerversePaymentResult>;\n load: () => Promise<LockerverseCatalog>;\n previewTotal: (\n input?: LockerverseCheckoutPricingInput\n ) => LockerverseCheckoutPreview;\n remove: (productSlug: string) => void;\n setAmount: (productSlug: string, amountCents: number) => void;\n setQuantity: (productSlug: string, quantity: number) => void;\n submitPayment: (\n submission: LockerversePaymentSubmission\n ) => Promise<LockerversePaymentResult>;\n subscribe: (listener: (state: LockerverseWidgetState) => void) => () => void;\n};\n"],"mappings":"ACKA,MAAa,EAA0BA,gBAmHvC,IAAa,EAAb,cAAyC,KAAM,CAC7C,KACA,UACA,WACA,WACA,OAEA,YAAY,CACV,OACA,UACA,YACA,aACA,UAOC,CACD,MAAM,CAAO,EACb,KAAK,KAAO,sBACZ,KAAK,KAAO,EACZ,KAAK,UAAY,EACjB,KAAK,WAAa,EAClB,KAAK,WAAa,EAClB,KAAK,OAAS,CAChB,CACF"}
|
|
1
|
+
{"version":3,"file":"types.js","names":["packageMetadata.version"],"sources":["../package.json","../src/types.ts"],"sourcesContent":["","import packageMetadata from \"../package.json\" with { type: \"json\" };\n\nexport type LockerversePaymentOption = \"one-time\" | \"monthly\" | \"annually\";\nexport type LockerverseEnvironment = \"development\" | \"production\";\n\nexport const LOCKERVERSE_SDK_VERSION = packageMetadata.version;\n\nexport type LockerverseProduct = {\n id: string;\n listingId: string;\n slug: string;\n name: string;\n description: string | null;\n pricingMode: \"fixed\" | \"custom\";\n paymentOption: LockerversePaymentOption;\n amountCents: number | null;\n minimumAmountCents: number | null;\n minimumQuantity: number | null;\n maximumQuantity: number | null;\n inventoryQuantity: number | null;\n acceptsDiscounts: boolean;\n};\n\nexport type LockerverseCatalog = {\n payment: LockerversePaymentConfiguration;\n pricingPolicy: LockerverseCheckoutPricingPolicy;\n products: LockerverseProduct[];\n widget: LockerverseWidgetConfiguration;\n};\n\nexport type LockerverseCheckoutPricingPolicy = {\n currency: \"usd\";\n serviceFeeRateBasisPoints: number;\n};\n\nexport type LockerversePaymentConfiguration = {\n currency: \"usd\";\n publishableKey: string;\n};\n\nexport type LockerverseCheckoutPaymentConfiguration =\n LockerversePaymentConfiguration & {\n connectedAccountId: string | null;\n };\n\nexport type LockerverseWidgetFields = {\n memberId: boolean;\n merchSize: boolean;\n phone: boolean;\n promoCode: boolean;\n serviceFee: boolean;\n shipping: boolean;\n tipping: boolean;\n};\n\nexport type LockerverseCustomFieldOption = { id: string; label: string };\n\ntype LockerverseCustomFieldBase = {\n id: string;\n label: string;\n required: boolean;\n};\n\nexport type LockerverseTextCustomField = LockerverseCustomFieldBase & {\n type: \"text\" | \"textarea\";\n};\n\nexport type LockerverseSingleOptionCustomField = LockerverseCustomFieldBase & {\n options: LockerverseCustomFieldOption[];\n type: \"radio\" | \"select\";\n};\n\nexport type LockerverseMultiOptionCustomField = LockerverseCustomFieldBase & {\n options: LockerverseCustomFieldOption[];\n type: \"checkboxes\" | \"multi_select\";\n};\n\nexport type LockerverseCustomField =\n | LockerverseTextCustomField\n | LockerverseSingleOptionCustomField\n | LockerverseMultiOptionCustomField;\n\nexport type LockerverseCustomFieldAnswerValue<\n Field extends LockerverseCustomField,\n> = Field extends LockerverseMultiOptionCustomField ? string[] : string;\n\nexport type LockerverseCustomFieldAnswer<\n Field extends LockerverseCustomField = LockerverseCustomField,\n> = Field extends LockerverseCustomField\n ? { fieldId: Field[\"id\"]; value: LockerverseCustomFieldAnswerValue<Field> }\n : never;\n\nexport type LockerverseWidgetConfiguration = {\n customFields: LockerverseCustomField[];\n description: string | null;\n fields: LockerverseWidgetFields;\n id: string;\n name: string;\n showCommunityBranding: boolean;\n title: string | null;\n};\n\nexport type LockerverseSdkErrorCode =\n | \"widget_load_failed\"\n | \"signup_load_failed\"\n | \"signup_submit_failed\"\n | \"total_calculation_failed\"\n | \"payment_submit_failed\"\n | \"payment_status_failed\"\n | \"invalid_selection\";\n\nexport type LockerverseSdkOperation =\n | \"load_widget\"\n | \"load_signup\"\n | \"submit_signup\"\n | \"calculate_total\"\n | \"submit_payment\"\n | \"get_payment_status\"\n | \"update_selection\";\n\nexport class LockerverseSdkError extends Error {\n readonly code: LockerverseSdkErrorCode;\n readonly operation: LockerverseSdkOperation;\n readonly reportable: boolean;\n readonly sdkVersion: string;\n readonly status: number | undefined;\n\n constructor({\n code,\n message,\n operation,\n reportable,\n status,\n }: {\n code: LockerverseSdkErrorCode;\n message: string;\n operation: LockerverseSdkOperation;\n reportable: boolean;\n status?: number;\n }) {\n super(message);\n this.name = \"LockerverseSdkError\";\n this.code = code;\n this.operation = operation;\n this.reportable = reportable;\n this.sdkVersion = LOCKERVERSE_SDK_VERSION;\n this.status = status;\n }\n}\n\nexport type LockerverseCheckoutLineItem = {\n productId: string;\n productName: string;\n listingId: string;\n listingSlug: string;\n acceptsDiscounts: boolean;\n pricingMode: \"fixed\" | \"custom\";\n paymentOption: LockerversePaymentOption;\n quantity: number;\n unitAmountCents: number;\n subtotalCents: number;\n};\n\nexport type LockerverseAppliedDiscount = {\n percentageOff: number;\n source: \"email_list\" | \"promo_code\";\n};\n\nexport type LockerverseCheckoutAmounts = {\n amountCents: number;\n discountableSubtotalCents: number;\n discountCents: number;\n serviceFeeCents: number;\n subtotalCents: number;\n tipCents: number;\n totalCents: number;\n};\n\nexport type LockerverseCheckoutQuote = LockerverseCheckoutAmounts & {\n appliedDiscount: LockerverseAppliedDiscount | null;\n authoritative: true;\n paymentReference: string;\n payment: LockerverseCheckoutPaymentConfiguration;\n paymentOption: \"one-time\";\n lineItems: LockerverseCheckoutLineItem[];\n};\n\nexport type LockerverseCheckoutTotal = LockerverseCheckoutQuote;\n\nexport type LockerverseCheckoutPricingInput = {\n email?: string;\n includeServiceFee?: boolean;\n promoCode?: string;\n tipCents?: number;\n};\n\nexport type LockerverseCheckoutPreview = LockerverseCheckoutAmounts & {\n appliedDiscount: null;\n authoritative: false;\n};\n\nexport type LockerversePaymentStatus =\n | \"action_required\"\n | \"failed\"\n | \"pending\"\n | \"success\";\n\nexport type LockerversePaymentResult = {\n checkoutId: string;\n paymentReference: string;\n checkoutStatus: LockerversePaymentStatus;\n clientSecret: string | null;\n requiresAction: boolean;\n status: string | null;\n};\n\nexport type LockerversePaymentSubmission = {\n confirmationToken: string;\n customFieldAnswers?: LockerverseCustomFieldAnswer[];\n email: string;\n memberId?: string;\n merchSize?: \"XS\" | \"S\" | \"M\" | \"L\" | \"XL\" | \"XXL\" | \"XXXL\";\n metadata?: Record<string, string>;\n phone?: string;\n};\n\nexport type LockerverseWidgetState =\n | { phase: \"idle\"; selection: LockerverseSelection }\n | { phase: \"loading\"; selection: LockerverseSelection }\n | {\n phase: \"ready\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview | null;\n }\n | {\n phase: \"quoting\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n }\n | {\n phase: \"quoted\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n quote: LockerverseCheckoutTotal;\n }\n | {\n phase: \"submitting\";\n catalog: LockerverseCatalog;\n selection: LockerverseSelection;\n preview: LockerverseCheckoutPreview;\n quote: LockerverseCheckoutTotal;\n }\n | {\n phase: \"recovering\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n paymentReference: string;\n }\n | {\n phase: \"payment\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n quote: LockerverseCheckoutTotal | null;\n payment: LockerversePaymentResult;\n }\n | {\n phase: \"error\";\n catalog: LockerverseCatalog | null;\n selection: LockerverseSelection;\n error: LockerverseSdkError;\n recoverablePaymentReference: string | null;\n };\n\nexport type LockerverseSelectionItem =\n | { productId: string; productSlug: string; quantity: number }\n | { productId: string; productSlug: string; amountCents: number };\n\nexport type LockerverseSelection = {\n items: LockerverseSelectionItem[];\n};\n\ntype CreateLockerverseWidgetBaseOptions = {\n communitySlug: string;\n fetch?: typeof globalThis.fetch;\n onError?: (error: LockerverseSdkError) => void;\n requestTimeoutMs?: number;\n sentryDsn?: string | null;\n widgetSlug: string;\n};\n\nexport type CreateLockerverseWidgetOptions =\n CreateLockerverseWidgetBaseOptions &\n (\n | {\n apiBaseUrl: string;\n environment: LockerverseEnvironment;\n }\n | {\n apiBaseUrl?: undefined;\n environment?: \"production\";\n }\n );\n\nexport type LockerverseWidget = {\n calculateTotal: (\n input?: LockerverseCheckoutPricingInput\n ) => Promise<LockerverseCheckoutQuote>;\n clear: () => void;\n getSelection: () => LockerverseSelection;\n getState: () => LockerverseWidgetState;\n getPaymentStatus: (\n paymentReference?: string\n ) => Promise<LockerversePaymentResult>;\n load: () => Promise<LockerverseCatalog>;\n previewTotal: (\n input?: LockerverseCheckoutPricingInput\n ) => LockerverseCheckoutPreview;\n remove: (productSlug: string) => void;\n setAmount: (productSlug: string, amountCents: number) => void;\n setQuantity: (productSlug: string, quantity: number) => void;\n submitPayment: (\n submission: LockerversePaymentSubmission\n ) => Promise<LockerversePaymentResult>;\n subscribe: (listener: (state: LockerverseWidgetState) => void) => () => void;\n};\n"],"mappings":"ACKA,MAAa,EAA0BA,gBAmHvC,IAAa,EAAb,cAAyC,KAAM,CAC7C,KACA,UACA,WACA,WACA,OAEA,YAAY,CACV,OACA,UACA,YACA,aACA,UAOC,CACD,MAAM,CAAO,EACb,KAAK,KAAO,sBACZ,KAAK,KAAO,EACZ,KAAK,UAAY,EACjB,KAAK,WAAa,EAClB,KAAK,WAAa,EAClB,KAAK,OAAS,CAChB,CACF"}
|