@donotdev/billing 0.0.4 → 0.0.6

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.
@@ -1 +1 @@
1
- {"version":3,"file":"useStripeBilling.d.ts","sourceRoot":"","sources":["../src/useStripeBilling.ts"],"names":[],"mappings":"AAuCA,OAAO,KAAK,EACV,QAAQ,EACR,UAAU,EAIV,aAAa,EACd,MAAM,gBAAgB,CAAC;AAqBxB;;;;;;;GAOG;AACH,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,QAAQ,GAAG,IAAI,CAAC;IACtB,MAAM,EAAE,aAAa,CAAC;CACvB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkEG;AACH,wBAAgB,gBAAgB,CAAC,CAAC,SAAS,MAAM,UAAU,EACzD,GAAG,EAAE,CAAC,EACN,SAAS,CAAC,EAAE,gBAAgB,GAC3B,UAAU,CAAC,CAAC,CAAC,CA+Vf"}
1
+ {"version":3,"file":"useStripeBilling.d.ts","sourceRoot":"","sources":["../src/useStripeBilling.ts"],"names":[],"mappings":"AA8CA,OAAO,KAAK,EACV,QAAQ,EACR,UAAU,EAIV,aAAa,EAGd,MAAM,gBAAgB,CAAC;AAsBxB;;;;;;;GAOG;AACH,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,QAAQ,GAAG,IAAI,CAAC;IACtB,MAAM,EAAE,aAAa,CAAC;CACvB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkEG;AACH,wBAAgB,gBAAgB,CAAC,CAAC,SAAS,MAAM,UAAU,EACzD,GAAG,EAAE,CAAC,EACN,SAAS,CAAC,EAAE,gBAAgB,GAC3B,UAAU,CAAC,CAAC,CAAC,CAyWf"}
@@ -1 +1 @@
1
- "use client";import{useState as U,useCallback as c}from"react";import{DEGRADED_BILLING_API as y,FEATURE_STATUS as u,isClient as C,handleError as l,getPlatformEnvVar as p,FRAMEWORK_FEATURES as k,redirectToExternalUrlWithErrorHandling as x,useFeatureConsent as M}from"@donotdev/core";import{getFirebaseFunctions as f,httpsCallable as h}from"@donotdev/firebase";let g=!1;function Z(a,E){const t=E?.user??null,w=(E?.status??u.DEGRADED)===u.READY,m=M(k.BILLING),[q,n]=U(!1),[F,s]=U(null),R=c(async r=>{if(!C()||!m)throw new Error("Billing not available in SSR or consent required");if(!t){const e=l(new Error("User must be authenticated"),{userMessage:"Please sign in to continue with checkout.",severity:"warning"});throw s(e.message),e}n(!0),s(null);try{const e=p("FIREBASE_FUNCTIONS_REGION")||"europe-west1",o=await f(e),i=h(o,"createCheckoutSession"),d=t.providerData?.find(L=>L.providerId==="github.com"),I=d?.displayName,N=d?.uid,T={priceId:r.priceId,userId:t.id,userEmail:t.email||"",customerEmail:t.email||"",metadata:{firebaseUid:t.id,...I&&{githubUsername:I},...N&&{githubUid:N},...r.metadata},successUrl:r.successUrl||`${typeof window<"u"?window.location.origin:""}/billing/success`,cancelUrl:r.cancelUrl||(typeof window<"u"?window.location.href:""),allowPromotionCodes:r.allowPromotionCodes??!0,mode:r.mode},G=await i(T),{sessionId:D,sessionUrl:b}=G.data;if(!b)throw new Error("No checkout URL received from server");return g=!1,{sessionId:D,sessionUrl:b,success:!0,error:void 0}}catch(e){if(g){const o=e instanceof Error?e:new Error("Checkout failed");throw s(o.message),o}else{const o=l(e,{userMessage:"Unable to start checkout. Please try again or contact support if the problem persists.",context:{priceId:r.priceId,mode:r.mode},severity:"error"});throw s(o.message),g=!0,o}}finally{n(!1)}},[t,m]),A=c(async()=>{if(!t)throw new Error("User must be authenticated");n(!0),s(null);try{const r=p("FIREBASE_FUNCTIONS_REGION")||"europe-west1",e=await f(r);return(await h(e,"cancelSubscription")({userId:t.id})).data}catch(r){const e=l(r,{userMessage:"Failed to cancel subscription. Please try again or contact support.",context:{operation:"cancelSubscription",userId:t.id},severity:"error"});throw s(e.message),e}finally{n(!1)}},[t]),P=c(async(r,e)=>{if(!t)throw new Error("User must be authenticated");n(!0),s(null);try{const o=p("FIREBASE_FUNCTIONS_REGION")||"europe-west1",i=await f(o);return(await h(i,"changePlan")({userId:t.id,newPriceId:r,billingConfigKey:e})).data}catch(o){const i=l(o,{userMessage:"Failed to change plan. Please try again or contact support.",context:{operation:"changePlan",userId:t.id,newPriceId:r,billingConfigKey:e},severity:"error"});throw s(i.message),i}finally{n(!1)}},[t]),v=c(async()=>{if(!t)throw new Error("User must be authenticated");n(!0),s(null);try{const r=p("FIREBASE_FUNCTIONS_REGION")||"europe-west1",e=await f(r);await h(e,"refreshSubscriptionStatus")({userId:t.id})}catch(r){const e=l(r,{userMessage:"Failed to refresh subscription status. Please try again.",context:{operation:"refreshStatus",userId:t.id},severity:"error"});throw s(e.message),e}finally{n(!1)}},[t]),_=c(async r=>{if(!t)throw new Error("User must be authenticated");n(!0),s(null);try{const e=p("FIREBASE_FUNCTIONS_REGION")||"europe-west1",o=await f(e),d=await h(o,"createCustomerPortal")({userId:t.id,returnUrl:r||(typeof window<"u"?window.location.href:"")});await x(d.data.url,{},"Failed to redirect to customer portal")}catch(e){const o=l(e,{userMessage:"Failed to open customer portal. Please try again or contact support.",context:{operation:"openCustomerPortal",userId:t.id},severity:"error"});throw s(o.message),o}finally{n(!1)}},[t]),B=c(()=>{s(null),g=!1},[]),S={checkout:R,cancelSubscription:A,changePlan:P,refreshStatus:v,openCustomerPortal:_,clearError:B};if(!C()||!m)return y[a];const O=w?u.READY:u.INITIALIZING;return a==="status"?O:a==="isAvailable"?!!w:a==="status"?w?u.READY:u.INITIALIZING:a==="error"?F:a in S?S[a]:y[a]}export{Z as useStripeBilling};
1
+ "use client";import{useState as N,useCallback as c}from"react";import{DEGRADED_BILLING_API as C,FEATURE_STATUS as g,isClient as F,handleError as u,getPlatformEnvVar as d,FRAMEWORK_FEATURES as q,redirectToExternalUrlWithErrorHandling as $,useFeatureConsent as W,useOverlay as v}from"@donotdev/core";import{getFirebaseFunctions as p,httpsCallable as f}from"@donotdev/firebase";let m=!1;function z(a,S){const r=S?.user??null,y=(S?.status??g.DEGRADED)===g.READY,E=W(q.BILLING),[A,n]=N(!1),[O,s]=N(null),h=v("showRedirectOverlay"),w=v("hideRedirectOverlay"),P=c(async t=>{if(!F()||!E)throw new Error("Billing not available in SSR or consent required");if(!r){const e=u(new Error("User must be authenticated"),{userMessage:"Please sign in to continue with checkout.",severity:"warning"});throw s(e.message),e}n(!0),s(null),h("stripe-checkout");try{const e=d("FIREBASE_FUNCTIONS_REGION")||"europe-west1",o=await p(e),i=f(o,"createCheckoutSession"),l=r.providerData?.find(j=>j.providerId==="github.com"),I=l?.displayName,R=l?.uid,x={priceId:t.priceId,userId:r.id,userEmail:r.email||"",customerEmail:r.email||"",metadata:{firebaseUid:r.id,...I&&{githubUsername:I},...R&&{githubUid:R},...t.metadata},successUrl:t.successUrl||`${typeof window<"u"?window.location.origin:""}/billing/success`,cancelUrl:t.cancelUrl||(typeof window<"u"?window.location.href:""),allowPromotionCodes:t.allowPromotionCodes??!0,mode:t.mode},L=await i(x),{sessionId:M,sessionUrl:U}=L.data;if(!U)throw new Error("No checkout URL received from server");return m=!1,{sessionId:M,sessionUrl:U,success:!0,error:void 0}}catch(e){if(w(),m){const o=e instanceof Error?e:new Error("Checkout failed");throw s(o.message),o}else{const o=u(e,{userMessage:"Unable to start checkout. Please try again or contact support if the problem persists.",context:{priceId:t.priceId,mode:t.mode},severity:"error"});throw s(o.message),m=!0,o}}finally{n(!1)}},[r,E,h,w]),_=c(async()=>{if(!r)throw new Error("User must be authenticated");n(!0),s(null);try{const t=d("FIREBASE_FUNCTIONS_REGION")||"europe-west1",e=await p(t);return(await f(e,"cancelSubscription")({userId:r.id})).data}catch(t){const e=u(t,{userMessage:"Failed to cancel subscription. Please try again or contact support.",context:{operation:"cancelSubscription",userId:r.id},severity:"error"});throw s(e.message),e}finally{n(!1)}},[r]),B=c(async(t,e)=>{if(!r)throw new Error("User must be authenticated");n(!0),s(null);try{const o=d("FIREBASE_FUNCTIONS_REGION")||"europe-west1",i=await p(o);return(await f(i,"changePlan")({userId:r.id,newPriceId:t,billingConfigKey:e})).data}catch(o){const i=u(o,{userMessage:"Failed to change plan. Please try again or contact support.",context:{operation:"changePlan",userId:r.id,newPriceId:t,billingConfigKey:e},severity:"error"});throw s(i.message),i}finally{n(!1)}},[r]),T=c(async()=>{if(!r)throw new Error("User must be authenticated");n(!0),s(null);try{const t=d("FIREBASE_FUNCTIONS_REGION")||"europe-west1",e=await p(t);await f(e,"refreshSubscriptionStatus")({userId:r.id})}catch(t){const e=u(t,{userMessage:"Failed to refresh subscription status. Please try again.",context:{operation:"refreshStatus",userId:r.id},severity:"error"});throw s(e.message),e}finally{n(!1)}},[r]),G=c(async t=>{if(!r)throw new Error("User must be authenticated");n(!0),s(null),h("stripe-portal");try{const e=d("FIREBASE_FUNCTIONS_REGION")||"europe-west1",o=await p(e),l=await f(o,"createCustomerPortal")({userId:r.id,returnUrl:t||(typeof window<"u"?window.location.href:"")});await $(l.data.url,{},"Failed to redirect to customer portal")}catch(e){w();const o=u(e,{userMessage:"Failed to open customer portal. Please try again or contact support.",context:{operation:"openCustomerPortal",userId:r.id},severity:"error"});throw s(o.message),o}finally{n(!1)}},[r,h,w]),D=c(()=>{s(null),m=!1},[]),b={checkout:P,cancelSubscription:_,changePlan:B,refreshStatus:T,openCustomerPortal:G,clearError:D};if(!F()||!E)return C[a];const k=y?g.READY:g.INITIALIZING;return a==="status"?k:a==="isAvailable"?!!y:a==="error"?O:a==="loading"?A:a in b?b[a]:C[a]}export{z as useStripeBilling};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@donotdev/billing",
3
- "version": "0.0.4",
3
+ "version": "0.0.6",
4
4
  "private": false,
5
5
  "type": "module",
6
6
  "license": "SEE LICENSE IN LICENSE.md",
@@ -33,14 +33,14 @@
33
33
  },
34
34
  "dependencies": {},
35
35
  "peerDependencies": {
36
- "@donotdev/auth": "0.0.4",
37
- "@donotdev/components": "0.0.4",
38
- "@donotdev/core": "0.0.4",
39
- "@donotdev/firebase": "0.0.4",
40
- "lucide-react": "^0.562.0",
41
- "react": "^19.2.3",
42
- "react-dom": "^19.2.3",
43
- "stripe": "^20.1.0"
36
+ "@donotdev/auth": "^0.0.6",
37
+ "@donotdev/components": "^0.0.15",
38
+ "@donotdev/core": "^0.0.20",
39
+ "@donotdev/firebase": "^0.0.9",
40
+ "lucide-react": "^0.563.0",
41
+ "react": "^19.2.4",
42
+ "react-dom": "^19.2.4",
43
+ "stripe": "^20.3.0"
44
44
  },
45
45
  "peerDependenciesMeta": {},
46
46
  "keywords": [
@@ -1,23 +0,0 @@
1
- export interface PaymentRedirectOverlayProps {
2
- /**
3
- * Whether to show the overlay
4
- */
5
- show: boolean;
6
- }
7
- /**
8
- * PaymentRedirectOverlay component
9
- *
10
- * Fullscreen overlay that appears during payment checkout redirect preparation.
11
- * Shows a security-focused message with lock icon and spinner.
12
- *
13
- * @version 0.0.1
14
- * @since 0.0.1
15
- * @author AMBROISE PARK Consulting
16
- *
17
- * @example
18
- * ```tsx
19
- * <PaymentRedirectOverlay show={loading} />
20
- * ```
21
- */
22
- export declare function PaymentRedirectOverlay({ show }: PaymentRedirectOverlayProps): import("react/jsx-runtime").JSX.Element | null;
23
- //# sourceMappingURL=PaymentRedirectOverlay.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"PaymentRedirectOverlay.d.ts","sourceRoot":"","sources":["../../src/components/PaymentRedirectOverlay.tsx"],"names":[],"mappings":"AAgBA,MAAM,WAAW,2BAA2B;IAC1C;;OAEG;IACH,IAAI,EAAE,OAAO,CAAC;CACf;AAED;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,sBAAsB,CAAC,EAAE,IAAI,EAAE,EAAE,2BAA2B,kDA8C3E"}
@@ -1 +0,0 @@
1
- import{jsx as e,jsxs as t}from"react/jsx-runtime";import{Lock as a}from"lucide-react";import{Spinner as n,Stack as l,Text as o}from"@donotdev/components";import{useTranslation as s}from"@donotdev/core";function u({show:i}){const{t:r}=s("billing");return i?e("div",{className:"dndev-spinner-overlay",role:"status","aria-busy":"true","aria-label":r("components.redirectOverlay.ariaLabel"),children:t("div",{style:{display:"flex",flexDirection:"column",alignItems:"center",justifyContent:"center",gap:"var(--gap-md)"},children:[t(l,{direction:"row",gap:"medium",align:"center",children:[e(a,{style:{width:"1.5rem",height:"1.5rem",color:"var(--primary)"},"aria-hidden":"true"}),e(n,{variant:"primary"})]}),e(o,{variant:"muted",style:{textAlign:"center",color:"var(--foreground)"},children:r("components.redirectOverlay.message")})]})}):null}export{u as PaymentRedirectOverlay};