@verapay/verapay-js 0.0.2 → 0.0.4
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 +49 -31
- package/dist/index.cjs +2 -2
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -15,7 +15,7 @@ A simple, PCI-compliant TypeScript SDK for Stripe payment processing.
|
|
|
15
15
|
## Installation
|
|
16
16
|
|
|
17
17
|
```bash
|
|
18
|
-
npm install verapay-js
|
|
18
|
+
npm install @verapay/verapay-js
|
|
19
19
|
```
|
|
20
20
|
|
|
21
21
|
## Quick Start
|
|
@@ -23,7 +23,7 @@ npm install verapay-js
|
|
|
23
23
|
Initialize the SDK with your `merchantId` and the payment details — no backend setup required:
|
|
24
24
|
|
|
25
25
|
```typescript
|
|
26
|
-
import { VerapayClient } from 'verapay-js';
|
|
26
|
+
import { VerapayClient } from '@verapay/verapay-js';
|
|
27
27
|
|
|
28
28
|
const verapay = new VerapayClient({
|
|
29
29
|
merchantId: 'your-merchant-id',
|
|
@@ -44,12 +44,21 @@ const result = await verapay.processPayment({
|
|
|
44
44
|
## Processing Payments
|
|
45
45
|
|
|
46
46
|
```typescript
|
|
47
|
-
import { VerapayClient, ValidationError, PaymentError } from 'verapay-js';
|
|
47
|
+
import { VerapayClient, ValidationError, PaymentError } from '@verapay/verapay-js';
|
|
48
48
|
|
|
49
49
|
const verapay = new VerapayClient({
|
|
50
50
|
merchantId: 'your-merchant-id',
|
|
51
51
|
paymentData: { amount: 5000, currency: 'gbp' },
|
|
52
52
|
});
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
If your Merchant account is associated with a Partner, include `partnerFee` — the fee you are taking from the payment, which you are responsible for calculating. It must not exceed the payment `amount`:
|
|
56
|
+
|
|
57
|
+
```typescript
|
|
58
|
+
const verapay = new VerapayClient({
|
|
59
|
+
merchantId: 'your-merchant-id',
|
|
60
|
+
paymentData: { amount: 5000, currency: 'gbp', partnerFee: 250 },
|
|
61
|
+
});
|
|
53
62
|
|
|
54
63
|
await verapay.mountPaymentForm('#payment-form');
|
|
55
64
|
|
|
@@ -100,6 +109,26 @@ await verapay.mountAddress('#billing-address', 'billing');
|
|
|
100
109
|
await verapay.mountAddress('#shipping-address', 'shipping');
|
|
101
110
|
```
|
|
102
111
|
|
|
112
|
+
### Styling the Payment Form and Address Element
|
|
113
|
+
|
|
114
|
+
When using `mountPaymentForm` or `mountAddress`, pass an `appearance` object to customise their look. See [Stripe's Appearance API](https://stripe.com/docs/elements/appearance-api) for the full set of options.
|
|
115
|
+
|
|
116
|
+
> **Note:** Styling is split across two APIs due to a Stripe limitation. `mountPaymentForm` and `mountAddress` use newer Stripe elements that support the `appearance` API. `mountCardNumber`, `mountCardExpiry`, and `mountCardCvc` use older Stripe element types that predate `appearance` and only support per-element `style` configuration via `elementsConfig`.
|
|
117
|
+
|
|
118
|
+
```typescript
|
|
119
|
+
const verapay = new VerapayClient({
|
|
120
|
+
merchantId: 'your-merchant-id',
|
|
121
|
+
paymentData: { amount: 5000, currency: 'gbp' },
|
|
122
|
+
appearance: {
|
|
123
|
+
theme: 'stripe',
|
|
124
|
+
variables: {
|
|
125
|
+
colorPrimary: '#6200ee',
|
|
126
|
+
fontFamily: 'Inter, sans-serif',
|
|
127
|
+
},
|
|
128
|
+
},
|
|
129
|
+
});
|
|
130
|
+
```
|
|
131
|
+
|
|
103
132
|
### Styling Individual Form Elements
|
|
104
133
|
|
|
105
134
|
> This section applies only when mounting individual form elements (`mountCardNumber`, `mountCardExpiry`, `mountCardCvc`). It does not apply to `mountPaymentForm`.
|
|
@@ -150,16 +179,7 @@ const verapay = new VerapayClient({
|
|
|
150
179
|
|
|
151
180
|
#### Container styling
|
|
152
181
|
|
|
153
|
-
The
|
|
154
|
-
|
|
155
|
-
```css
|
|
156
|
-
.card-field {
|
|
157
|
-
border: 1px solid #e0e0e0;
|
|
158
|
-
border-radius: 4px;
|
|
159
|
-
padding: 12px;
|
|
160
|
-
background: white;
|
|
161
|
-
}
|
|
162
|
-
```
|
|
182
|
+
The SDK mounts Stripe Elements into whichever `div` selectors you provide. Style those containers however you like using your own CSS — there are no SDK-specific class names.
|
|
163
183
|
|
|
164
184
|
#### Locale
|
|
165
185
|
|
|
@@ -202,7 +222,7 @@ import {
|
|
|
202
222
|
ValidationError,
|
|
203
223
|
PaymentError,
|
|
204
224
|
ErrorFormatter,
|
|
205
|
-
} from 'verapay-js';
|
|
225
|
+
} from '@verapay/verapay-js';
|
|
206
226
|
|
|
207
227
|
try {
|
|
208
228
|
await verapay.processPayment(request);
|
|
@@ -230,7 +250,7 @@ import type {
|
|
|
230
250
|
ElementsConfig,
|
|
231
251
|
CardValidation,
|
|
232
252
|
ErrorCode,
|
|
233
|
-
} from 'verapay-js';
|
|
253
|
+
} from '@verapay/verapay-js';
|
|
234
254
|
```
|
|
235
255
|
|
|
236
256
|
## Extension Architecture
|
|
@@ -238,7 +258,7 @@ import type {
|
|
|
238
258
|
Use extensions to hook into the payment lifecycle:
|
|
239
259
|
|
|
240
260
|
```typescript
|
|
241
|
-
import type { PaymentExtension } from 'verapay-js';
|
|
261
|
+
import type { PaymentExtension } from '@verapay/verapay-js';
|
|
242
262
|
|
|
243
263
|
const analyticsExtension: PaymentExtension = {
|
|
244
264
|
name: 'analytics',
|
|
@@ -302,12 +322,12 @@ new VerapayClient(config: VerapayConfig)
|
|
|
302
322
|
|
|
303
323
|
| Property | Type | Required | Description |
|
|
304
324
|
|---|---|---|---|
|
|
305
|
-
| `merchantId` | `string` | Yes | Your
|
|
306
|
-
| `paymentData` | `PaymentData` | Yes | Amount, currency, and optional
|
|
307
|
-
| `appearance` | `Appearance` | No |
|
|
325
|
+
| `merchantId` | `string` | Yes | Your Merchant ID from onboarding |
|
|
326
|
+
| `paymentData` | `PaymentData` | Yes | Amount, currency, and optional Partner fee |
|
|
327
|
+
| `appearance` | `Appearance` | No | Styles `mountPaymentForm` and `mountAddress` elements |
|
|
308
328
|
| `locale` | `StripeElementLocale` | No | Locale for Stripe Elements |
|
|
309
329
|
| `fonts` | `StripeElementsOptions['fonts']` | No | Custom fonts for Stripe Elements |
|
|
310
|
-
| `elementsConfig` | `ElementsConfig` | No |
|
|
330
|
+
| `elementsConfig` | `ElementsConfig` | No | Styles `mountCardNumber`, `mountCardExpiry`, and `mountCardCvc` elements |
|
|
311
331
|
|
|
312
332
|
#### PaymentData
|
|
313
333
|
|
|
@@ -315,7 +335,7 @@ new VerapayClient(config: VerapayConfig)
|
|
|
315
335
|
|---|---|---|---|
|
|
316
336
|
| `amount` | `number` | Yes | Amount in the smallest currency unit (e.g., pence for GBP) |
|
|
317
337
|
| `currency` | `string` | Yes | ISO 4217 currency code (e.g., `'gbp'`) |
|
|
318
|
-
| `partnerFee` | `number` | No |
|
|
338
|
+
| `partnerFee` | `number` | No | Your fee in the smallest currency unit, taken from the payment amount. Only applicable if your Merchant account is associated with a Partner — ignored otherwise. You are responsible for calculating this value. Must not exceed `amount`. |
|
|
319
339
|
|
|
320
340
|
#### Methods
|
|
321
341
|
|
|
@@ -331,13 +351,13 @@ new VerapayClient(config: VerapayConfig)
|
|
|
331
351
|
|
|
332
352
|
#### ProcessPaymentRequest
|
|
333
353
|
|
|
334
|
-
| Property | Type | Description |
|
|
335
|
-
|
|
336
|
-
| `
|
|
337
|
-
| `
|
|
338
|
-
| `
|
|
339
|
-
| `customerFirstName` | `string` | Customer first name |
|
|
340
|
-
| `customerLastName` | `string` | Customer last name |
|
|
354
|
+
| Property | Type | Required | Description |
|
|
355
|
+
|---|---|---|---|
|
|
356
|
+
| `customerEmail` | `string` | Yes | Customer email address |
|
|
357
|
+
| `description` | `string` | No | Payment description |
|
|
358
|
+
| `metadata` | `Record<string, string>` | No | Arbitrary key-value metadata |
|
|
359
|
+
| `customerFirstName` | `string` | No | Customer first name |
|
|
360
|
+
| `customerLastName` | `string` | No | Customer last name |
|
|
341
361
|
|
|
342
362
|
#### PaymentResult
|
|
343
363
|
|
|
@@ -356,7 +376,5 @@ This software is proprietary and confidential. Unauthorised copying, distributio
|
|
|
356
376
|
|
|
357
377
|
## Support
|
|
358
378
|
|
|
359
|
-
For issues and questions
|
|
360
|
-
- [GitHub Issues](https://github.com/your-org/verapay-js/issues)
|
|
361
|
-
- [Stripe Documentation](https://stripe.com/docs)
|
|
379
|
+
For issues and questions, contact the Lopay engineering team.
|
|
362
380
|
|
package/dist/index.cjs
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
'use strict';var stripeJs=require('@stripe/stripe-js'),tsMoney=require('ts-money');var i=class o extends Error{constructor(e,t="PAYMENT_FAILED",r){super(e),this.name="VerapayError",this.code=t,this.details={code:t,message:e,formattedMessage:this.formatMessage(e,t),...r},Error.captureStackTrace&&Error.captureStackTrace(this,o);}formatMessage(e,t){return {VALIDATION_ERROR:"Please check your payment information and try again.",PAYMENT_FAILED:"Your payment could not be processed. Please try again.",AUTHENTICATION_FAILED:"Payment authentication failed. Please try again.",NETWORK_ERROR:"Network error. Please check your connection and try again.",STRIPE_ERROR:"Payment service error. Please try again later.",CONFIGURATION_ERROR:"Configuration error. Please contact support.",CARD_DECLINED:"Your card was declined. Please use a different payment method.",INSUFFICIENT_FUNDS:"Insufficient funds. Please use a different payment method.",EXPIRED_CARD:"Your card has expired. Please use a different payment method."}[t]||e}toJSON(){return {name:this.name,code:this.code,message:this.message,details:this.details}}};var l=class extends i{constructor(e,t,r){super(e,"VALIDATION_ERROR",{field:t,metadata:r}),this.name="ValidationError";}};var m=class o extends i{constructor(e,t,r){let n=o.mapStripeCode(t);super(e,n,{stripeCode:t,metadata:r}),this.name="PaymentError";}static mapStripeCode(e){return e?{card_declined:"CARD_DECLINED",insufficient_funds:"INSUFFICIENT_FUNDS",expired_card:"EXPIRED_CARD",incorrect_cvc:"VALIDATION_ERROR",processing_error:"PAYMENT_FAILED",authentication_failed:"AUTHENTICATION_FAILED"}[e]||"PAYMENT_FAILED":"PAYMENT_FAILED"}};var y=class{static formatForUser(e){return "formattedMessage"in e?e.formattedMessage:"details"in e&&e.details&&typeof e.details=="object"&&"formattedMessage"in e.details&&typeof e.details.formattedMessage=="string"?e.details.formattedMessage:"An unexpected error occurred. Please try again."}static formatForDeveloper(e){return "code"in e&&"message"in e?`[${e.code}] ${e.message}`:e.message||"Unknown error"}static toJSON(e){return "toJSON"in e&&typeof e.toJSON=="function"?e.toJSON():{name:e.name||"Error",message:e.message,..."code"in e&&{code:e.code},..."details"in e&&{details:e.details}}}};var u=class{constructor(e){this.stripe=e;}async confirmPayment(e,t){let r=await this.stripe.confirmPayment({clientSecret:t,confirmParams:{payment_method:e,return_url:window.location.href},redirect:"if_required"});if(r.error)throw new m(r.error.message||"Payment failed",r.error.code);return r}async confirmCardPayment(e,t){let r=await this.stripe.confirmCardPayment(t,{payment_method:e});if(r.error)throw new m(r.error.message||"Payment failed",r.error.code);return r}async createPaymentMethod(e,t=false){let r;if(!t)r=await this.stripe.createPaymentMethod({elements:e});else {let a=(await e.getElement("address",{mode:"billing"}).getValue()).value;r=await this.stripe.createPaymentMethod({type:"card",card:e.getElement("cardNumber"),billing_details:{name:a.name,address:{...a.address,line2:a.address.line2??void 0}}});}if(r.error||!r.paymentMethod)throw new m(r.error?.message||"Failed to create payment method",r.error?.code);return r.paymentMethod.id}};var d={showIcon:true,iconStyle:"solid",placeholders:{cardNumber:"1234 1234 1234 1234",cardExpiry:"MM / YY",cardCvc:"CVC"},style:{base:{color:"#333333",fontFamily:"system-ui, -apple-system, sans-serif",fontSize:"16px","::placeholder":{color:"#aab7c4"}},complete:{color:"#333333"},empty:{},invalid:{color:"#df1b41"}}},v={cardNumber:"Card number",cardExpiry:"Expiry date",cardCvc:"CVC",address:"Address"},E=class{constructor(e,t,r){this.stripe=e;this.config=t;this.clientSecret=r;this.elements=null;this.mountedElements=new Map;this.elementStates=new Map;if(!r)throw new i("Client secret not initialized","CONFIGURATION_ERROR")}mountPaymentElement(e){if(!this.elements){let n={clientSecret:this.clientSecret,appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"};this.elements=this.stripe.elements(n);}if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let r=this.elements.create("payment",{layout:"tabs"});r.mount(e),this.mountedElements.set("payment",r);}mountCardNumberElement(e){this.mountIndividualFormElement(e,"cardNumber",this.cardElementOptions("cardNumber"));}mountCardExpiryElement(e){this.mountIndividualFormElement(e,"cardExpiry",this.cardElementOptions("cardExpiry"));}mountCardCvcElement(e){this.mountIndividualFormElement(e,"cardCvc",this.cardElementOptions("cardCvc"));}mountAddressElement(e,t){this.mountIndividualFormElement(e,"address",{mode:t});}cardElementOptions(e){let{elementsConfig:t}=this.config,r={placeholder:t?.placeholders?.[e]??d.placeholders[e],style:{base:{...d.style.base,...t?.style?.base},complete:{...d.style.complete,...t?.style?.complete},empty:{...d.style.empty,...t?.style?.empty},invalid:{...d.style.invalid,...t?.style?.invalid}}};return e==="cardNumber"&&(r.showIcon=t?.showIcon??d.showIcon,r.iconStyle=t?.iconStyle??d.iconStyle),r}mountIndividualFormElement(e,t,r){if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let a=this.createIndividualFormElement(t,r);a.mount(e),this.mountedElements.set(t,a),this.trackElementState(t,a);}createIndividualFormElement(e,t){return this.elements||(this.elements=this.stripe.elements({appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"})),this.elements.create(e,t)}async validate(){let e=[];for(let[t,r]of this.elementStates.entries())r.complete||e.push({field:t,message:r.error??`${v[t]??t} failed validation`});return {isValid:e.length===0,errors:e}}getElements(){return this.elements}unmountAll(){for(let e of this.mountedElements.values())e.unmount();this.mountedElements.clear(),this.elementStates.clear();}trackElementState(e,t){this.elementStates.set(e,{complete:false});let r=n=>{this.elementStates.set(e,{complete:n.complete,error:n.error?.message});};t.on("change",r);}};var f=class{constructor(){this.extensions=[];}add(e){this.extensions.push(e);}async runBeforePayment(e){let t=e;for(let r of this.extensions)r.beforePayment&&(t=await r.beforePayment(t));return t}async runAfterPayment(e){await Promise.all(this.extensions.filter(t=>t.afterPayment).map(t=>t.afterPayment(e)));}async runOnError(e){await Promise.all(this.extensions.filter(t=>t.onPaymentError).map(t=>t.onPaymentError(e)));}};var g=class{constructor(e,t,r){this.stripeAdapter=e;this.elementsManager=t;this.verapayService=r;}async process(e,t){let r=this.elementsManager.getElements();await this.validatePaymentCanProceed(r,t),await r.submit();let n=await this.stripeAdapter.createPaymentMethod(r,t.isUsingIndividualFormElements);return await this.verapayService.processPrePayment({merchantId:t.merchantId,paymentIntentId:t.paymentIntentId,paymentMethodId:n,customerData:{email:e.customerEmail,firstName:e.customerFirstName,lastName:e.customerLastName},description:e.description,metadata:e.metadata}),this.confirmPayment(n,t)}async validatePaymentCanProceed(e,t){if(!e)throw new i("Payment form not mounted","CONFIGURATION_ERROR");if(t.isUsingStripePaymentElement&&t.isUsingIndividualFormElements)throw new i("Both forms of payment form in use");if(t.isUsingIndividualFormElements){let r=await this.elementsManager.validate();if(!r.isValid)throw new i(r.errors[0].message,"VALIDATION_ERROR")}}async confirmPayment(e,t){let{clientSecret:r,isUsingStripePaymentElement:n,isUsingIndividualFormElements:a}=t,s;return n?s=await this.stripeAdapter.confirmPayment(e,r):a&&(s=await this.stripeAdapter.confirmCardPayment(e,r)),this.formatPaymentResult(s)}formatPaymentResult(e){return {success:e.paymentIntent.status==="succeeded",paymentIntentId:e.paymentIntent.id,status:e.paymentIntent.status}}};var p=class{constructor(e="http://localhost:3333"){this.baseUrl=e;}async initialisePayment(e){let{merchantId:t,paymentData:r}=e;try{let n=await fetch(`${this.baseUrl}/api/initialise-payment`,{method:"POST",headers:{"Content-Type":"application/json","x-api-key":"example.api.key"},body:JSON.stringify({merchantId:t,paymentData:{...r,paymentMethodType:"card"}})});if(!n.ok){let s=await n.json().catch(()=>({}));throw new i(s.error||`HTTP error! status: ${n.status}`,"CONFIGURATION_ERROR")}let a=await n.json();if(!a.clientSecret||!a.paymentIntentId)throw new i("Missing clientSecret or paymentIntentId in server response","CONFIGURATION_ERROR");return {paymentIntentId:a.paymentIntentId,clientSecret:a.clientSecret,connectAccountId:a.connectAccountId}}catch(n){throw n instanceof i?n:new i(n instanceof Error?n.message:"Unknown error occurred","CONFIGURATION_ERROR")}}async processPrePayment(e){try{let t=await fetch(`${this.baseUrl}/api/process-prepayment`,{method:"POST",headers:{"Content-Type":"application/json","x-forwarded-for":"example.ip.addr"},body:JSON.stringify({merchantId:e.merchantId,paymentIntentId:e.paymentIntentId,paymentMethodId:e.paymentMethodId,customerData:e.customerData,description:e.description,metadata:e.metadata})});if(!t.ok){let r=await t.json().catch(()=>({}));throw new i(r.error||`HTTP error! status: ${t.status}`,"CONFIGURATION_ERROR")}}catch(t){throw t instanceof i?t:new i(t instanceof Error?t.message:"Unknown error occurred","CONFIGURATION_ERROR")}}};var h=class h{constructor(e){this.stripeAdapter=null;this.elementsManager=null;this.paymentService=null;this.isUsingStripePaymentElement=false;this.isUsingIndividualFormElements=false;this.clientSecret=null;this.paymentIntentId=null;this.config=e,this.verapayService=new p,this.extensionsManager=new f;}async initialize(){this.validatePaymentInitialisation();let{clientSecret:e,paymentIntentId:t}=await this.verapayService.initialisePayment({merchantId:this.config.merchantId,paymentData:this.config.paymentData});this.clientSecret=e,this.paymentIntentId=t;let r=await stripeJs.loadStripe(h.STRIPE_PUBLISHABLE_KEY);if(!r)throw new i("Failed to load Stripe","CONFIGURATION_ERROR");this.stripeAdapter=new u(r),this.elementsManager=new E(r,this.config,e),this.paymentService=new g(this.stripeAdapter,this.elementsManager,this.verapayService);}async processPayment(e){await this.ensureInitialized();let t=await this.extensionsManager.runBeforePayment(e);try{let r=await this.paymentService.process(t,{merchantId:this.config.merchantId,paymentIntentId:this.paymentIntentId,clientSecret:this.clientSecret,isUsingStripePaymentElement:this.isUsingStripePaymentElement,isUsingIndividualFormElements:this.isUsingIndividualFormElements});return await this.extensionsManager.runAfterPayment(r),r}catch(r){throw await this.extensionsManager.runOnError(r),this.handlePaymentError(r)}}async mountPaymentForm(e){await this.ensureInitialized(),this.elementsManager.mountPaymentElement(e),this.isUsingStripePaymentElement=true;}async mountCardNumber(e){await this.ensureInitialized(),this.elementsManager.mountCardNumberElement(e),this.isUsingIndividualFormElements=true;}async mountCardExpiry(e){await this.ensureInitialized(),this.elementsManager.mountCardExpiryElement(e),this.isUsingIndividualFormElements=true;}async mountCardCvc(e){await this.ensureInitialized(),this.elementsManager.mountCardCvcElement(e),this.isUsingIndividualFormElements=true;}async mountAddress(e,t){await this.ensureInitialized(),this.elementsManager.mountAddressElement(e,t),this.isUsingIndividualFormElements=true;}addExtension(e){this.extensionsManager.add(e);}async ensureInitialized(){this.stripeAdapter||await this.initialize();}validatePaymentInitialisation(){let{amount:e,currency:t,partnerFee:r}=this.config.paymentData;if(!t)throw new l("Currency is required","currency");let n=t.toUpperCase(),a=this.toMoney(e,n,"amount");if(a.isZero()||a.isNegative())throw new l("Amount must be greater than 0","amount");if(r!==void 0&&this.toMoney(r,n,"partnerFee").isNegative())throw new l("partnerFee cannot be negative","partnerFee")}toMoney(e,t,r){try{return tsMoney.Money.fromInteger(e,t)}catch{throw new l(`${r} must be an integer in the smallest currency unit (e.g., cents for USD)`,r)}}handlePaymentError(e){return e instanceof i?e:new m(e.message||"Payment failed",e.code)}};h.STRIPE_PUBLISHABLE_KEY="pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq";var R=h;var I=class{validateCardNumber(e){let t=e.replace(/\D/g,"");if(t.length<13||t.length>19)return false;let r=0,n=false;for(let a=t.length-1;a>=0;a--){let s=parseInt(t[a],10);n&&(s*=2,s>9&&(s-=9)),r+=s,n=!n;}return r%10===0}detectCardType(e){let t=e.replace(/\D/g,"");return /^4/.test(t)?"visa":/^5[1-5]/.test(t)?"mastercard":/^3[47]/.test(t)?"amex":/^6(?:011|5)/.test(t)?"discover":"unknown"}validateExpiry(e,t){let r=new Date,n=r.getFullYear(),a=r.getMonth()+1;if(e<1||e>12)return false;let s=t<100?2e3+t:t;return !(s<n||s===n&&e<a)}validateCVC(e,t="unknown"){let r=e.replace(/\D/g,"");return t==="amex"?r.length===4:r.length===3||r.length===4}validateAll(e,t,r,n){let a=this.detectCardType(e);return {number:{isValid:this.validateCardNumber(e),cardType:a},expiry:{isValid:this.validateExpiry(t,r),month:t,year:r},cvc:{isValid:this.validateCVC(n,a),length:n.replace(/\D/g,"").length}}}};var P=class{static sanitizeCardNumber(e){return e.replace(/\D/g,"")}static formatCardNumber(e){return this.sanitizeCardNumber(e).replace(/(\d{4})/g,"$1 ").trim()}static sanitizeCVC(e){return e.replace(/\D/g,"").slice(0,4)}static sanitizeExpiry(e){let t=e.replace(/\D/g,"");return t.length===4?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,4),10)}:t.length===6?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,6),10)}:null}};var ue="0.0.1";
|
|
2
|
-
exports.CardValidator=I;exports.ErrorFormatter=y;exports.InputSanitizer=P;exports.PaymentError=
|
|
1
|
+
'use strict';var stripeJs=require('@stripe/stripe-js'),tsMoney=require('ts-money');var i=class o extends Error{constructor(e,t="PAYMENT_FAILED",r){super(e),this.name="VerapayError",this.code=t,this.details={code:t,message:e,formattedMessage:this.formatMessage(e,t),...r},Error.captureStackTrace&&Error.captureStackTrace(this,o);}formatMessage(e,t){return {VALIDATION_ERROR:"Please check your payment information and try again.",PAYMENT_FAILED:"Your payment could not be processed. Please try again.",AUTHENTICATION_FAILED:"Payment authentication failed. Please try again.",NETWORK_ERROR:"Network error. Please check your connection and try again.",STRIPE_ERROR:"Payment service error. Please try again later.",CONFIGURATION_ERROR:"Configuration error. Please contact support.",CARD_DECLINED:"Your card was declined. Please use a different payment method.",INSUFFICIENT_FUNDS:"Insufficient funds. Please use a different payment method.",EXPIRED_CARD:"Your card has expired. Please use a different payment method."}[t]||e}toJSON(){return {name:this.name,code:this.code,message:this.message,details:this.details}}};var m=class extends i{constructor(e,t,r){super(e,"VALIDATION_ERROR",{field:t,metadata:r}),this.name="ValidationError";}};var l=class o extends i{constructor(e,t,r){let n=o.mapStripeCode(t);super(e,n,{stripeCode:t,metadata:r}),this.name="PaymentError";}static mapStripeCode(e){return e?{card_declined:"CARD_DECLINED",insufficient_funds:"INSUFFICIENT_FUNDS",expired_card:"EXPIRED_CARD",incorrect_cvc:"VALIDATION_ERROR",processing_error:"PAYMENT_FAILED",authentication_failed:"AUTHENTICATION_FAILED"}[e]||"PAYMENT_FAILED":"PAYMENT_FAILED"}};var y=class{static formatForUser(e){return "formattedMessage"in e?e.formattedMessage:"details"in e&&e.details&&typeof e.details=="object"&&"formattedMessage"in e.details&&typeof e.details.formattedMessage=="string"?e.details.formattedMessage:"An unexpected error occurred. Please try again."}static formatForDeveloper(e){return "code"in e&&"message"in e?`[${e.code}] ${e.message}`:e.message||"Unknown error"}static toJSON(e){return "toJSON"in e&&typeof e.toJSON=="function"?e.toJSON():{name:e.name||"Error",message:e.message,..."code"in e&&{code:e.code},..."details"in e&&{details:e.details}}}};var u=class{constructor(e){this.stripe=e;}async confirmPayment(e,t){let r=await this.stripe.confirmPayment({clientSecret:t,confirmParams:{payment_method:e,return_url:window.location.href},redirect:"if_required"});if(r.error)throw new l(r.error.message||"Payment failed",r.error.code);return r}async confirmCardPayment(e,t){let r=await this.stripe.confirmCardPayment(t,{payment_method:e});if(r.error)throw new l(r.error.message||"Payment failed",r.error.code);return r}async createPaymentMethod(e,t=false){let r;if(!t)r=await this.stripe.createPaymentMethod({elements:e});else {let a=(await e.getElement("address",{mode:"billing"}).getValue()).value;r=await this.stripe.createPaymentMethod({type:"card",card:e.getElement("cardNumber"),billing_details:{name:a.name,address:{...a.address,line2:a.address.line2??void 0}}});}if(r.error||!r.paymentMethod)throw new l(r.error?.message||"Failed to create payment method",r.error?.code);return r.paymentMethod.id}};var d={showIcon:true,iconStyle:"solid",placeholders:{cardNumber:"1234 1234 1234 1234",cardExpiry:"MM / YY - TESTING",cardCvc:"CVC"},style:{base:{color:"#333333",fontFamily:"system-ui, -apple-system, sans-serif",fontSize:"16px","::placeholder":{color:"#aab7c4"}},complete:{color:"#333333"},empty:{},invalid:{color:"#df1b41"}}},v={cardNumber:"Card number",cardExpiry:"Expiry date",cardCvc:"CVC",address:"Address"},E=class{constructor(e,t,r){this.stripe=e;this.config=t;this.clientSecret=r;this.elements=null;this.mountedElements=new Map;this.elementStates=new Map;if(!r)throw new i("Client secret not initialized","CONFIGURATION_ERROR")}mountPaymentElement(e){if(!this.elements){let n={clientSecret:this.clientSecret,appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"};this.elements=this.stripe.elements(n);}if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let r=this.elements.create("payment",{layout:"tabs"});r.mount(e),this.mountedElements.set("payment",r);}mountCardNumberElement(e){this.mountIndividualFormElement(e,"cardNumber",this.cardElementOptions("cardNumber"));}mountCardExpiryElement(e){this.mountIndividualFormElement(e,"cardExpiry",this.cardElementOptions("cardExpiry"));}mountCardCvcElement(e){this.mountIndividualFormElement(e,"cardCvc",this.cardElementOptions("cardCvc"));}mountAddressElement(e,t){this.mountIndividualFormElement(e,"address",{mode:t});}cardElementOptions(e){let{elementsConfig:t}=this.config,r={placeholder:t?.placeholders?.[e]??d.placeholders[e],style:{base:{...d.style.base,...t?.style?.base},complete:{...d.style.complete,...t?.style?.complete},empty:{...d.style.empty,...t?.style?.empty},invalid:{...d.style.invalid,...t?.style?.invalid}}};return e==="cardNumber"&&(r.showIcon=t?.showIcon??d.showIcon,r.iconStyle=t?.iconStyle??d.iconStyle),r}mountIndividualFormElement(e,t,r){if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let a=this.createIndividualFormElement(t,r);a.mount(e),this.mountedElements.set(t,a),this.trackElementState(t,a);}createIndividualFormElement(e,t){return this.elements||(this.elements=this.stripe.elements({appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"})),this.elements.create(e,t)}async validate(){let e=[];for(let[t,r]of this.elementStates.entries())r.complete||e.push({field:t,message:r.error??`${v[t]??t} failed validation`});return {isValid:e.length===0,errors:e}}getElements(){return this.elements}unmountAll(){for(let e of this.mountedElements.values())e.unmount();this.mountedElements.clear(),this.elementStates.clear();}trackElementState(e,t){this.elementStates.set(e,{complete:false});let r=n=>{this.elementStates.set(e,{complete:n.complete,error:n.error?.message});};t.on("change",r);}};var f=class{constructor(){this.extensions=[];}add(e){this.extensions.push(e);}async runBeforePayment(e){let t=e;for(let r of this.extensions)r.beforePayment&&(t=await r.beforePayment(t));return t}async runAfterPayment(e){await Promise.all(this.extensions.filter(t=>t.afterPayment).map(t=>t.afterPayment(e)));}async runOnError(e){await Promise.all(this.extensions.filter(t=>t.onPaymentError).map(t=>t.onPaymentError(e)));}};var g=class{constructor(e,t,r){this.stripeAdapter=e;this.elementsManager=t;this.verapayService=r;}async process(e,t){let r=this.elementsManager.getElements();await this.validatePaymentCanProceed(r,t),await r.submit();let n=await this.stripeAdapter.createPaymentMethod(r,t.isUsingIndividualFormElements);return await this.verapayService.processPrePayment({merchantId:t.merchantId,paymentIntentId:t.paymentIntentId,paymentMethodId:n,customerData:{email:e.customerEmail,firstName:e.customerFirstName,lastName:e.customerLastName},description:e.description,metadata:e.metadata}),this.confirmPayment(n,t)}async validatePaymentCanProceed(e,t){if(!e)throw new i("Payment form not mounted","CONFIGURATION_ERROR");if(t.isUsingStripePaymentElement&&t.isUsingIndividualFormElements)throw new i("Both forms of payment form in use");if(t.isUsingIndividualFormElements){let r=await this.elementsManager.validate();if(!r.isValid)throw new i(r.errors[0].message,"VALIDATION_ERROR")}}async confirmPayment(e,t){let{clientSecret:r,isUsingStripePaymentElement:n,isUsingIndividualFormElements:a}=t,s;return n?s=await this.stripeAdapter.confirmPayment(e,r):a&&(s=await this.stripeAdapter.confirmCardPayment(e,r)),this.formatPaymentResult(s)}formatPaymentResult(e){return {success:e.paymentIntent.status==="succeeded",paymentIntentId:e.paymentIntent.id,status:e.paymentIntent.status}}};var p=class{constructor(e="http://localhost:3333"){this.baseUrl=e;}async initialisePayment(e){let{merchantId:t,paymentData:r}=e;try{let n=await fetch(`${this.baseUrl}/api/initialise-payment`,{method:"POST",headers:{"Content-Type":"application/json","x-api-key":"example.api.key"},body:JSON.stringify({merchantId:t,paymentData:{...r,paymentMethodType:"card"}})});if(!n.ok){let s=await n.json().catch(()=>({}));throw new i(s.error||`HTTP error! status: ${n.status}`,"CONFIGURATION_ERROR")}let a=await n.json();if(!a.clientSecret||!a.paymentIntentId)throw new i("Missing clientSecret or paymentIntentId in server response","CONFIGURATION_ERROR");return {paymentIntentId:a.paymentIntentId,clientSecret:a.clientSecret,connectAccountId:a.connectAccountId}}catch(n){throw n instanceof i?n:new i(n instanceof Error?n.message:"Unknown error occurred","CONFIGURATION_ERROR")}}async processPrePayment(e){try{let t=await fetch(`${this.baseUrl}/api/process-prepayment`,{method:"POST",headers:{"Content-Type":"application/json","x-forwarded-for":"example.ip.addr"},body:JSON.stringify({merchantId:e.merchantId,paymentIntentId:e.paymentIntentId,paymentMethodId:e.paymentMethodId,customerData:e.customerData,description:e.description,metadata:e.metadata})});if(!t.ok){let r=await t.json().catch(()=>({}));throw new i(r.error||`HTTP error! status: ${t.status}`,"CONFIGURATION_ERROR")}}catch(t){throw t instanceof i?t:new i(t instanceof Error?t.message:"Unknown error occurred","CONFIGURATION_ERROR")}}};var h=class h{constructor(e){this.stripeAdapter=null;this.elementsManager=null;this.paymentService=null;this.isUsingStripePaymentElement=false;this.isUsingIndividualFormElements=false;this.clientSecret=null;this.paymentIntentId=null;this.config=e,this.verapayService=new p,this.extensionsManager=new f;}async initialize(){this.validatePaymentInitialisation();let{clientSecret:e,paymentIntentId:t}=await this.verapayService.initialisePayment({merchantId:this.config.merchantId,paymentData:this.config.paymentData});this.clientSecret=e,this.paymentIntentId=t;let r=await stripeJs.loadStripe(h.STRIPE_PUBLISHABLE_KEY);if(!r)throw new i("Failed to load Stripe","CONFIGURATION_ERROR");this.stripeAdapter=new u(r),this.elementsManager=new E(r,this.config,e),this.paymentService=new g(this.stripeAdapter,this.elementsManager,this.verapayService);}async processPayment(e){await this.ensureInitialized();let t=await this.extensionsManager.runBeforePayment(e);try{let r=await this.paymentService.process(t,{merchantId:this.config.merchantId,paymentIntentId:this.paymentIntentId,clientSecret:this.clientSecret,isUsingStripePaymentElement:this.isUsingStripePaymentElement,isUsingIndividualFormElements:this.isUsingIndividualFormElements});return await this.extensionsManager.runAfterPayment(r),r}catch(r){throw await this.extensionsManager.runOnError(r),this.handlePaymentError(r)}}async mountPaymentForm(e){await this.ensureInitialized(),this.elementsManager.mountPaymentElement(e),this.isUsingStripePaymentElement=true;}async mountCardNumber(e){await this.ensureInitialized(),this.elementsManager.mountCardNumberElement(e),this.isUsingIndividualFormElements=true;}async mountCardExpiry(e){await this.ensureInitialized(),this.elementsManager.mountCardExpiryElement(e),this.isUsingIndividualFormElements=true;}async mountCardCvc(e){await this.ensureInitialized(),this.elementsManager.mountCardCvcElement(e),this.isUsingIndividualFormElements=true;}async mountAddress(e,t){await this.ensureInitialized(),this.elementsManager.mountAddressElement(e,t),this.isUsingIndividualFormElements=true;}addExtension(e){this.extensionsManager.add(e);}async ensureInitialized(){this.stripeAdapter||await this.initialize();}validatePaymentInitialisation(){let{amount:e,currency:t,partnerFee:r}=this.config.paymentData;if(!t)throw new m("Currency is required","currency");let n=t.toUpperCase(),a=this.toMoney(e,n,"amount");if(a.isZero()||a.isNegative())throw new m("Amount must be greater than 0","amount");if(r!==void 0){let s=this.toMoney(r,n,"partnerFee");if(s.isNegative())throw new m("partnerFee cannot be negative","partnerFee");if(s.greaterThan(a))throw new m("partnerFee cannot exceed the payment amount","partnerFee")}}toMoney(e,t,r){try{return tsMoney.Money.fromInteger(e,t)}catch{throw new m(`${r} must be an integer in the smallest currency unit (e.g., cents for USD)`,r)}}handlePaymentError(e){return e instanceof i?e:new l(e.message||"Payment failed",e.code)}};h.STRIPE_PUBLISHABLE_KEY="pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq";var R=h;var I=class{validateCardNumber(e){let t=e.replace(/\D/g,"");if(t.length<13||t.length>19)return false;let r=0,n=false;for(let a=t.length-1;a>=0;a--){let s=parseInt(t[a],10);n&&(s*=2,s>9&&(s-=9)),r+=s,n=!n;}return r%10===0}detectCardType(e){let t=e.replace(/\D/g,"");return /^4/.test(t)?"visa":/^5[1-5]/.test(t)?"mastercard":/^3[47]/.test(t)?"amex":/^6(?:011|5)/.test(t)?"discover":"unknown"}validateExpiry(e,t){let r=new Date,n=r.getFullYear(),a=r.getMonth()+1;if(e<1||e>12)return false;let s=t<100?2e3+t:t;return !(s<n||s===n&&e<a)}validateCVC(e,t="unknown"){let r=e.replace(/\D/g,"");return t==="amex"?r.length===4:r.length===3||r.length===4}validateAll(e,t,r,n){let a=this.detectCardType(e);return {number:{isValid:this.validateCardNumber(e),cardType:a},expiry:{isValid:this.validateExpiry(t,r),month:t,year:r},cvc:{isValid:this.validateCVC(n,a),length:n.replace(/\D/g,"").length}}}};var P=class{static sanitizeCardNumber(e){return e.replace(/\D/g,"")}static formatCardNumber(e){return this.sanitizeCardNumber(e).replace(/(\d{4})/g,"$1 ").trim()}static sanitizeCVC(e){return e.replace(/\D/g,"").slice(0,4)}static sanitizeExpiry(e){let t=e.replace(/\D/g,"");return t.length===4?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,4),10)}:t.length===6?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,6),10)}:null}};var ue="0.0.1";
|
|
2
|
+
exports.CardValidator=I;exports.ErrorFormatter=y;exports.InputSanitizer=P;exports.PaymentError=l;exports.VERSION=ue;exports.ValidationError=m;exports.VerapayClient=R;exports.VerapayError=i;exports.VerapayService=p;//# sourceMappingURL=index.cjs.map
|
|
3
3
|
//# sourceMappingURL=index.cjs.map
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/errors/VerapayError.ts","../src/errors/ValidationError.ts","../src/errors/PaymentError.ts","../src/errors/errorFormatter.ts","../src/client/StripeAdapter.ts","../src/client/ElementsManager.ts","../src/client/PaymentExtensionsManager.ts","../src/services/PaymentService.ts","../src/services/VerapayService.ts","../src/client/VerapayClient.ts","../src/validation/cardValidator.ts","../src/validation/inputSanitizer.ts","../src/index.ts"],"names":["VerapayError","_VerapayError","message","code","details","ValidationError","field","metadata","PaymentError","_PaymentError","stripeCode","ErrorFormatter","error","StripeAdapter","stripe","paymentMethodId","clientSecret","result","elements","isUsingIndividualFormElements","address","DEFAULT_CARD_ELEMENT_CONFIG","FIELD_LABELS","ElementsManager","config","selector","elementsConfig","element","mode","fieldType","options","formFieldType","errors","state","handleElementChange","event","PaymentExtensionsManager","extension","request","modifiedRequest","ext","PaymentService","stripeAdapter","elementsManager","verapayService","context","validation","isUsingStripePaymentElement","VerapayService","baseUrl","merchantId","paymentData","response","errorData","data","_VerapayClient","paymentIntentId","loadStripe","paymentResult","amount","currency","partnerFee","uppercaseCurrency","paymentAmount","value","fieldName","Money","VerapayClient","CardValidator","cardNumber","cleaned","sum","isEven","i","digit","month","year","now","currentYear","currentMonth","fullYear","cvc","cardType","expiryMonth","expiryYear","InputSanitizer","input","VERSION"],"mappings":"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","file":"index.cjs","sourcesContent":["import type { ErrorDetails } from '../types';\nimport { ErrorCode } from '../types';\n\nexport class VerapayError extends Error {\n public readonly code: ErrorCode;\n public readonly details: ErrorDetails;\n\n constructor(\n message: string,\n code: ErrorCode = ErrorCode.PAYMENT_FAILED,\n details?: Partial<ErrorDetails>\n ) {\n super(message);\n this.name = 'VerapayError';\n this.code = code;\n this.details = {\n code,\n message,\n formattedMessage: this.formatMessage(message, code),\n ...details,\n };\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, VerapayError);\n }\n }\n\n private formatMessage(message: string, code: ErrorCode): string {\n const messageMap: Record<ErrorCode, string> = {\n [ErrorCode.VALIDATION_ERROR]:\n 'Please check your payment information and try again.',\n [ErrorCode.PAYMENT_FAILED]:\n 'Your payment could not be processed. Please try again.',\n [ErrorCode.AUTHENTICATION_FAILED]:\n 'Payment authentication failed. Please try again.',\n [ErrorCode.NETWORK_ERROR]:\n 'Network error. Please check your connection and try again.',\n [ErrorCode.STRIPE_ERROR]:\n 'Payment service error. Please try again later.',\n [ErrorCode.CONFIGURATION_ERROR]:\n 'Configuration error. Please contact support.',\n [ErrorCode.CARD_DECLINED]:\n 'Your card was declined. Please use a different payment method.',\n [ErrorCode.INSUFFICIENT_FUNDS]:\n 'Insufficient funds. Please use a different payment method.',\n [ErrorCode.EXPIRED_CARD]:\n 'Your card has expired. Please use a different payment method.',\n };\n\n return messageMap[code] || message;\n }\n\n toJSON() {\n return {\n name: this.name,\n code: this.code,\n message: this.message,\n details: this.details,\n };\n }\n}\n","import { VerapayError } from './VerapayError';\nimport { ErrorCode } from '../types';\n\nexport class ValidationError extends VerapayError {\n constructor(message: string, field?: string, metadata?: Record<string, any>) {\n super(message, ErrorCode.VALIDATION_ERROR, {\n field,\n metadata,\n });\n this.name = 'ValidationError';\n }\n}\n","import { VerapayError } from './VerapayError';\nimport { ErrorCode } from '../types';\n\nexport class PaymentError extends VerapayError {\n constructor(\n message: string,\n stripeCode?: string,\n metadata?: Record<string, any>\n ) {\n const code = PaymentError.mapStripeCode(stripeCode);\n super(message, code, {\n stripeCode,\n metadata,\n });\n this.name = 'PaymentError';\n }\n\n private static mapStripeCode(stripeCode?: string): ErrorCode {\n if (!stripeCode) return ErrorCode.PAYMENT_FAILED;\n\n const codeMap: Record<string, ErrorCode> = {\n card_declined: ErrorCode.CARD_DECLINED,\n insufficient_funds: ErrorCode.INSUFFICIENT_FUNDS,\n expired_card: ErrorCode.EXPIRED_CARD,\n incorrect_cvc: ErrorCode.VALIDATION_ERROR,\n processing_error: ErrorCode.PAYMENT_FAILED,\n authentication_failed: ErrorCode.AUTHENTICATION_FAILED,\n };\n\n return codeMap[stripeCode] || ErrorCode.PAYMENT_FAILED;\n }\n}\n","import type { ErrorDetails } from '../types';\n\nexport class ErrorFormatter {\n static formatForUser(error: Error | ErrorDetails): string {\n if ('formattedMessage' in error) {\n return error.formattedMessage;\n }\n if (\n 'details' in error &&\n error.details &&\n typeof error.details === 'object' &&\n 'formattedMessage' in error.details &&\n typeof error.details.formattedMessage === 'string'\n ) {\n return error.details.formattedMessage;\n }\n return 'An unexpected error occurred. Please try again.';\n }\n\n static formatForDeveloper(error: Error | ErrorDetails): string {\n if ('code' in error && 'message' in error) {\n return `[${error.code}] ${error.message}`;\n }\n return error.message || 'Unknown error';\n }\n\n static toJSON(error: Error | ErrorDetails): Record<string, any> {\n if ('toJSON' in error && typeof error.toJSON === 'function') {\n return error.toJSON();\n }\n\n return {\n name: (error as Error).name || 'Error',\n message: error.message,\n ...('code' in error && { code: error.code }),\n ...('details' in error && { details: error.details }),\n };\n }\n}\n","import type { PaymentIntent, Stripe, StripeElements } from '@stripe/stripe-js';\nimport { PaymentError } from '../errors';\n\nexport class StripeAdapter {\n constructor(private stripe: Stripe) {}\n\n async confirmPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmPayment({\n clientSecret,\n confirmParams: {\n payment_method: paymentMethodId,\n return_url: window.location.href,\n },\n redirect: 'if_required',\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async confirmCardPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmCardPayment(clientSecret, {\n payment_method: paymentMethodId,\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async createPaymentMethod(\n elements: StripeElements,\n isUsingIndividualFormElements: boolean = false\n ): Promise<string> {\n let result;\n\n if (!isUsingIndividualFormElements) {\n result = await this.stripe.createPaymentMethod({\n elements,\n });\n } else {\n // @ts-ignore - Stripe types don't include mode parameter for getElement\n const addressElement = await elements.getElement('address', { mode: 'billing' })!.getValue();\n const address = addressElement!.value;\n\n result = await this.stripe.createPaymentMethod({\n type: 'card',\n card: elements.getElement('cardNumber')!,\n billing_details: {\n name: address.name,\n address: {\n ...address.address,\n line2: address.address.line2 ?? undefined,\n },\n },\n });\n }\n\n if (result.error || !result.paymentMethod) {\n throw new PaymentError(\n result.error?.message || 'Failed to create payment method',\n result.error?.code\n );\n }\n\n return result.paymentMethod.id;\n }\n}\n","import type {\n Stripe,\n StripeElements,\n StripeElement,\n StripePaymentElement,\n StripeCardNumberElement,\n} from '@stripe/stripe-js';\nimport type { VerapayConfig, ValidationError, ValidationResult } from '../types';\nimport { VerapayError, ErrorCode } from '../errors';\n\ntype ElementState = { complete: boolean; error?: string }\n\nconst DEFAULT_CARD_ELEMENT_CONFIG = {\n showIcon: true,\n iconStyle: 'solid' as const,\n placeholders: {\n cardNumber: '1234 1234 1234 1234',\n cardExpiry: 'MM / YY',\n cardCvc: 'CVC',\n },\n style: {\n base: {\n color: '#333333',\n fontFamily: 'system-ui, -apple-system, sans-serif',\n fontSize: '16px',\n '::placeholder': { color: '#aab7c4' },\n },\n complete: {\n color: '#333333',\n },\n empty: {},\n invalid: {\n color: '#df1b41',\n },\n },\n}\n\nconst FIELD_LABELS: Record<string, string> = {\n cardNumber: 'Card number',\n cardExpiry: 'Expiry date',\n cardCvc: 'CVC',\n address: 'Address',\n}\n\nexport class ElementsManager {\n private elements: StripeElements | null = null;\n private mountedElements: Map<string, StripeElement> = new Map();\n private elementStates: Map<string, ElementState> = new Map();\n\n constructor(\n private stripe: Stripe,\n private config: VerapayConfig,\n private clientSecret: string\n ) {\n if (!clientSecret) {\n throw new VerapayError(\n 'Client secret not initialized',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n mountPaymentElement(selector: string): void {\n if (!this.elements) {\n const elementsConfig = {\n clientSecret: this.clientSecret,\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n };\n\n this.elements = this.stripe.elements(elementsConfig);\n }\n\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.elements.create('payment', {\n layout: 'tabs',\n }) as StripePaymentElement;\n\n element.mount(selector);\n this.mountedElements.set('payment', element);\n }\n\n mountCardNumberElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardNumber', this.cardElementOptions('cardNumber'));\n }\n\n mountCardExpiryElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardExpiry', this.cardElementOptions('cardExpiry'));\n }\n\n mountCardCvcElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardCvc', this.cardElementOptions('cardCvc'));\n }\n\n mountAddressElement(selector: string, mode: 'billing' | 'shipping'): void {\n this.mountIndividualFormElement(selector, 'address', { mode });\n }\n\n private cardElementOptions(fieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc'): Record<string, unknown> {\n const { elementsConfig } = this.config;\n const options: Record<string, unknown> = {\n placeholder: elementsConfig?.placeholders?.[fieldType] ?? DEFAULT_CARD_ELEMENT_CONFIG.placeholders[fieldType],\n style: {\n base: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.base, ...elementsConfig?.style?.base },\n complete: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.complete, ...elementsConfig?.style?.complete },\n empty: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.empty, ...elementsConfig?.style?.empty },\n invalid: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.invalid, ...elementsConfig?.style?.invalid },\n },\n };\n\n if (fieldType === 'cardNumber') {\n options.showIcon = elementsConfig?.showIcon ?? DEFAULT_CARD_ELEMENT_CONFIG.showIcon;\n options.iconStyle = elementsConfig?.iconStyle ?? DEFAULT_CARD_ELEMENT_CONFIG.iconStyle;\n }\n\n return options;\n }\n\n private mountIndividualFormElement(selector: string, formFieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc' | 'address', options?: Record<string, unknown>) {\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.createIndividualFormElement(formFieldType, options) as StripeCardNumberElement;\n element.mount(selector);\n\n this.mountedElements.set(formFieldType, element);\n this.trackElementState(formFieldType, element);\n }\n\n private createIndividualFormElement(\n formFieldType: any,\n options?: Record<string, unknown>\n ): StripeElement {\n if (!this.elements) {\n // For individual card elements, don't pass clientSecret\n // It's only needed when creating Payment Element or confirming payment\n this.elements = this.stripe.elements({\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n });\n }\n\n return this.elements.create(formFieldType, options);\n }\n\n async validate(): Promise<ValidationResult> {\n const errors: ValidationError[] = []\n\n for (const [field, state] of this.elementStates.entries()) {\n if (!state.complete) {\n errors.push({\n field,\n message: state.error ?? `${FIELD_LABELS[field] ?? field} failed validation`,\n })\n }\n }\n\n return { isValid: errors.length === 0, errors }\n }\n\n getElements(): StripeElements | null {\n return this.elements;\n }\n\n unmountAll(): void {\n for (const element of this.mountedElements.values()) {\n element.unmount();\n }\n this.mountedElements.clear();\n this.elementStates.clear();\n }\n\n private trackElementState(field: string, element: StripeElement): void {\n this.elementStates.set(field, { complete: false })\n\n const handleElementChange = (event: { complete: boolean; error?: { message: string } }) => {\n this.elementStates.set(field, { complete: event.complete, error: event.error?.message })\n };\n\n (element as any).on('change', handleElementChange)\n }\n}\n","import type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport type { PaymentExtension } from '../extensions'\n\nexport class PaymentExtensionsManager {\n private extensions: PaymentExtension[] = []\n\n add(extension: PaymentExtension): void {\n this.extensions.push(extension)\n }\n\n async runBeforePayment(request: ProcessPaymentRequest): Promise<ProcessPaymentRequest> {\n let modifiedRequest = request\n for (const ext of this.extensions) {\n if (ext.beforePayment) {\n modifiedRequest = await ext.beforePayment(modifiedRequest)\n }\n }\n return modifiedRequest\n }\n\n async runAfterPayment(result: PaymentResult): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.afterPayment)\n .map((ext) => ext.afterPayment!(result)),\n )\n }\n\n async runOnError(error: Error): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.onPaymentError)\n .map((ext) => ext.onPaymentError!(error)),\n )\n }\n}\n","import { StripeAdapter } from '../client/StripeAdapter'\nimport { ElementsManager } from '../client/ElementsManager'\nimport { ErrorCode, VerapayError } from '../errors'\nimport { VerapayService } from './VerapayService'\nimport type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport { StripeElements } from '@stripe/stripe-js';\n\nexport interface ProcessPaymentContext {\n merchantId: string\n paymentIntentId: string\n clientSecret: string\n isUsingStripePaymentElement: boolean\n isUsingIndividualFormElements: boolean\n}\n\nexport class PaymentService {\n constructor(\n private stripeAdapter: StripeAdapter,\n private elementsManager: ElementsManager,\n private verapayService: VerapayService,\n ) {}\n\n async process(request: ProcessPaymentRequest, context: ProcessPaymentContext): Promise<PaymentResult> {\n const elements = this.elementsManager.getElements()\n\n await this.validatePaymentCanProceed(elements, context);\n\n await elements!.submit()\n\n const paymentMethodId = await this.stripeAdapter.createPaymentMethod(\n elements!,\n context.isUsingIndividualFormElements,\n )\n\n await this.verapayService.processPrePayment({\n merchantId: context.merchantId,\n paymentIntentId: context.paymentIntentId,\n paymentMethodId,\n customerData: {\n email: request.customerEmail,\n firstName: request.customerFirstName,\n lastName: request.customerLastName,\n },\n description: request.description,\n metadata: request.metadata,\n })\n\n return this.confirmPayment(paymentMethodId, context)\n }\n\n private async validatePaymentCanProceed(elements: StripeElements | null, context: ProcessPaymentContext) {\n if (!elements) {\n throw new VerapayError('Payment form not mounted', ErrorCode.CONFIGURATION_ERROR)\n }\n\n if (context.isUsingStripePaymentElement && context.isUsingIndividualFormElements) {\n throw new VerapayError('Both forms of payment form in use');\n }\n\n if (context.isUsingIndividualFormElements) {\n const validation = await this.elementsManager.validate()\n if (!validation.isValid) {\n throw new VerapayError(validation.errors[0].message, ErrorCode.VALIDATION_ERROR)\n }\n }\n }\n\n private async confirmPayment(\n paymentMethodId: string,\n context: ProcessPaymentContext,\n ): Promise<PaymentResult> {\n const { clientSecret, isUsingStripePaymentElement, isUsingIndividualFormElements } = context\n\n let result\n\n if (isUsingStripePaymentElement) {\n result = await this.stripeAdapter.confirmPayment(paymentMethodId, clientSecret)\n } else if (isUsingIndividualFormElements) {\n result = await this.stripeAdapter.confirmCardPayment(paymentMethodId, clientSecret)\n }\n\n return this.formatPaymentResult(result)\n }\n\n private formatPaymentResult(result: any): PaymentResult {\n return {\n success: result.paymentIntent.status === 'succeeded',\n paymentIntentId: result.paymentIntent.id,\n status: result.paymentIntent.status,\n }\n }\n}\n","import { ErrorCode, VerapayError } from '../errors';\nimport { PaymentData } from '../types';\n\nexport interface InitialisePaymentRequest {\n merchantId: string;\n paymentData: PaymentData;\n}\n\nexport interface InitialisePaymentResponse {\n paymentIntentId: string;\n clientSecret: string;\n connectAccountId: string;\n}\n\nexport interface ProcessPrePaymentRequest {\n merchantId: string;\n paymentIntentId: string;\n paymentMethodId: string;\n customerData: Record<string, any>;\n description?: string;\n metadata?: Record<string, string>;\n}\n\nexport class VerapayService {\n private readonly baseUrl: string;\n\n constructor(baseUrl: string = 'http://localhost:3333') {\n this.baseUrl = baseUrl;\n }\n\n async initialisePayment(\n request: InitialisePaymentRequest\n ): Promise<InitialisePaymentResponse> {\n const { merchantId, paymentData } = request;\n\n try {\n const response = await fetch(`${this.baseUrl}/api/initialise-payment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-api-key': 'example.api.key',\n },\n body: JSON.stringify({\n merchantId,\n paymentData: { ...paymentData, paymentMethodType: 'card' },\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const data = await response.json();\n\n if (!data.clientSecret || !data.paymentIntentId) {\n throw new VerapayError(\n 'Missing clientSecret or paymentIntentId in server response',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n return {\n paymentIntentId: data.paymentIntentId,\n clientSecret: data.clientSecret,\n connectAccountId: data.connectAccountId,\n };\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n async processPrePayment(request: ProcessPrePaymentRequest): Promise<void> {\n try {\n const response = await fetch(`${this.baseUrl}/api/process-prepayment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-forwarded-for': 'example.ip.addr',\n },\n body: JSON.stringify({\n merchantId: request.merchantId,\n paymentIntentId: request.paymentIntentId,\n paymentMethodId: request.paymentMethodId,\n customerData: request.customerData,\n description: request.description,\n metadata: request.metadata,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n}\n","import { loadStripe } from '@stripe/stripe-js';\nimport { Money } from 'ts-money';\nimport { StripeAdapter } from './StripeAdapter';\nimport { ElementsManager } from './ElementsManager';\nimport type { PaymentExtension } from '../extensions';\nimport { PaymentExtensionsManager } from './PaymentExtensionsManager';\nimport { PaymentService } from '../services/PaymentService';\nimport {\n ErrorCode,\n VerapayError,\n PaymentError,\n ValidationError,\n} from '../errors';\nimport { VerapayService } from '../services/VerapayService';\nimport type {\n VerapayConfig,\n ProcessPaymentRequest,\n PaymentResult,\n} from '../types';\n\nexport class VerapayClient {\n private static readonly STRIPE_PUBLISHABLE_KEY =\n 'pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq';\n\n private config: VerapayConfig;\n private verapayService: VerapayService;\n private extensionsManager: PaymentExtensionsManager;\n\n private stripeAdapter: StripeAdapter | null = null;\n private elementsManager: ElementsManager | null = null;\n private paymentService: PaymentService | null = null;\n\n private isUsingStripePaymentElement: boolean = false;\n private isUsingIndividualFormElements: boolean = false;\n\n private clientSecret: string | null = null;\n private paymentIntentId: string | null = null;\n\n constructor(config: VerapayConfig) {\n this.config = config;\n this.verapayService = new VerapayService();\n this.extensionsManager = new PaymentExtensionsManager();\n }\n\n async initialize(): Promise<void> {\n this.validatePaymentInitialisation()\n\n const { clientSecret, paymentIntentId } =\n await this.verapayService.initialisePayment({\n merchantId: this.config.merchantId,\n paymentData: this.config.paymentData\n });\n\n this.clientSecret = clientSecret;\n this.paymentIntentId = paymentIntentId;\n\n const stripe = await loadStripe(VerapayClient.STRIPE_PUBLISHABLE_KEY);\n\n if (!stripe) {\n throw new VerapayError(\n 'Failed to load Stripe',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n this.stripeAdapter = new StripeAdapter(stripe);\n this.elementsManager = new ElementsManager(\n stripe,\n this.config,\n clientSecret\n );\n this.paymentService = new PaymentService(\n this.stripeAdapter,\n this.elementsManager,\n this.verapayService\n );\n }\n\n async processPayment(request: ProcessPaymentRequest): Promise<PaymentResult> {\n await this.ensureInitialized();\n\n let modifiedRequest =\n await this.extensionsManager.runBeforePayment(request);\n\n try {\n const paymentResult = await this.paymentService!.process(\n modifiedRequest,\n {\n merchantId: this.config.merchantId,\n paymentIntentId: this.paymentIntentId!,\n clientSecret: this.clientSecret!,\n isUsingStripePaymentElement: this.isUsingStripePaymentElement,\n isUsingIndividualFormElements: this.isUsingIndividualFormElements,\n }\n );\n\n await this.extensionsManager.runAfterPayment(paymentResult);\n\n return paymentResult;\n } catch (error) {\n await this.extensionsManager.runOnError(error as Error);\n throw this.handlePaymentError(error);\n }\n }\n\n async mountPaymentForm(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountPaymentElement(selector);\n this.isUsingStripePaymentElement = true;\n }\n\n async mountCardNumber(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardNumberElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardExpiry(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardExpiryElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardCvc(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardCvcElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountAddress(\n selector: string,\n mode: 'billing' | 'shipping'\n ): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountAddressElement(selector, mode);\n this.isUsingIndividualFormElements = true;\n }\n\n addExtension(extension: PaymentExtension): void {\n this.extensionsManager.add(extension);\n }\n\n private async ensureInitialized(): Promise<void> {\n if (!this.stripeAdapter) {\n await this.initialize();\n }\n }\n\n private validatePaymentInitialisation(): void {\n const { amount, currency, partnerFee } = this.config.paymentData;\n\n if (!currency) {\n throw new ValidationError('Currency is required', 'currency');\n }\n\n const uppercaseCurrency = currency.toUpperCase();\n\n const paymentAmount = this.toMoney(amount, uppercaseCurrency, 'amount');\n\n if (paymentAmount.isZero() || paymentAmount.isNegative()) {\n throw new ValidationError('Amount must be greater than 0', 'amount');\n }\n\n if (partnerFee !== undefined) {\n const partnerFeeAmount = this.toMoney(partnerFee, uppercaseCurrency, 'partnerFee');\n\n if (partnerFeeAmount.isNegative()) {\n throw new ValidationError('partnerFee cannot be negative', 'partnerFee');\n }\n }\n }\n\n private toMoney(value: number, currency: string, fieldName: string): Money {\n try {\n return Money.fromInteger(value, currency);\n } catch {\n throw new ValidationError(\n `${fieldName} must be an integer in the smallest currency unit (e.g., cents for USD)`,\n fieldName\n );\n }\n }\n\n private handlePaymentError(error: any): Error {\n if (error instanceof VerapayError) {\n return error;\n }\n return new PaymentError(error.message || 'Payment failed', error.code);\n }\n}\n","import type { CardValidation } from '../types';\n\nexport class CardValidator {\n validateCardNumber(cardNumber: string): boolean {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (cleaned.length < 13 || cleaned.length > 19) {\n return false;\n }\n\n let sum = 0;\n let isEven = false;\n\n for (let i = cleaned.length - 1; i >= 0; i--) {\n let digit = parseInt(cleaned[i], 10);\n\n if (isEven) {\n digit *= 2;\n if (digit > 9) {\n digit -= 9;\n }\n }\n\n sum += digit;\n isEven = !isEven;\n }\n\n return sum % 10 === 0;\n }\n\n detectCardType(cardNumber: string): string {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (/^4/.test(cleaned)) return 'visa';\n if (/^5[1-5]/.test(cleaned)) return 'mastercard';\n if (/^3[47]/.test(cleaned)) return 'amex';\n if (/^6(?:011|5)/.test(cleaned)) return 'discover';\n\n return 'unknown';\n }\n\n validateExpiry(month: number, year: number): boolean {\n const now = new Date();\n const currentYear = now.getFullYear();\n const currentMonth = now.getMonth() + 1;\n\n if (month < 1 || month > 12) {\n return false;\n }\n\n const fullYear = year < 100 ? 2000 + year : year;\n\n if (fullYear < currentYear) {\n return false;\n }\n\n if (fullYear === currentYear && month < currentMonth) {\n return false;\n }\n\n return true;\n }\n\n validateCVC(cvc: string, cardType: string = 'unknown'): boolean {\n const cleaned = cvc.replace(/\\D/g, '');\n\n if (cardType === 'amex') {\n return cleaned.length === 4;\n }\n\n return cleaned.length === 3 || cleaned.length === 4;\n }\n\n validateAll(\n cardNumber: string,\n expiryMonth: number,\n expiryYear: number,\n cvc: string\n ): CardValidation {\n const cardType = this.detectCardType(cardNumber);\n\n return {\n number: {\n isValid: this.validateCardNumber(cardNumber),\n cardType: cardType as any,\n },\n expiry: {\n isValid: this.validateExpiry(expiryMonth, expiryYear),\n month: expiryMonth,\n year: expiryYear,\n },\n cvc: {\n isValid: this.validateCVC(cvc, cardType),\n length: cvc.replace(/\\D/g, '').length,\n },\n };\n }\n}\n","export class InputSanitizer {\n static sanitizeCardNumber(input: string): string {\n return input.replace(/\\D/g, '');\n }\n\n static formatCardNumber(input: string): string {\n const cleaned = this.sanitizeCardNumber(input);\n return cleaned.replace(/(\\d{4})/g, '$1 ').trim();\n }\n\n static sanitizeCVC(input: string): string {\n return input.replace(/\\D/g, '').slice(0, 4);\n }\n\n static sanitizeExpiry(input: string): { month: number; year: number } | null {\n const cleaned = input.replace(/\\D/g, '');\n\n if (cleaned.length === 4) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 4), 10),\n };\n } else if (cleaned.length === 6) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 6), 10),\n };\n }\n\n return null;\n }\n}\n","export { VerapayClient } from './client/VerapayClient';\nexport { VerapayService } from './services/VerapayService';\n\nexport type {\n InitialisePaymentRequest,\n InitialisePaymentResponse,\n ProcessPrePaymentRequest,\n} from './services/VerapayService';\n\nexport type {\n VerapayConfig,\n ElementsConfig,\n ProcessPaymentRequest,\n PaymentResult,\n CardValidation,\n ErrorDetails,\n ErrorCode,\n} from './types';\n\nexport {\n VerapayError,\n ValidationError,\n PaymentError,\n ErrorFormatter,\n} from './errors';\n\nexport { CardValidator, InputSanitizer } from './validation';\n\nexport type {\n PaymentExtension,\n DatabaseExtension,\n AnalyticsExtension,\n} from './extensions';\n\nexport const VERSION = '0.0.1';\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/errors/verapay-error.ts","../src/errors/validation-error.ts","../src/errors/payment-error.ts","../src/errors/error-formatter.ts","../src/client/stripe-adapter.ts","../src/client/elements-manager.ts","../src/client/payment-extensions-manager.ts","../src/services/payment-service.ts","../src/services/verapay-service.ts","../src/client/verapay-client.ts","../src/validation/card-validator.ts","../src/validation/input-sanitizer.ts","../src/index.ts"],"names":["VerapayError","_VerapayError","message","code","details","ValidationError","field","metadata","PaymentError","_PaymentError","stripeCode","ErrorFormatter","error","StripeAdapter","stripe","paymentMethodId","clientSecret","result","elements","isUsingIndividualFormElements","address","DEFAULT_CARD_ELEMENT_CONFIG","FIELD_LABELS","ElementsManager","config","selector","elementsConfig","element","mode","fieldType","options","formFieldType","errors","state","handleElementChange","event","PaymentExtensionsManager","extension","request","modifiedRequest","ext","PaymentService","stripeAdapter","elementsManager","verapayService","context","validation","isUsingStripePaymentElement","VerapayService","baseUrl","merchantId","paymentData","response","errorData","data","_VerapayClient","paymentIntentId","loadStripe","paymentResult","amount","currency","partnerFee","uppercaseCurrency","paymentAmount","partnerFeeAmount","value","fieldName","Money","VerapayClient","CardValidator","cardNumber","cleaned","sum","isEven","i","digit","month","year","now","currentYear","currentMonth","fullYear","cvc","cardType","expiryMonth","expiryYear","InputSanitizer","input","VERSION"],"mappings":"mFAGO,IAAMA,CAAAA,CAAN,MAAMC,CAAAA,SAAqB,KAAM,CAItC,WAAA,CACEC,CAAAA,CACAC,CAAAA,CAAAA,gBAAAA,CACAC,CAAAA,CACA,CACA,KAAA,CAAMF,CAAO,CAAA,CACb,IAAA,CAAK,IAAA,CAAO,cAAA,CACZ,IAAA,CAAK,IAAA,CAAOC,CAAAA,CACZ,IAAA,CAAK,OAAA,CAAU,CACb,IAAA,CAAAA,CAAAA,CACA,OAAA,CAAAD,CAAAA,CACA,gBAAA,CAAkB,IAAA,CAAK,aAAA,CAAcA,CAAAA,CAASC,CAAI,CAAA,CAClD,GAAGC,CACL,CAAA,CAEI,KAAA,CAAM,iBAAA,EACR,KAAA,CAAM,kBAAkB,IAAA,CAAMH,CAAY,EAE9C,CAEQ,aAAA,CAAcC,CAAAA,CAAiBC,CAAAA,CAAyB,CAsB9D,OArB8C,CAC3C,gBAAA,CACC,sDAAA,CACD,cAAA,CACC,wDAAA,CACD,qBAAA,CACC,kDAAA,CACD,cACC,4DAAA,CACD,YAAA,CACC,gDAAA,CACD,mBAAA,CACC,8CAAA,CACD,aAAA,CACC,gEAAA,CACD,kBAAA,CACC,4DAAA,CACD,YAAA,CACC,+DACJ,CAAA,CAEkBA,CAAI,CAAA,EAAKD,CAC7B,CAEA,QAAS,CACP,OAAO,CACL,IAAA,CAAM,IAAA,CAAK,IAAA,CACX,IAAA,CAAM,IAAA,CAAK,IAAA,CACX,OAAA,CAAS,IAAA,CAAK,OAAA,CACd,OAAA,CAAS,IAAA,CAAK,OAChB,CACF,CACF,ECzDO,IAAMG,CAAAA,CAAN,cAA8BL,CAAa,CAChD,WAAA,CAAYE,CAAAA,CAAiBI,CAAAA,CAAgBC,CAAAA,CAAgC,CAC3E,KAAA,CAAML,CAAAA,CAAAA,kBAAAA,CAAqC,CACzC,KAAA,CAAAI,CAAAA,CACA,SAAAC,CACF,CAAC,CAAA,CACD,IAAA,CAAK,IAAA,CAAO,kBACd,CACF,MCRaC,CAAAA,CAAN,MAAMC,CAAAA,SAAqBT,CAAa,CAC7C,WAAA,CACEE,CAAAA,CACAQ,CAAAA,CACAH,EACA,CACA,IAAMJ,CAAAA,CAAOM,CAAAA,CAAa,aAAA,CAAcC,CAAU,CAAA,CAClD,KAAA,CAAMR,CAAAA,CAASC,CAAAA,CAAM,CACnB,UAAA,CAAAO,CAAAA,CACA,QAAA,CAAAH,CACF,CAAC,EACD,IAAA,CAAK,IAAA,CAAO,eACd,CAEA,OAAe,aAAA,CAAcG,CAAAA,CAAgC,CAC3D,OAAKA,CAAAA,CAEsC,CACzC,aAAA,CAAA,eAAA,CACA,kBAAA,CAAA,oBAAA,CACA,YAAA,CAAA,cAAA,CACA,aAAA,CAAA,kBAAA,CACA,gBAAA,CAAA,gBAAA,CACA,6CACF,CAAA,CAEeA,CAAU,CAAA,EAAK,gBAAA,CAAA,gBAChC,CACF,EC7BO,IAAMC,CAAAA,CAAN,KAAqB,CAC1B,OAAO,aAAA,CAAcC,CAAAA,CAAqC,CACxD,OAAI,kBAAA,GAAsBA,EACjBA,CAAAA,CAAM,gBAAA,CAGb,SAAA,GAAaA,CAAAA,EACbA,CAAAA,CAAM,OAAA,EACN,OAAOA,CAAAA,CAAM,OAAA,EAAY,QAAA,EACzB,kBAAA,GAAsBA,CAAAA,CAAM,OAAA,EAC5B,OAAOA,CAAAA,CAAM,OAAA,CAAQ,kBAAqB,QAAA,CAEnCA,CAAAA,CAAM,OAAA,CAAQ,gBAAA,CAEhB,iDACT,CAEA,OAAO,kBAAA,CAAmBA,CAAAA,CAAqC,CAC7D,OAAI,MAAA,GAAUA,CAAAA,EAAS,SAAA,GAAaA,CAAAA,CAC3B,CAAA,CAAA,EAAIA,EAAM,IAAI,CAAA,EAAA,EAAKA,CAAAA,CAAM,OAAO,CAAA,CAAA,CAElCA,CAAAA,CAAM,OAAA,EAAW,eAC1B,CAEA,OAAO,MAAA,CAAOA,CAAAA,CAAkD,CAC9D,OAAI,QAAA,GAAYA,CAAAA,EAAS,OAAOA,CAAAA,CAAM,MAAA,EAAW,UAAA,CACxCA,CAAAA,CAAM,MAAA,EAAO,CAGf,CACL,IAAA,CAAOA,CAAAA,CAAgB,IAAA,EAAQ,OAAA,CAC/B,OAAA,CAASA,CAAAA,CAAM,OAAA,CACf,GAAI,MAAA,GAAUA,GAAS,CAAE,IAAA,CAAMA,CAAAA,CAAM,IAAK,CAAA,CAC1C,GAAI,SAAA,GAAaA,CAAAA,EAAS,CAAE,OAAA,CAASA,CAAAA,CAAM,OAAQ,CACrD,CACF,CACF,ECnCO,IAAMC,EAAN,KAAoB,CACzB,WAAA,CAAoBC,CAAAA,CAAgB,CAAhB,IAAA,CAAA,MAAA,CAAAA,EAAiB,CAErC,MAAM,cAAA,CACJC,CAAAA,CACAC,CAAAA,CAC2C,CAC3C,IAAMC,CAAAA,CAAS,MAAM,KAAK,MAAA,CAAO,cAAA,CAAe,CAC9C,YAAA,CAAAD,CAAAA,CACA,aAAA,CAAe,CACb,cAAA,CAAgBD,CAAAA,CAChB,UAAA,CAAY,MAAA,CAAO,QAAA,CAAS,IAC9B,CAAA,CACA,QAAA,CAAU,aACZ,CAAC,CAAA,CAED,GAAIE,CAAAA,CAAO,KAAA,CACT,MAAM,IAAIT,CAAAA,CACRS,CAAAA,CAAO,KAAA,CAAM,OAAA,EAAW,gBAAA,CACxBA,CAAAA,CAAO,KAAA,CAAM,IACf,CAAA,CAGF,OAAOA,CACT,CAEA,MAAM,kBAAA,CACJF,CAAAA,CACAC,CAAAA,CAC2C,CAC3C,IAAMC,CAAAA,CAAS,MAAM,IAAA,CAAK,MAAA,CAAO,kBAAA,CAAmBD,CAAAA,CAAc,CAChE,cAAA,CAAgBD,CAClB,CAAC,CAAA,CAED,GAAIE,CAAAA,CAAO,KAAA,CACT,MAAM,IAAIT,CAAAA,CACRS,CAAAA,CAAO,KAAA,CAAM,OAAA,EAAW,gBAAA,CACxBA,CAAAA,CAAO,KAAA,CAAM,IACf,CAAA,CAGF,OAAOA,CACT,CAEA,MAAM,mBAAA,CACJC,CAAAA,CACAC,CAAAA,CAAyC,KAAA,CACxB,CACjB,IAAIF,CAAAA,CAEJ,GAAI,CAACE,CAAAA,CACHF,CAAAA,CAAS,MAAM,IAAA,CAAK,MAAA,CAAO,oBAAoB,CAC7C,QAAA,CAAAC,CACF,CAAC,CAAA,CAAA,KACI,CAGL,IAAME,CAAAA,CAAAA,CADiB,MAAMF,CAAAA,CAAS,UAAA,CAAW,SAAA,CAAW,CAAE,IAAA,CAAM,SAAU,CAAC,EAAG,QAAA,EAAS,EAC3D,KAAA,CAEhCD,CAAAA,CAAS,MAAM,IAAA,CAAK,MAAA,CAAO,mBAAA,CAAoB,CAC7C,IAAA,CAAM,MAAA,CACN,IAAA,CAAMC,CAAAA,CAAS,UAAA,CAAW,YAAY,CAAA,CACtC,eAAA,CAAiB,CACf,IAAA,CAAME,CAAAA,CAAQ,IAAA,CACd,OAAA,CAAS,CACP,GAAGA,CAAAA,CAAQ,OAAA,CACX,KAAA,CAAOA,CAAAA,CAAQ,OAAA,CAAQ,KAAA,EAAS,MAClC,CACF,CACF,CAAC,EACH,CAEA,GAAIH,CAAAA,CAAO,KAAA,EAAS,CAACA,CAAAA,CAAO,aAAA,CAC1B,MAAM,IAAIT,CAAAA,CACRS,CAAAA,CAAO,KAAA,EAAO,OAAA,EAAW,iCAAA,CACzBA,CAAAA,CAAO,KAAA,EAAO,IAChB,CAAA,CAGF,OAAOA,CAAAA,CAAO,aAAA,CAAc,EAC9B,CACF,CAAA,CCxEA,IAAMI,CAAAA,CAA8B,CAClC,QAAA,CAAU,IAAA,CACV,SAAA,CAAW,OAAA,CACX,YAAA,CAAc,CACZ,WAAY,qBAAA,CACZ,UAAA,CAAY,mBAAA,CACZ,OAAA,CAAS,KACX,CAAA,CACA,KAAA,CAAO,CACL,KAAM,CACJ,KAAA,CAAO,SAAA,CACP,UAAA,CAAY,sCAAA,CACZ,QAAA,CAAU,MAAA,CACV,eAAA,CAAiB,CAAE,KAAA,CAAO,SAAU,CACtC,CAAA,CACA,QAAA,CAAU,CACR,KAAA,CAAO,SACT,CAAA,CACA,KAAA,CAAO,EAAC,CACR,OAAA,CAAS,CACP,KAAA,CAAO,SACT,CACF,CACF,CAAA,CAEMC,CAAAA,CAAuC,CAC3C,UAAA,CAAY,aAAA,CACZ,UAAA,CAAY,aAAA,CACZ,OAAA,CAAS,KAAA,CACT,OAAA,CAAS,SACX,CAAA,CAEaC,CAAAA,CAAN,KAAsB,CAK3B,YACUT,CAAAA,CACAU,CAAAA,CACAR,CAAAA,CACR,CAHQ,IAAA,CAAA,MAAA,CAAAF,CAAAA,CACA,IAAA,CAAA,MAAA,CAAAU,CAAAA,CACA,IAAA,CAAA,YAAA,CAAAR,CAAAA,CAPV,IAAA,CAAQ,QAAA,CAAkC,IAAA,CAC1C,IAAA,CAAQ,eAAA,CAA8C,IAAI,IAC1D,IAAA,CAAQ,aAAA,CAA2C,IAAI,GAAA,CAOrD,GAAI,CAACA,CAAAA,CACH,MAAM,IAAIhB,CAAAA,CACR,+BAAA,CAAA,qBAEF,CAEJ,CAEA,mBAAA,CAAoByB,CAAAA,CAAwB,CAC1C,GAAI,CAAC,IAAA,CAAK,QAAA,CAAU,CAClB,IAAMC,CAAAA,CAAiB,CACrB,YAAA,CAAc,IAAA,CAAK,YAAA,CACnB,UAAA,CAAY,IAAA,CAAK,MAAA,CAAO,UAAA,CACxB,MAAA,CAAQ,IAAA,CAAK,MAAA,CAAO,OACpB,KAAA,CAAO,IAAA,CAAK,MAAA,CAAO,KAAA,CACnB,qBAAA,CAAuB,QACzB,CAAA,CAEA,IAAA,CAAK,QAAA,CAAW,IAAA,CAAK,MAAA,CAAO,QAAA,CAASA,CAAc,EACrD,CAIA,GAAI,CAFc,QAAA,CAAS,aAAA,CAAcD,CAAQ,CAAA,CAG/C,MAAM,IAAIzB,CAAAA,CACR,CAAA,mBAAA,EAAsByB,CAAQ,CAAA,CAAA,CAAA,qBAEhC,CAAA,CAGF,IAAME,CAAAA,CAAU,IAAA,CAAK,QAAA,CAAS,MAAA,CAAO,UAAW,CAC9C,MAAA,CAAQ,MACV,CAAC,CAAA,CAEDA,CAAAA,CAAQ,KAAA,CAAMF,CAAQ,CAAA,CACtB,IAAA,CAAK,eAAA,CAAgB,GAAA,CAAI,SAAA,CAAWE,CAAO,EAC7C,CAEA,uBAAuBF,CAAAA,CAAwB,CAC7C,IAAA,CAAK,0BAAA,CAA2BA,CAAAA,CAAU,YAAA,CAAc,IAAA,CAAK,kBAAA,CAAmB,YAAY,CAAC,EAC/F,CAEA,sBAAA,CAAuBA,CAAAA,CAAwB,CAC7C,IAAA,CAAK,2BAA2BA,CAAAA,CAAU,YAAA,CAAc,IAAA,CAAK,kBAAA,CAAmB,YAAY,CAAC,EAC/F,CAEA,mBAAA,CAAoBA,CAAAA,CAAwB,CAC1C,IAAA,CAAK,0BAAA,CAA2BA,CAAAA,CAAU,SAAA,CAAW,IAAA,CAAK,mBAAmB,SAAS,CAAC,EACzF,CAEA,mBAAA,CAAoBA,CAAAA,CAAkBG,CAAAA,CAAoC,CACxE,IAAA,CAAK,0BAAA,CAA2BH,CAAAA,CAAU,SAAA,CAAW,CAAE,IAAA,CAAAG,CAAK,CAAC,EAC/D,CAEQ,kBAAA,CAAmBC,CAAAA,CAA6E,CACtG,GAAM,CAAE,cAAA,CAAAH,CAAe,EAAI,IAAA,CAAK,MAAA,CAC1BI,CAAAA,CAAmC,CACvC,WAAA,CAAaJ,CAAAA,EAAgB,YAAA,GAAeG,CAAS,GAAKR,CAAAA,CAA4B,YAAA,CAAaQ,CAAS,CAAA,CAC5G,KAAA,CAAO,CACL,IAAA,CAAM,CAAE,GAAGR,CAAAA,CAA4B,KAAA,CAAM,IAAA,CAAM,GAAGK,CAAAA,EAAgB,KAAA,EAAO,IAAK,EAClF,QAAA,CAAU,CAAE,GAAGL,CAAAA,CAA4B,KAAA,CAAM,QAAA,CAAU,GAAGK,CAAAA,EAAgB,KAAA,EAAO,QAAS,CAAA,CAC9F,KAAA,CAAO,CAAE,GAAGL,CAAAA,CAA4B,KAAA,CAAM,MAAO,GAAGK,CAAAA,EAAgB,KAAA,EAAO,KAAM,CAAA,CACrF,OAAA,CAAS,CAAE,GAAGL,CAAAA,CAA4B,KAAA,CAAM,OAAA,CAAS,GAAGK,CAAAA,EAAgB,KAAA,EAAO,OAAQ,CAC7F,CACF,CAAA,CAEA,OAAIG,CAAAA,GAAc,YAAA,GAChBC,CAAAA,CAAQ,QAAA,CAAWJ,CAAAA,EAAgB,QAAA,EAAYL,EAA4B,QAAA,CAC3ES,CAAAA,CAAQ,SAAA,CAAYJ,CAAAA,EAAgB,SAAA,EAAaL,CAAAA,CAA4B,SAAA,CAAA,CAGxES,CACT,CAEQ,0BAAA,CAA2BL,CAAAA,CAAkBM,CAAAA,CAAoED,CAAAA,CAAoC,CAG3J,GAAI,CAFc,QAAA,CAAS,aAAA,CAAcL,CAAQ,CAAA,CAG/C,MAAM,IAAIzB,CAAAA,CACR,CAAA,mBAAA,EAAsByB,CAAQ,wBAEhC,CAAA,CAGF,IAAME,CAAAA,CAAU,IAAA,CAAK,2BAAA,CAA4BI,CAAAA,CAAeD,CAAO,CAAA,CACvEH,CAAAA,CAAQ,KAAA,CAAMF,CAAQ,CAAA,CAEtB,IAAA,CAAK,eAAA,CAAgB,GAAA,CAAIM,CAAAA,CAAeJ,CAAO,CAAA,CAC/C,IAAA,CAAK,iBAAA,CAAkBI,CAAAA,CAAeJ,CAAO,EAC/C,CAEQ,2BAAA,CACNI,CAAAA,CACAD,CAAAA,CACe,CACf,OAAK,IAAA,CAAK,QAAA,GAGR,IAAA,CAAK,QAAA,CAAW,KAAK,MAAA,CAAO,QAAA,CAAS,CACnC,UAAA,CAAY,IAAA,CAAK,MAAA,CAAO,UAAA,CACxB,MAAA,CAAQ,KAAK,MAAA,CAAO,MAAA,CACpB,KAAA,CAAO,IAAA,CAAK,MAAA,CAAO,KAAA,CACnB,qBAAA,CAAuB,QACzB,CAAC,CAAA,CAAA,CAGI,IAAA,CAAK,QAAA,CAAS,MAAA,CAAOC,CAAAA,CAAeD,CAAO,CACpD,CAEA,MAAM,QAAA,EAAsC,CAC1C,IAAME,CAAAA,CAA4B,EAAC,CAEnC,IAAA,GAAW,CAAC1B,CAAAA,CAAO2B,CAAK,CAAA,GAAK,IAAA,CAAK,aAAA,CAAc,OAAA,EAAQ,CACjDA,CAAAA,CAAM,QAAA,EACTD,CAAAA,CAAO,IAAA,CAAK,CACV,KAAA,CAAA1B,CAAAA,CACA,OAAA,CAAS2B,CAAAA,CAAM,OAAS,CAAA,EAAGX,CAAAA,CAAahB,CAAK,CAAA,EAAKA,CAAK,CAAA,kBAAA,CACzD,CAAC,CAAA,CAIL,OAAO,CAAE,OAAA,CAAS0B,CAAAA,CAAO,MAAA,GAAW,CAAA,CAAG,MAAA,CAAAA,CAAO,CAChD,CAEA,WAAA,EAAqC,CACnC,OAAO,IAAA,CAAK,QACd,CAEA,UAAA,EAAmB,CACjB,IAAA,IAAWL,CAAAA,IAAW,IAAA,CAAK,eAAA,CAAgB,MAAA,EAAO,CAChDA,CAAAA,CAAQ,SAAQ,CAElB,IAAA,CAAK,eAAA,CAAgB,KAAA,EAAM,CAC3B,IAAA,CAAK,aAAA,CAAc,KAAA,GACrB,CAEQ,iBAAA,CAAkBrB,CAAAA,CAAeqB,CAAAA,CAA8B,CACrE,IAAA,CAAK,aAAA,CAAc,IAAIrB,CAAAA,CAAO,CAAE,QAAA,CAAU,KAAM,CAAC,CAAA,CAEjD,IAAM4B,CAAAA,CAAuBC,CAAAA,EAA8D,CACzF,IAAA,CAAK,aAAA,CAAc,GAAA,CAAI7B,CAAAA,CAAO,CAAE,QAAA,CAAU6B,EAAM,QAAA,CAAU,KAAA,CAAOA,CAAAA,CAAM,KAAA,EAAO,OAAQ,CAAC,EACzF,CAAA,CAECR,CAAAA,CAAgB,EAAA,CAAG,QAAA,CAAUO,CAAmB,EACnD,CACF,CAAA,CCpMO,IAAME,EAAN,KAA+B,CAA/B,WAAA,EAAA,CACL,IAAA,CAAQ,UAAA,CAAiC,GAAC,CAE1C,GAAA,CAAIC,EAAmC,CACrC,IAAA,CAAK,UAAA,CAAW,IAAA,CAAKA,CAAS,EAChC,CAEA,MAAM,iBAAiBC,CAAAA,CAAgE,CACrF,IAAIC,CAAAA,CAAkBD,CAAAA,CACtB,IAAA,IAAWE,CAAAA,IAAO,IAAA,CAAK,UAAA,CACjBA,CAAAA,CAAI,aAAA,GACND,CAAAA,CAAkB,MAAMC,CAAAA,CAAI,aAAA,CAAcD,CAAe,GAG7D,OAAOA,CACT,CAEA,MAAM,eAAA,CAAgBtB,CAAAA,CAAsC,CAC1D,MAAM,OAAA,CAAQ,GAAA,CACZ,IAAA,CAAK,UAAA,CACF,MAAA,CAAQuB,CAAAA,EAAQA,CAAAA,CAAI,YAAY,EAChC,GAAA,CAAKA,CAAAA,EAAQA,CAAAA,CAAI,YAAA,CAAcvB,CAAM,CAAC,CAC3C,EACF,CAEA,MAAM,UAAA,CAAWL,CAAAA,CAA6B,CAC5C,MAAM,OAAA,CAAQ,GAAA,CACZ,KAAK,UAAA,CACF,MAAA,CAAQ4B,CAAAA,EAAQA,CAAAA,CAAI,cAAc,CAAA,CAClC,GAAA,CAAKA,CAAAA,EAAQA,EAAI,cAAA,CAAgB5B,CAAK,CAAC,CAC5C,EACF,CACF,CAAA,CCpBO,IAAM6B,EAAN,KAAqB,CAC1B,WAAA,CACUC,CAAAA,CACAC,CAAAA,CACAC,CAAAA,CACR,CAHQ,IAAA,CAAA,aAAA,CAAAF,CAAAA,CACA,IAAA,CAAA,eAAA,CAAAC,CAAAA,CACA,IAAA,CAAA,cAAA,CAAAC,EACP,CAEH,MAAM,OAAA,CAAQN,EAAgCO,CAAAA,CAAwD,CACpG,IAAM3B,CAAAA,CAAW,IAAA,CAAK,eAAA,CAAgB,WAAA,EAAY,CAElD,MAAM,IAAA,CAAK,yBAAA,CAA0BA,CAAAA,CAAU2B,CAAO,CAAA,CAEtD,MAAM3B,CAAAA,CAAU,QAAO,CAEvB,IAAMH,CAAAA,CAAkB,MAAM,IAAA,CAAK,aAAA,CAAc,mBAAA,CAC/CG,CAAAA,CACA2B,CAAAA,CAAQ,6BACV,CAAA,CAEA,OAAA,MAAM,IAAA,CAAK,cAAA,CAAe,iBAAA,CAAkB,CAC1C,WAAYA,CAAAA,CAAQ,UAAA,CACpB,eAAA,CAAiBA,CAAAA,CAAQ,eAAA,CACzB,eAAA,CAAA9B,CAAAA,CACA,YAAA,CAAc,CACZ,KAAA,CAAOuB,CAAAA,CAAQ,aAAA,CACf,SAAA,CAAWA,CAAAA,CAAQ,iBAAA,CACnB,QAAA,CAAUA,CAAAA,CAAQ,gBACpB,CAAA,CACA,WAAA,CAAaA,CAAAA,CAAQ,WAAA,CACrB,QAAA,CAAUA,CAAAA,CAAQ,QACpB,CAAC,CAAA,CAEM,IAAA,CAAK,cAAA,CAAevB,CAAAA,CAAiB8B,CAAO,CACrD,CAEA,MAAc,0BAA0B3B,CAAAA,CAAiC2B,CAAAA,CAAgC,CACvG,GAAI,CAAC3B,CAAAA,CACH,MAAM,IAAIlB,CAAAA,CAAa,0BAAA,CAAA,qBAAyD,CAAA,CAGlF,GAAI6C,CAAAA,CAAQ,2BAAA,EAA+BA,CAAAA,CAAQ,6BAAA,CACjD,MAAM,IAAI7C,CAAAA,CAAa,mCAAmC,CAAA,CAG5D,GAAI6C,CAAAA,CAAQ,6BAAA,CAA+B,CACzC,IAAMC,CAAAA,CAAa,MAAM,IAAA,CAAK,eAAA,CAAgB,QAAA,EAAS,CACvD,GAAI,CAACA,CAAAA,CAAW,OAAA,CACd,MAAM,IAAI9C,CAAAA,CAAa8C,CAAAA,CAAW,MAAA,CAAO,CAAC,CAAA,CAAE,OAAA,CAAA,kBAAmC,CAEnF,CACF,CAEA,MAAc,cAAA,CACZ/B,CAAAA,CACA8B,EACwB,CACxB,GAAM,CAAE,YAAA,CAAA7B,CAAAA,CAAc,2BAAA,CAAA+B,CAAAA,CAA6B,6BAAA,CAAA5B,CAA8B,CAAA,CAAI0B,CAAAA,CAEjF5B,CAAAA,CAEJ,OAAI8B,CAAAA,CACF9B,CAAAA,CAAS,MAAM,KAAK,aAAA,CAAc,cAAA,CAAeF,CAAAA,CAAiBC,CAAY,CAAA,CACrEG,CAAAA,GACTF,CAAAA,CAAS,MAAM,IAAA,CAAK,aAAA,CAAc,kBAAA,CAAmBF,CAAAA,CAAiBC,CAAY,CAAA,CAAA,CAG7E,IAAA,CAAK,mBAAA,CAAoBC,CAAM,CACxC,CAEQ,mBAAA,CAAoBA,CAAAA,CAA4B,CACtD,OAAO,CACL,OAAA,CAASA,CAAAA,CAAO,aAAA,CAAc,MAAA,GAAW,WAAA,CACzC,eAAA,CAAiBA,CAAAA,CAAO,aAAA,CAAc,EAAA,CACtC,OAAQA,CAAAA,CAAO,aAAA,CAAc,MAC/B,CACF,CACF,CAAA,CCpEO,IAAM+B,CAAAA,CAAN,KAAqB,CAG1B,WAAA,CAAYC,CAAAA,CAAkB,uBAAA,CAAyB,CACrD,IAAA,CAAK,OAAA,CAAUA,EACjB,CAEA,MAAM,iBAAA,CACJX,CAAAA,CACoC,CACpC,GAAM,CAAE,UAAA,CAAAY,CAAAA,CAAY,WAAA,CAAAC,CAAY,CAAA,CAAIb,CAAAA,CAEpC,GAAI,CACF,IAAMc,CAAAA,CAAW,MAAM,KAAA,CAAM,CAAA,EAAG,IAAA,CAAK,OAAO,CAAA,uBAAA,CAAA,CAA2B,CACrE,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CACP,cAAA,CAAgB,kBAAA,CAChB,WAAA,CAAa,iBACf,CAAA,CACA,IAAA,CAAM,KAAK,SAAA,CAAU,CACnB,UAAA,CAAAF,CAAAA,CACA,WAAA,CAAa,CAAE,GAAGC,CAAAA,CAAa,iBAAA,CAAmB,MAAO,CAC3D,CAAC,CACH,CAAC,CAAA,CAED,GAAI,CAACC,CAAAA,CAAS,EAAA,CAAI,CAChB,IAAMC,CAAAA,CAAY,MAAMD,CAAAA,CAAS,IAAA,GAAO,KAAA,CAAM,KAAO,EAAC,CAAE,CAAA,CACxD,MAAM,IAAIpD,CAAAA,CACRqD,EAAU,KAAA,EAAS,CAAA,oBAAA,EAAuBD,CAAAA,CAAS,MAAM,CAAA,CAAA,CAAA,qBAE3D,CACF,CAEA,IAAME,CAAAA,CAAO,MAAMF,CAAAA,CAAS,IAAA,EAAK,CAEjC,GAAI,CAACE,CAAAA,CAAK,cAAgB,CAACA,CAAAA,CAAK,eAAA,CAC9B,MAAM,IAAItD,CAAAA,CACR,4DAAA,CAAA,qBAEF,CAAA,CAGF,OAAO,CACL,eAAA,CAAiBsD,CAAAA,CAAK,eAAA,CACtB,YAAA,CAAcA,CAAAA,CAAK,YAAA,CACnB,iBAAkBA,CAAAA,CAAK,gBACzB,CACF,CAAA,MAAS1C,CAAAA,CAAO,CACd,MAAIA,CAAAA,YAAiBZ,CAAAA,CACbY,CAAAA,CAEF,IAAIZ,CAAAA,CACRY,CAAAA,YAAiB,KAAA,CAAQA,CAAAA,CAAM,OAAA,CAAU,8CAE3C,CACF,CACF,CAEA,MAAM,iBAAA,CAAkB0B,CAAAA,CAAkD,CACxE,GAAI,CACF,IAAMc,CAAAA,CAAW,MAAM,KAAA,CAAM,CAAA,EAAG,IAAA,CAAK,OAAO,CAAA,uBAAA,CAAA,CAA2B,CACrE,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CACP,cAAA,CAAgB,kBAAA,CAChB,iBAAA,CAAmB,iBACrB,CAAA,CACA,IAAA,CAAM,IAAA,CAAK,SAAA,CAAU,CACnB,UAAA,CAAYd,CAAAA,CAAQ,UAAA,CACpB,gBAAiBA,CAAAA,CAAQ,eAAA,CACzB,eAAA,CAAiBA,CAAAA,CAAQ,eAAA,CACzB,YAAA,CAAcA,CAAAA,CAAQ,YAAA,CACtB,WAAA,CAAaA,CAAAA,CAAQ,WAAA,CACrB,QAAA,CAAUA,CAAAA,CAAQ,QACpB,CAAC,CACH,CAAC,CAAA,CAED,GAAI,CAACc,CAAAA,CAAS,EAAA,CAAI,CAChB,IAAMC,CAAAA,CAAY,MAAMD,CAAAA,CAAS,IAAA,EAAK,CAAE,KAAA,CAAM,KAAO,EAAC,CAAE,EACxD,MAAM,IAAIpD,CAAAA,CACRqD,CAAAA,CAAU,KAAA,EAAS,CAAA,oBAAA,EAAuBD,CAAAA,CAAS,MAAM,CAAA,CAAA,CAAA,qBAE3D,CACF,CACF,CAAA,MAASxC,CAAAA,CAAO,CACd,MAAIA,CAAAA,YAAiBZ,EACbY,CAAAA,CAEF,IAAIZ,CAAAA,CACRY,CAAAA,YAAiB,KAAA,CAAQA,CAAAA,CAAM,OAAA,CAAU,wBAAA,CAAA,qBAE3C,CACF,CACF,CACF,EChGO,IAAM2C,CAAAA,CAAN,MAAMA,CAAc,CAkBzB,WAAA,CAAY/B,CAAAA,CAAuB,CAVnC,IAAA,CAAQ,aAAA,CAAsC,IAAA,CAC9C,IAAA,CAAQ,eAAA,CAA0C,IAAA,CAClD,IAAA,CAAQ,cAAA,CAAwC,IAAA,CAEhD,IAAA,CAAQ,2BAAA,CAAuC,KAAA,CAC/C,IAAA,CAAQ,8BAAyC,KAAA,CAEjD,IAAA,CAAQ,YAAA,CAA8B,IAAA,CACtC,IAAA,CAAQ,eAAA,CAAiC,IAAA,CAGvC,IAAA,CAAK,MAAA,CAASA,CAAAA,CACd,IAAA,CAAK,cAAA,CAAiB,IAAIwB,CAAAA,CAC1B,IAAA,CAAK,iBAAA,CAAoB,IAAIZ,EAC/B,CAEA,MAAM,UAAA,EAA4B,CAChC,IAAA,CAAK,6BAAA,EAA8B,CAEnC,GAAM,CAAE,YAAA,CAAApB,CAAAA,CAAc,eAAA,CAAAwC,CAAgB,CAAA,CACpC,MAAM,IAAA,CAAK,eAAe,iBAAA,CAAkB,CAC1C,UAAA,CAAY,IAAA,CAAK,MAAA,CAAO,UAAA,CACxB,WAAA,CAAa,IAAA,CAAK,MAAA,CAAO,WAC3B,CAAC,CAAA,CAEH,IAAA,CAAK,YAAA,CAAexC,CAAAA,CACpB,IAAA,CAAK,gBAAkBwC,CAAAA,CAEvB,IAAM1C,CAAAA,CAAS,MAAM2C,mBAAAA,CAAWF,CAAAA,CAAc,sBAAsB,CAAA,CAEpE,GAAI,CAACzC,CAAAA,CACH,MAAM,IAAId,CAAAA,CACR,uBAAA,CAAA,qBAEF,CAAA,CAGF,KAAK,aAAA,CAAgB,IAAIa,CAAAA,CAAcC,CAAM,CAAA,CAC7C,IAAA,CAAK,eAAA,CAAkB,IAAIS,CAAAA,CACzBT,CAAAA,CACA,IAAA,CAAK,MAAA,CACLE,CACF,CAAA,CACA,IAAA,CAAK,cAAA,CAAiB,IAAIyB,CAAAA,CACxB,IAAA,CAAK,aAAA,CACL,IAAA,CAAK,eAAA,CACL,IAAA,CAAK,cACP,EACF,CAEA,MAAM,cAAA,CAAeH,CAAAA,CAAwD,CAC3E,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAE7B,IAAIC,CAAAA,CACF,MAAM,IAAA,CAAK,iBAAA,CAAkB,gBAAA,CAAiBD,CAAO,CAAA,CAEvD,GAAI,CACF,IAAMoB,CAAAA,CAAgB,MAAM,IAAA,CAAK,cAAA,CAAgB,OAAA,CAC/CnB,CAAAA,CACA,CACE,UAAA,CAAY,IAAA,CAAK,MAAA,CAAO,UAAA,CACxB,eAAA,CAAiB,IAAA,CAAK,eAAA,CACtB,YAAA,CAAc,IAAA,CAAK,YAAA,CACnB,2BAAA,CAA6B,IAAA,CAAK,2BAAA,CAClC,6BAAA,CAA+B,IAAA,CAAK,6BACtC,CACF,CAAA,CAEA,OAAA,MAAM,IAAA,CAAK,iBAAA,CAAkB,eAAA,CAAgBmB,CAAa,CAAA,CAEnDA,CACT,CAAA,MAAS9C,CAAAA,CAAO,CACd,MAAA,MAAM,IAAA,CAAK,iBAAA,CAAkB,UAAA,CAAWA,CAAc,EAChD,IAAA,CAAK,kBAAA,CAAmBA,CAAK,CACrC,CACF,CAEA,MAAM,gBAAA,CAAiBa,EAAiC,CACtD,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAC7B,IAAA,CAAK,eAAA,CAAiB,mBAAA,CAAoBA,CAAQ,CAAA,CAClD,IAAA,CAAK,2BAAA,CAA8B,KACrC,CAEA,MAAM,eAAA,CAAgBA,CAAAA,CAAiC,CACrD,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAC7B,IAAA,CAAK,eAAA,CAAiB,sBAAA,CAAuBA,CAAQ,CAAA,CACrD,IAAA,CAAK,6BAAA,CAAgC,KACvC,CAEA,MAAM,eAAA,CAAgBA,CAAAA,CAAiC,CACrD,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAC7B,IAAA,CAAK,eAAA,CAAiB,sBAAA,CAAuBA,CAAQ,CAAA,CACrD,IAAA,CAAK,6BAAA,CAAgC,KACvC,CAEA,MAAM,YAAA,CAAaA,CAAAA,CAAiC,CAClD,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAC7B,IAAA,CAAK,eAAA,CAAiB,mBAAA,CAAoBA,CAAQ,CAAA,CAClD,IAAA,CAAK,6BAAA,CAAgC,KACvC,CAEA,MAAM,YAAA,CACJA,CAAAA,CACAG,CAAAA,CACe,CACf,MAAM,IAAA,CAAK,iBAAA,EAAkB,CAC7B,IAAA,CAAK,eAAA,CAAiB,oBAAoBH,CAAAA,CAAUG,CAAI,CAAA,CACxD,IAAA,CAAK,6BAAA,CAAgC,KACvC,CAEA,YAAA,CAAaS,CAAAA,CAAmC,CAC9C,IAAA,CAAK,iBAAA,CAAkB,GAAA,CAAIA,CAAS,EACtC,CAEA,MAAc,iBAAA,EAAmC,CAC1C,IAAA,CAAK,aAAA,EACR,MAAM,IAAA,CAAK,UAAA,GAEf,CAEQ,6BAAA,EAAsC,CAC5C,GAAM,CAAE,MAAA,CAAAsB,CAAAA,CAAQ,QAAA,CAAAC,EAAU,UAAA,CAAAC,CAAW,CAAA,CAAI,IAAA,CAAK,MAAA,CAAO,WAAA,CAErD,GAAI,CAACD,CAAAA,CACH,MAAM,IAAIvD,CAAAA,CAAgB,sBAAA,CAAwB,UAAU,CAAA,CAG9D,IAAMyD,EAAoBF,CAAAA,CAAS,WAAA,EAAY,CAEzCG,CAAAA,CAAgB,IAAA,CAAK,OAAA,CAAQJ,CAAAA,CAAQG,CAAAA,CAAmB,QAAQ,CAAA,CAEtE,GAAIC,CAAAA,CAAc,MAAA,EAAO,EAAKA,CAAAA,CAAc,UAAA,EAAW,CACrD,MAAM,IAAI1D,CAAAA,CAAgB,+BAAA,CAAiC,QAAQ,CAAA,CAGrE,GAAIwD,CAAAA,GAAe,MAAA,CAAW,CAC5B,IAAMG,CAAAA,CAAmB,IAAA,CAAK,OAAA,CAAQH,CAAAA,CAAYC,CAAAA,CAAmB,YAAY,EAEjF,GAAIE,CAAAA,CAAiB,UAAA,EAAW,CAC9B,MAAM,IAAI3D,CAAAA,CAAgB,+BAAA,CAAiC,YAAY,CAAA,CAGzE,GAAI2D,CAAAA,CAAiB,WAAA,CAAYD,CAAa,CAAA,CAC5C,MAAM,IAAI1D,CAAAA,CAAgB,6CAAA,CAA+C,YAAY,CAEzF,CACF,CAEQ,OAAA,CAAQ4D,CAAAA,CAAeL,CAAAA,CAAkBM,CAAAA,CAA0B,CACzE,GAAI,CACF,OAAOC,aAAAA,CAAM,WAAA,CAAYF,EAAOL,CAAQ,CAC1C,CAAA,KAAQ,CACN,MAAM,IAAIvD,CAAAA,CACR,CAAA,EAAG6D,CAAS,CAAA,uEAAA,CAAA,CACZA,CACF,CACF,CACF,CAEQ,kBAAA,CAAmBtD,CAAAA,CAAmB,CAC5C,OAAIA,CAAAA,YAAiBZ,CAAAA,CACZY,CAAAA,CAEF,IAAIJ,CAAAA,CAAaI,CAAAA,CAAM,OAAA,EAAW,gBAAA,CAAkBA,CAAAA,CAAM,IAAI,CACvE,CACF,CAAA,CA7Ka2C,CAAAA,CACa,sBAAA,CACtB,6GAAA,KAFSa,CAAAA,CAANb,EClBA,IAAMc,CAAAA,CAAN,KAAoB,CACzB,kBAAA,CAAmBC,CAAAA,CAA6B,CAC9C,IAAMC,CAAAA,CAAUD,CAAAA,CAAW,OAAA,CAAQ,KAAA,CAAO,EAAE,CAAA,CAE5C,GAAIC,CAAAA,CAAQ,MAAA,CAAS,EAAA,EAAMA,CAAAA,CAAQ,MAAA,CAAS,EAAA,CAC1C,OAAO,MAAA,CAGT,IAAIC,CAAAA,CAAM,CAAA,CACNC,CAAAA,CAAS,KAAA,CAEb,IAAA,IAASC,CAAAA,CAAIH,CAAAA,CAAQ,OAAS,CAAA,CAAGG,CAAAA,EAAK,CAAA,CAAGA,CAAAA,EAAAA,CAAK,CAC5C,IAAIC,CAAAA,CAAQ,QAAA,CAASJ,EAAQG,CAAC,CAAA,CAAG,EAAE,CAAA,CAE/BD,CAAAA,GACFE,CAAAA,EAAS,CAAA,CACLA,CAAAA,CAAQ,IACVA,CAAAA,EAAS,CAAA,CAAA,CAAA,CAIbH,CAAAA,EAAOG,CAAAA,CACPF,CAAAA,CAAS,CAACA,EACZ,CAEA,OAAOD,CAAAA,CAAM,EAAA,GAAO,CACtB,CAEA,cAAA,CAAeF,CAAAA,CAA4B,CACzC,IAAMC,CAAAA,CAAUD,CAAAA,CAAW,OAAA,CAAQ,KAAA,CAAO,EAAE,CAAA,CAE5C,OAAI,IAAA,CAAK,IAAA,CAAKC,CAAO,CAAA,CAAU,MAAA,CAC3B,SAAA,CAAU,IAAA,CAAKA,CAAO,CAAA,CAAU,aAChC,QAAA,CAAS,IAAA,CAAKA,CAAO,CAAA,CAAU,MAAA,CAC/B,aAAA,CAAc,IAAA,CAAKA,CAAO,CAAA,CAAU,UAAA,CAEjC,SACT,CAEA,cAAA,CAAeK,CAAAA,CAAeC,CAAAA,CAAuB,CACnD,IAAMC,CAAAA,CAAM,IAAI,IAAA,CACVC,CAAAA,CAAcD,CAAAA,CAAI,WAAA,EAAY,CAC9BE,CAAAA,CAAeF,CAAAA,CAAI,QAAA,EAAS,CAAI,CAAA,CAEtC,GAAIF,CAAAA,CAAQ,CAAA,EAAKA,CAAAA,CAAQ,GACvB,OAAO,MAAA,CAGT,IAAMK,CAAAA,CAAWJ,CAAAA,CAAO,GAAA,CAAM,GAAA,CAAOA,CAAAA,CAAOA,CAAAA,CAM5C,OAJI,EAAAI,CAAAA,CAAWF,CAAAA,EAIXE,CAAAA,GAAaF,CAAAA,EAAeH,CAAAA,CAAQI,EAK1C,CAEA,WAAA,CAAYE,CAAAA,CAAaC,CAAAA,CAAmB,SAAA,CAAoB,CAC9D,IAAMZ,CAAAA,CAAUW,CAAAA,CAAI,OAAA,CAAQ,KAAA,CAAO,EAAE,CAAA,CAErC,OAAIC,CAAAA,GAAa,MAAA,CACRZ,EAAQ,MAAA,GAAW,CAAA,CAGrBA,CAAAA,CAAQ,MAAA,GAAW,CAAA,EAAKA,CAAAA,CAAQ,MAAA,GAAW,CACpD,CAEA,WAAA,CACED,CAAAA,CACAc,CAAAA,CACAC,CAAAA,CACAH,CAAAA,CACgB,CAChB,IAAMC,EAAW,IAAA,CAAK,cAAA,CAAeb,CAAU,CAAA,CAE/C,OAAO,CACL,MAAA,CAAQ,CACN,QAAS,IAAA,CAAK,kBAAA,CAAmBA,CAAU,CAAA,CAC3C,QAAA,CAAUa,CACZ,CAAA,CACA,MAAA,CAAQ,CACN,OAAA,CAAS,IAAA,CAAK,cAAA,CAAeC,CAAAA,CAAaC,CAAU,CAAA,CACpD,KAAA,CAAOD,CAAAA,CACP,IAAA,CAAMC,CACR,CAAA,CACA,GAAA,CAAK,CACH,OAAA,CAAS,IAAA,CAAK,WAAA,CAAYH,EAAKC,CAAQ,CAAA,CACvC,MAAA,CAAQD,CAAAA,CAAI,OAAA,CAAQ,KAAA,CAAO,EAAE,CAAA,CAAE,MACjC,CACF,CACF,CACF,ECjGO,IAAMI,CAAAA,CAAN,KAAqB,CAC1B,OAAO,kBAAA,CAAmBC,CAAAA,CAAuB,CAC/C,OAAOA,CAAAA,CAAM,OAAA,CAAQ,KAAA,CAAO,EAAE,CAChC,CAEA,OAAO,gBAAA,CAAiBA,CAAAA,CAAuB,CAE7C,OADgB,KAAK,kBAAA,CAAmBA,CAAK,CAAA,CAC9B,OAAA,CAAQ,UAAA,CAAY,KAAK,CAAA,CAAE,IAAA,EAC5C,CAEA,OAAO,WAAA,CAAYA,CAAAA,CAAuB,CACxC,OAAOA,CAAAA,CAAM,OAAA,CAAQ,MAAO,EAAE,CAAA,CAAE,KAAA,CAAM,CAAA,CAAG,CAAC,CAC5C,CAEA,OAAO,cAAA,CAAeA,CAAAA,CAAuD,CAC3E,IAAMhB,CAAAA,CAAUgB,CAAAA,CAAM,OAAA,CAAQ,KAAA,CAAO,EAAE,CAAA,CAEvC,OAAIhB,CAAAA,CAAQ,MAAA,GAAW,CAAA,CACd,CACL,KAAA,CAAO,QAAA,CAASA,CAAAA,CAAQ,KAAA,CAAM,CAAA,CAAG,CAAC,CAAA,CAAG,EAAE,CAAA,CACvC,IAAA,CAAM,SAASA,CAAAA,CAAQ,KAAA,CAAM,CAAA,CAAG,CAAC,CAAA,CAAG,EAAE,CACxC,CAAA,CACSA,CAAAA,CAAQ,MAAA,GAAW,CAAA,CACrB,CACL,KAAA,CAAO,QAAA,CAASA,CAAAA,CAAQ,KAAA,CAAM,EAAG,CAAC,CAAA,CAAG,EAAE,CAAA,CACvC,IAAA,CAAM,QAAA,CAASA,CAAAA,CAAQ,KAAA,CAAM,EAAG,CAAC,CAAA,CAAG,EAAE,CACxC,CAAA,CAGK,IACT,CACF,MCGaiB,EAAAA,CAAU","file":"index.cjs","sourcesContent":["import type { ErrorDetails } from '../types';\nimport { ErrorCode } from '../types';\n\nexport class VerapayError extends Error {\n public readonly code: ErrorCode;\n public readonly details: ErrorDetails;\n\n constructor(\n message: string,\n code: ErrorCode = ErrorCode.PAYMENT_FAILED,\n details?: Partial<ErrorDetails>\n ) {\n super(message);\n this.name = 'VerapayError';\n this.code = code;\n this.details = {\n code,\n message,\n formattedMessage: this.formatMessage(message, code),\n ...details,\n };\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, VerapayError);\n }\n }\n\n private formatMessage(message: string, code: ErrorCode): string {\n const messageMap: Record<ErrorCode, string> = {\n [ErrorCode.VALIDATION_ERROR]:\n 'Please check your payment information and try again.',\n [ErrorCode.PAYMENT_FAILED]:\n 'Your payment could not be processed. Please try again.',\n [ErrorCode.AUTHENTICATION_FAILED]:\n 'Payment authentication failed. Please try again.',\n [ErrorCode.NETWORK_ERROR]:\n 'Network error. Please check your connection and try again.',\n [ErrorCode.STRIPE_ERROR]:\n 'Payment service error. Please try again later.',\n [ErrorCode.CONFIGURATION_ERROR]:\n 'Configuration error. Please contact support.',\n [ErrorCode.CARD_DECLINED]:\n 'Your card was declined. Please use a different payment method.',\n [ErrorCode.INSUFFICIENT_FUNDS]:\n 'Insufficient funds. Please use a different payment method.',\n [ErrorCode.EXPIRED_CARD]:\n 'Your card has expired. Please use a different payment method.',\n };\n\n return messageMap[code] || message;\n }\n\n toJSON() {\n return {\n name: this.name,\n code: this.code,\n message: this.message,\n details: this.details,\n };\n }\n}\n","import { VerapayError } from './verapay-error';\nimport { ErrorCode } from '../types';\n\nexport class ValidationError extends VerapayError {\n constructor(message: string, field?: string, metadata?: Record<string, any>) {\n super(message, ErrorCode.VALIDATION_ERROR, {\n field,\n metadata,\n });\n this.name = 'ValidationError';\n }\n}\n","import { VerapayError } from './verapay-error';\nimport { ErrorCode } from '../types';\n\nexport class PaymentError extends VerapayError {\n constructor(\n message: string,\n stripeCode?: string,\n metadata?: Record<string, any>\n ) {\n const code = PaymentError.mapStripeCode(stripeCode);\n super(message, code, {\n stripeCode,\n metadata,\n });\n this.name = 'PaymentError';\n }\n\n private static mapStripeCode(stripeCode?: string): ErrorCode {\n if (!stripeCode) return ErrorCode.PAYMENT_FAILED;\n\n const codeMap: Record<string, ErrorCode> = {\n card_declined: ErrorCode.CARD_DECLINED,\n insufficient_funds: ErrorCode.INSUFFICIENT_FUNDS,\n expired_card: ErrorCode.EXPIRED_CARD,\n incorrect_cvc: ErrorCode.VALIDATION_ERROR,\n processing_error: ErrorCode.PAYMENT_FAILED,\n authentication_failed: ErrorCode.AUTHENTICATION_FAILED,\n };\n\n return codeMap[stripeCode] || ErrorCode.PAYMENT_FAILED;\n }\n}\n","import type { ErrorDetails } from '../types';\n\nexport class ErrorFormatter {\n static formatForUser(error: Error | ErrorDetails): string {\n if ('formattedMessage' in error) {\n return error.formattedMessage;\n }\n if (\n 'details' in error &&\n error.details &&\n typeof error.details === 'object' &&\n 'formattedMessage' in error.details &&\n typeof error.details.formattedMessage === 'string'\n ) {\n return error.details.formattedMessage;\n }\n return 'An unexpected error occurred. Please try again.';\n }\n\n static formatForDeveloper(error: Error | ErrorDetails): string {\n if ('code' in error && 'message' in error) {\n return `[${error.code}] ${error.message}`;\n }\n return error.message || 'Unknown error';\n }\n\n static toJSON(error: Error | ErrorDetails): Record<string, any> {\n if ('toJSON' in error && typeof error.toJSON === 'function') {\n return error.toJSON();\n }\n\n return {\n name: (error as Error).name || 'Error',\n message: error.message,\n ...('code' in error && { code: error.code }),\n ...('details' in error && { details: error.details }),\n };\n }\n}\n","import type { PaymentIntent, Stripe, StripeElements } from '@stripe/stripe-js';\nimport { PaymentError } from '../errors';\n\nexport class StripeAdapter {\n constructor(private stripe: Stripe) {}\n\n async confirmPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmPayment({\n clientSecret,\n confirmParams: {\n payment_method: paymentMethodId,\n return_url: window.location.href,\n },\n redirect: 'if_required',\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async confirmCardPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmCardPayment(clientSecret, {\n payment_method: paymentMethodId,\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async createPaymentMethod(\n elements: StripeElements,\n isUsingIndividualFormElements: boolean = false\n ): Promise<string> {\n let result;\n\n if (!isUsingIndividualFormElements) {\n result = await this.stripe.createPaymentMethod({\n elements,\n });\n } else {\n // @ts-ignore - Stripe types don't include mode parameter for getElement\n const addressElement = await elements.getElement('address', { mode: 'billing' })!.getValue();\n const address = addressElement!.value;\n\n result = await this.stripe.createPaymentMethod({\n type: 'card',\n card: elements.getElement('cardNumber')!,\n billing_details: {\n name: address.name,\n address: {\n ...address.address,\n line2: address.address.line2 ?? undefined,\n },\n },\n });\n }\n\n if (result.error || !result.paymentMethod) {\n throw new PaymentError(\n result.error?.message || 'Failed to create payment method',\n result.error?.code\n );\n }\n\n return result.paymentMethod.id;\n }\n}\n","import type {\n Stripe,\n StripeElements,\n StripeElement,\n StripePaymentElement,\n StripeCardNumberElement,\n} from '@stripe/stripe-js';\nimport type { VerapayConfig, ValidationError, ValidationResult } from '../types';\nimport { VerapayError, ErrorCode } from '../errors';\n\ntype ElementState = { complete: boolean; error?: string }\n\nconst DEFAULT_CARD_ELEMENT_CONFIG = {\n showIcon: true,\n iconStyle: 'solid' as const,\n placeholders: {\n cardNumber: '1234 1234 1234 1234',\n cardExpiry: 'MM / YY - TESTING',\n cardCvc: 'CVC',\n },\n style: {\n base: {\n color: '#333333',\n fontFamily: 'system-ui, -apple-system, sans-serif',\n fontSize: '16px',\n '::placeholder': { color: '#aab7c4' },\n },\n complete: {\n color: '#333333',\n },\n empty: {},\n invalid: {\n color: '#df1b41',\n },\n },\n}\n\nconst FIELD_LABELS: Record<string, string> = {\n cardNumber: 'Card number',\n cardExpiry: 'Expiry date',\n cardCvc: 'CVC',\n address: 'Address',\n}\n\nexport class ElementsManager {\n private elements: StripeElements | null = null;\n private mountedElements: Map<string, StripeElement> = new Map();\n private elementStates: Map<string, ElementState> = new Map();\n\n constructor(\n private stripe: Stripe,\n private config: VerapayConfig,\n private clientSecret: string\n ) {\n if (!clientSecret) {\n throw new VerapayError(\n 'Client secret not initialized',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n mountPaymentElement(selector: string): void {\n if (!this.elements) {\n const elementsConfig = {\n clientSecret: this.clientSecret,\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n };\n\n this.elements = this.stripe.elements(elementsConfig);\n }\n\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.elements.create('payment', {\n layout: 'tabs',\n }) as StripePaymentElement;\n\n element.mount(selector);\n this.mountedElements.set('payment', element);\n }\n\n mountCardNumberElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardNumber', this.cardElementOptions('cardNumber'));\n }\n\n mountCardExpiryElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardExpiry', this.cardElementOptions('cardExpiry'));\n }\n\n mountCardCvcElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardCvc', this.cardElementOptions('cardCvc'));\n }\n\n mountAddressElement(selector: string, mode: 'billing' | 'shipping'): void {\n this.mountIndividualFormElement(selector, 'address', { mode });\n }\n\n private cardElementOptions(fieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc'): Record<string, unknown> {\n const { elementsConfig } = this.config;\n const options: Record<string, unknown> = {\n placeholder: elementsConfig?.placeholders?.[fieldType] ?? DEFAULT_CARD_ELEMENT_CONFIG.placeholders[fieldType],\n style: {\n base: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.base, ...elementsConfig?.style?.base },\n complete: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.complete, ...elementsConfig?.style?.complete },\n empty: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.empty, ...elementsConfig?.style?.empty },\n invalid: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.invalid, ...elementsConfig?.style?.invalid },\n },\n };\n\n if (fieldType === 'cardNumber') {\n options.showIcon = elementsConfig?.showIcon ?? DEFAULT_CARD_ELEMENT_CONFIG.showIcon;\n options.iconStyle = elementsConfig?.iconStyle ?? DEFAULT_CARD_ELEMENT_CONFIG.iconStyle;\n }\n\n return options;\n }\n\n private mountIndividualFormElement(selector: string, formFieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc' | 'address', options?: Record<string, unknown>) {\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.createIndividualFormElement(formFieldType, options) as StripeCardNumberElement;\n element.mount(selector);\n\n this.mountedElements.set(formFieldType, element);\n this.trackElementState(formFieldType, element);\n }\n\n private createIndividualFormElement(\n formFieldType: any,\n options?: Record<string, unknown>\n ): StripeElement {\n if (!this.elements) {\n // For individual card elements, don't pass clientSecret\n // It's only needed when creating Payment Element or confirming payment\n this.elements = this.stripe.elements({\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n });\n }\n\n return this.elements.create(formFieldType, options);\n }\n\n async validate(): Promise<ValidationResult> {\n const errors: ValidationError[] = []\n\n for (const [field, state] of this.elementStates.entries()) {\n if (!state.complete) {\n errors.push({\n field,\n message: state.error ?? `${FIELD_LABELS[field] ?? field} failed validation`,\n })\n }\n }\n\n return { isValid: errors.length === 0, errors }\n }\n\n getElements(): StripeElements | null {\n return this.elements;\n }\n\n unmountAll(): void {\n for (const element of this.mountedElements.values()) {\n element.unmount();\n }\n this.mountedElements.clear();\n this.elementStates.clear();\n }\n\n private trackElementState(field: string, element: StripeElement): void {\n this.elementStates.set(field, { complete: false })\n\n const handleElementChange = (event: { complete: boolean; error?: { message: string } }) => {\n this.elementStates.set(field, { complete: event.complete, error: event.error?.message })\n };\n\n (element as any).on('change', handleElementChange)\n }\n}\n","import type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport type { PaymentExtension } from '../extensions'\n\nexport class PaymentExtensionsManager {\n private extensions: PaymentExtension[] = []\n\n add(extension: PaymentExtension): void {\n this.extensions.push(extension)\n }\n\n async runBeforePayment(request: ProcessPaymentRequest): Promise<ProcessPaymentRequest> {\n let modifiedRequest = request\n for (const ext of this.extensions) {\n if (ext.beforePayment) {\n modifiedRequest = await ext.beforePayment(modifiedRequest)\n }\n }\n return modifiedRequest\n }\n\n async runAfterPayment(result: PaymentResult): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.afterPayment)\n .map((ext) => ext.afterPayment!(result)),\n )\n }\n\n async runOnError(error: Error): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.onPaymentError)\n .map((ext) => ext.onPaymentError!(error)),\n )\n }\n}\n","import { StripeAdapter } from '../client/stripe-adapter'\nimport { ElementsManager } from '../client/elements-manager'\nimport { ErrorCode, VerapayError } from '../errors'\nimport { VerapayService } from './verapay-service'\nimport type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport { StripeElements } from '@stripe/stripe-js';\n\nexport interface ProcessPaymentContext {\n merchantId: string\n paymentIntentId: string\n clientSecret: string\n isUsingStripePaymentElement: boolean\n isUsingIndividualFormElements: boolean\n}\n\nexport class PaymentService {\n constructor(\n private stripeAdapter: StripeAdapter,\n private elementsManager: ElementsManager,\n private verapayService: VerapayService,\n ) {}\n\n async process(request: ProcessPaymentRequest, context: ProcessPaymentContext): Promise<PaymentResult> {\n const elements = this.elementsManager.getElements()\n\n await this.validatePaymentCanProceed(elements, context);\n\n await elements!.submit()\n\n const paymentMethodId = await this.stripeAdapter.createPaymentMethod(\n elements!,\n context.isUsingIndividualFormElements,\n )\n\n await this.verapayService.processPrePayment({\n merchantId: context.merchantId,\n paymentIntentId: context.paymentIntentId,\n paymentMethodId,\n customerData: {\n email: request.customerEmail,\n firstName: request.customerFirstName,\n lastName: request.customerLastName,\n },\n description: request.description,\n metadata: request.metadata,\n })\n\n return this.confirmPayment(paymentMethodId, context)\n }\n\n private async validatePaymentCanProceed(elements: StripeElements | null, context: ProcessPaymentContext) {\n if (!elements) {\n throw new VerapayError('Payment form not mounted', ErrorCode.CONFIGURATION_ERROR)\n }\n\n if (context.isUsingStripePaymentElement && context.isUsingIndividualFormElements) {\n throw new VerapayError('Both forms of payment form in use');\n }\n\n if (context.isUsingIndividualFormElements) {\n const validation = await this.elementsManager.validate()\n if (!validation.isValid) {\n throw new VerapayError(validation.errors[0].message, ErrorCode.VALIDATION_ERROR)\n }\n }\n }\n\n private async confirmPayment(\n paymentMethodId: string,\n context: ProcessPaymentContext,\n ): Promise<PaymentResult> {\n const { clientSecret, isUsingStripePaymentElement, isUsingIndividualFormElements } = context\n\n let result\n\n if (isUsingStripePaymentElement) {\n result = await this.stripeAdapter.confirmPayment(paymentMethodId, clientSecret)\n } else if (isUsingIndividualFormElements) {\n result = await this.stripeAdapter.confirmCardPayment(paymentMethodId, clientSecret)\n }\n\n return this.formatPaymentResult(result)\n }\n\n private formatPaymentResult(result: any): PaymentResult {\n return {\n success: result.paymentIntent.status === 'succeeded',\n paymentIntentId: result.paymentIntent.id,\n status: result.paymentIntent.status,\n }\n }\n}\n","import { ErrorCode, VerapayError } from '../errors';\nimport { PaymentData } from '../types';\n\nexport interface InitialisePaymentRequest {\n merchantId: string;\n paymentData: PaymentData;\n}\n\nexport interface InitialisePaymentResponse {\n paymentIntentId: string;\n clientSecret: string;\n connectAccountId: string;\n}\n\nexport interface ProcessPrePaymentRequest {\n merchantId: string;\n paymentIntentId: string;\n paymentMethodId: string;\n customerData: Record<string, any>;\n description?: string;\n metadata?: Record<string, string>;\n}\n\nexport class VerapayService {\n private readonly baseUrl: string;\n\n constructor(baseUrl: string = 'http://localhost:3333') {\n this.baseUrl = baseUrl;\n }\n\n async initialisePayment(\n request: InitialisePaymentRequest\n ): Promise<InitialisePaymentResponse> {\n const { merchantId, paymentData } = request;\n\n try {\n const response = await fetch(`${this.baseUrl}/api/initialise-payment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-api-key': 'example.api.key',\n },\n body: JSON.stringify({\n merchantId,\n paymentData: { ...paymentData, paymentMethodType: 'card' },\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const data = await response.json();\n\n if (!data.clientSecret || !data.paymentIntentId) {\n throw new VerapayError(\n 'Missing clientSecret or paymentIntentId in server response',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n return {\n paymentIntentId: data.paymentIntentId,\n clientSecret: data.clientSecret,\n connectAccountId: data.connectAccountId,\n };\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n async processPrePayment(request: ProcessPrePaymentRequest): Promise<void> {\n try {\n const response = await fetch(`${this.baseUrl}/api/process-prepayment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-forwarded-for': 'example.ip.addr',\n },\n body: JSON.stringify({\n merchantId: request.merchantId,\n paymentIntentId: request.paymentIntentId,\n paymentMethodId: request.paymentMethodId,\n customerData: request.customerData,\n description: request.description,\n metadata: request.metadata,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n}\n","import { loadStripe } from '@stripe/stripe-js';\nimport { Money } from 'ts-money';\nimport { StripeAdapter } from './stripe-adapter';\nimport { ElementsManager } from './elements-manager';\nimport type { PaymentExtension } from '../extensions';\nimport { PaymentExtensionsManager } from './payment-extensions-manager';\nimport { PaymentService } from '../services/payment-service';\nimport {\n ErrorCode,\n VerapayError,\n PaymentError,\n ValidationError,\n} from '../errors';\nimport { VerapayService } from '../services/verapay-service';\nimport type {\n VerapayConfig,\n ProcessPaymentRequest,\n PaymentResult,\n} from '../types';\n\nexport class VerapayClient {\n private static readonly STRIPE_PUBLISHABLE_KEY =\n 'pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq';\n\n private config: VerapayConfig;\n private verapayService: VerapayService;\n private extensionsManager: PaymentExtensionsManager;\n\n private stripeAdapter: StripeAdapter | null = null;\n private elementsManager: ElementsManager | null = null;\n private paymentService: PaymentService | null = null;\n\n private isUsingStripePaymentElement: boolean = false;\n private isUsingIndividualFormElements: boolean = false;\n\n private clientSecret: string | null = null;\n private paymentIntentId: string | null = null;\n\n constructor(config: VerapayConfig) {\n this.config = config;\n this.verapayService = new VerapayService();\n this.extensionsManager = new PaymentExtensionsManager();\n }\n\n async initialize(): Promise<void> {\n this.validatePaymentInitialisation()\n\n const { clientSecret, paymentIntentId } =\n await this.verapayService.initialisePayment({\n merchantId: this.config.merchantId,\n paymentData: this.config.paymentData\n });\n\n this.clientSecret = clientSecret;\n this.paymentIntentId = paymentIntentId;\n\n const stripe = await loadStripe(VerapayClient.STRIPE_PUBLISHABLE_KEY);\n\n if (!stripe) {\n throw new VerapayError(\n 'Failed to load Stripe',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n this.stripeAdapter = new StripeAdapter(stripe);\n this.elementsManager = new ElementsManager(\n stripe,\n this.config,\n clientSecret\n );\n this.paymentService = new PaymentService(\n this.stripeAdapter,\n this.elementsManager,\n this.verapayService\n );\n }\n\n async processPayment(request: ProcessPaymentRequest): Promise<PaymentResult> {\n await this.ensureInitialized();\n\n let modifiedRequest =\n await this.extensionsManager.runBeforePayment(request);\n\n try {\n const paymentResult = await this.paymentService!.process(\n modifiedRequest,\n {\n merchantId: this.config.merchantId,\n paymentIntentId: this.paymentIntentId!,\n clientSecret: this.clientSecret!,\n isUsingStripePaymentElement: this.isUsingStripePaymentElement,\n isUsingIndividualFormElements: this.isUsingIndividualFormElements,\n }\n );\n\n await this.extensionsManager.runAfterPayment(paymentResult);\n\n return paymentResult;\n } catch (error) {\n await this.extensionsManager.runOnError(error as Error);\n throw this.handlePaymentError(error);\n }\n }\n\n async mountPaymentForm(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountPaymentElement(selector);\n this.isUsingStripePaymentElement = true;\n }\n\n async mountCardNumber(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardNumberElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardExpiry(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardExpiryElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardCvc(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardCvcElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountAddress(\n selector: string,\n mode: 'billing' | 'shipping'\n ): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountAddressElement(selector, mode);\n this.isUsingIndividualFormElements = true;\n }\n\n addExtension(extension: PaymentExtension): void {\n this.extensionsManager.add(extension);\n }\n\n private async ensureInitialized(): Promise<void> {\n if (!this.stripeAdapter) {\n await this.initialize();\n }\n }\n\n private validatePaymentInitialisation(): void {\n const { amount, currency, partnerFee } = this.config.paymentData;\n\n if (!currency) {\n throw new ValidationError('Currency is required', 'currency');\n }\n\n const uppercaseCurrency = currency.toUpperCase();\n\n const paymentAmount = this.toMoney(amount, uppercaseCurrency, 'amount');\n\n if (paymentAmount.isZero() || paymentAmount.isNegative()) {\n throw new ValidationError('Amount must be greater than 0', 'amount');\n }\n\n if (partnerFee !== undefined) {\n const partnerFeeAmount = this.toMoney(partnerFee, uppercaseCurrency, 'partnerFee');\n\n if (partnerFeeAmount.isNegative()) {\n throw new ValidationError('partnerFee cannot be negative', 'partnerFee');\n }\n\n if (partnerFeeAmount.greaterThan(paymentAmount)) {\n throw new ValidationError('partnerFee cannot exceed the payment amount', 'partnerFee');\n }\n }\n }\n\n private toMoney(value: number, currency: string, fieldName: string): Money {\n try {\n return Money.fromInteger(value, currency);\n } catch {\n throw new ValidationError(\n `${fieldName} must be an integer in the smallest currency unit (e.g., cents for USD)`,\n fieldName\n );\n }\n }\n\n private handlePaymentError(error: any): Error {\n if (error instanceof VerapayError) {\n return error;\n }\n return new PaymentError(error.message || 'Payment failed', error.code);\n }\n}\n","import type { CardValidation } from '../types';\n\nexport class CardValidator {\n validateCardNumber(cardNumber: string): boolean {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (cleaned.length < 13 || cleaned.length > 19) {\n return false;\n }\n\n let sum = 0;\n let isEven = false;\n\n for (let i = cleaned.length - 1; i >= 0; i--) {\n let digit = parseInt(cleaned[i], 10);\n\n if (isEven) {\n digit *= 2;\n if (digit > 9) {\n digit -= 9;\n }\n }\n\n sum += digit;\n isEven = !isEven;\n }\n\n return sum % 10 === 0;\n }\n\n detectCardType(cardNumber: string): string {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (/^4/.test(cleaned)) return 'visa';\n if (/^5[1-5]/.test(cleaned)) return 'mastercard';\n if (/^3[47]/.test(cleaned)) return 'amex';\n if (/^6(?:011|5)/.test(cleaned)) return 'discover';\n\n return 'unknown';\n }\n\n validateExpiry(month: number, year: number): boolean {\n const now = new Date();\n const currentYear = now.getFullYear();\n const currentMonth = now.getMonth() + 1;\n\n if (month < 1 || month > 12) {\n return false;\n }\n\n const fullYear = year < 100 ? 2000 + year : year;\n\n if (fullYear < currentYear) {\n return false;\n }\n\n if (fullYear === currentYear && month < currentMonth) {\n return false;\n }\n\n return true;\n }\n\n validateCVC(cvc: string, cardType: string = 'unknown'): boolean {\n const cleaned = cvc.replace(/\\D/g, '');\n\n if (cardType === 'amex') {\n return cleaned.length === 4;\n }\n\n return cleaned.length === 3 || cleaned.length === 4;\n }\n\n validateAll(\n cardNumber: string,\n expiryMonth: number,\n expiryYear: number,\n cvc: string\n ): CardValidation {\n const cardType = this.detectCardType(cardNumber);\n\n return {\n number: {\n isValid: this.validateCardNumber(cardNumber),\n cardType: cardType as any,\n },\n expiry: {\n isValid: this.validateExpiry(expiryMonth, expiryYear),\n month: expiryMonth,\n year: expiryYear,\n },\n cvc: {\n isValid: this.validateCVC(cvc, cardType),\n length: cvc.replace(/\\D/g, '').length,\n },\n };\n }\n}\n","export class InputSanitizer {\n static sanitizeCardNumber(input: string): string {\n return input.replace(/\\D/g, '');\n }\n\n static formatCardNumber(input: string): string {\n const cleaned = this.sanitizeCardNumber(input);\n return cleaned.replace(/(\\d{4})/g, '$1 ').trim();\n }\n\n static sanitizeCVC(input: string): string {\n return input.replace(/\\D/g, '').slice(0, 4);\n }\n\n static sanitizeExpiry(input: string): { month: number; year: number } | null {\n const cleaned = input.replace(/\\D/g, '');\n\n if (cleaned.length === 4) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 4), 10),\n };\n } else if (cleaned.length === 6) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 6), 10),\n };\n }\n\n return null;\n }\n}\n","export { VerapayClient } from './client/verapay-client';\nexport { VerapayService } from './services/verapay-service';\n\nexport type {\n InitialisePaymentRequest,\n InitialisePaymentResponse,\n ProcessPrePaymentRequest,\n} from './services/verapay-service';\n\nexport type {\n VerapayConfig,\n ElementsConfig,\n ProcessPaymentRequest,\n PaymentResult,\n CardValidation,\n ErrorDetails,\n ErrorCode,\n} from './types';\n\nexport {\n VerapayError,\n ValidationError,\n PaymentError,\n ErrorFormatter,\n} from './errors';\n\nexport { CardValidator, InputSanitizer } from './validation';\n\nexport type {\n PaymentExtension,\n DatabaseExtension,\n AnalyticsExtension,\n} from './extensions';\n\nexport const VERSION = '0.0.1';\n"]}
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import {loadStripe}from'@stripe/stripe-js';import {Money}from'ts-money';var i=class o extends Error{constructor(e,t="PAYMENT_FAILED",r){super(e),this.name="VerapayError",this.code=t,this.details={code:t,message:e,formattedMessage:this.formatMessage(e,t),...r},Error.captureStackTrace&&Error.captureStackTrace(this,o);}formatMessage(e,t){return {VALIDATION_ERROR:"Please check your payment information and try again.",PAYMENT_FAILED:"Your payment could not be processed. Please try again.",AUTHENTICATION_FAILED:"Payment authentication failed. Please try again.",NETWORK_ERROR:"Network error. Please check your connection and try again.",STRIPE_ERROR:"Payment service error. Please try again later.",CONFIGURATION_ERROR:"Configuration error. Please contact support.",CARD_DECLINED:"Your card was declined. Please use a different payment method.",INSUFFICIENT_FUNDS:"Insufficient funds. Please use a different payment method.",EXPIRED_CARD:"Your card has expired. Please use a different payment method."}[t]||e}toJSON(){return {name:this.name,code:this.code,message:this.message,details:this.details}}};var l=class extends i{constructor(e,t,r){super(e,"VALIDATION_ERROR",{field:t,metadata:r}),this.name="ValidationError";}};var m=class o extends i{constructor(e,t,r){let n=o.mapStripeCode(t);super(e,n,{stripeCode:t,metadata:r}),this.name="PaymentError";}static mapStripeCode(e){return e?{card_declined:"CARD_DECLINED",insufficient_funds:"INSUFFICIENT_FUNDS",expired_card:"EXPIRED_CARD",incorrect_cvc:"VALIDATION_ERROR",processing_error:"PAYMENT_FAILED",authentication_failed:"AUTHENTICATION_FAILED"}[e]||"PAYMENT_FAILED":"PAYMENT_FAILED"}};var y=class{static formatForUser(e){return "formattedMessage"in e?e.formattedMessage:"details"in e&&e.details&&typeof e.details=="object"&&"formattedMessage"in e.details&&typeof e.details.formattedMessage=="string"?e.details.formattedMessage:"An unexpected error occurred. Please try again."}static formatForDeveloper(e){return "code"in e&&"message"in e?`[${e.code}] ${e.message}`:e.message||"Unknown error"}static toJSON(e){return "toJSON"in e&&typeof e.toJSON=="function"?e.toJSON():{name:e.name||"Error",message:e.message,..."code"in e&&{code:e.code},..."details"in e&&{details:e.details}}}};var u=class{constructor(e){this.stripe=e;}async confirmPayment(e,t){let r=await this.stripe.confirmPayment({clientSecret:t,confirmParams:{payment_method:e,return_url:window.location.href},redirect:"if_required"});if(r.error)throw new m(r.error.message||"Payment failed",r.error.code);return r}async confirmCardPayment(e,t){let r=await this.stripe.confirmCardPayment(t,{payment_method:e});if(r.error)throw new m(r.error.message||"Payment failed",r.error.code);return r}async createPaymentMethod(e,t=false){let r;if(!t)r=await this.stripe.createPaymentMethod({elements:e});else {let a=(await e.getElement("address",{mode:"billing"}).getValue()).value;r=await this.stripe.createPaymentMethod({type:"card",card:e.getElement("cardNumber"),billing_details:{name:a.name,address:{...a.address,line2:a.address.line2??void 0}}});}if(r.error||!r.paymentMethod)throw new m(r.error?.message||"Failed to create payment method",r.error?.code);return r.paymentMethod.id}};var d={showIcon:true,iconStyle:"solid",placeholders:{cardNumber:"1234 1234 1234 1234",cardExpiry:"MM / YY",cardCvc:"CVC"},style:{base:{color:"#333333",fontFamily:"system-ui, -apple-system, sans-serif",fontSize:"16px","::placeholder":{color:"#aab7c4"}},complete:{color:"#333333"},empty:{},invalid:{color:"#df1b41"}}},v={cardNumber:"Card number",cardExpiry:"Expiry date",cardCvc:"CVC",address:"Address"},E=class{constructor(e,t,r){this.stripe=e;this.config=t;this.clientSecret=r;this.elements=null;this.mountedElements=new Map;this.elementStates=new Map;if(!r)throw new i("Client secret not initialized","CONFIGURATION_ERROR")}mountPaymentElement(e){if(!this.elements){let n={clientSecret:this.clientSecret,appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"};this.elements=this.stripe.elements(n);}if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let r=this.elements.create("payment",{layout:"tabs"});r.mount(e),this.mountedElements.set("payment",r);}mountCardNumberElement(e){this.mountIndividualFormElement(e,"cardNumber",this.cardElementOptions("cardNumber"));}mountCardExpiryElement(e){this.mountIndividualFormElement(e,"cardExpiry",this.cardElementOptions("cardExpiry"));}mountCardCvcElement(e){this.mountIndividualFormElement(e,"cardCvc",this.cardElementOptions("cardCvc"));}mountAddressElement(e,t){this.mountIndividualFormElement(e,"address",{mode:t});}cardElementOptions(e){let{elementsConfig:t}=this.config,r={placeholder:t?.placeholders?.[e]??d.placeholders[e],style:{base:{...d.style.base,...t?.style?.base},complete:{...d.style.complete,...t?.style?.complete},empty:{...d.style.empty,...t?.style?.empty},invalid:{...d.style.invalid,...t?.style?.invalid}}};return e==="cardNumber"&&(r.showIcon=t?.showIcon??d.showIcon,r.iconStyle=t?.iconStyle??d.iconStyle),r}mountIndividualFormElement(e,t,r){if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let a=this.createIndividualFormElement(t,r);a.mount(e),this.mountedElements.set(t,a),this.trackElementState(t,a);}createIndividualFormElement(e,t){return this.elements||(this.elements=this.stripe.elements({appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"})),this.elements.create(e,t)}async validate(){let e=[];for(let[t,r]of this.elementStates.entries())r.complete||e.push({field:t,message:r.error??`${v[t]??t} failed validation`});return {isValid:e.length===0,errors:e}}getElements(){return this.elements}unmountAll(){for(let e of this.mountedElements.values())e.unmount();this.mountedElements.clear(),this.elementStates.clear();}trackElementState(e,t){this.elementStates.set(e,{complete:false});let r=n=>{this.elementStates.set(e,{complete:n.complete,error:n.error?.message});};t.on("change",r);}};var f=class{constructor(){this.extensions=[];}add(e){this.extensions.push(e);}async runBeforePayment(e){let t=e;for(let r of this.extensions)r.beforePayment&&(t=await r.beforePayment(t));return t}async runAfterPayment(e){await Promise.all(this.extensions.filter(t=>t.afterPayment).map(t=>t.afterPayment(e)));}async runOnError(e){await Promise.all(this.extensions.filter(t=>t.onPaymentError).map(t=>t.onPaymentError(e)));}};var g=class{constructor(e,t,r){this.stripeAdapter=e;this.elementsManager=t;this.verapayService=r;}async process(e,t){let r=this.elementsManager.getElements();await this.validatePaymentCanProceed(r,t),await r.submit();let n=await this.stripeAdapter.createPaymentMethod(r,t.isUsingIndividualFormElements);return await this.verapayService.processPrePayment({merchantId:t.merchantId,paymentIntentId:t.paymentIntentId,paymentMethodId:n,customerData:{email:e.customerEmail,firstName:e.customerFirstName,lastName:e.customerLastName},description:e.description,metadata:e.metadata}),this.confirmPayment(n,t)}async validatePaymentCanProceed(e,t){if(!e)throw new i("Payment form not mounted","CONFIGURATION_ERROR");if(t.isUsingStripePaymentElement&&t.isUsingIndividualFormElements)throw new i("Both forms of payment form in use");if(t.isUsingIndividualFormElements){let r=await this.elementsManager.validate();if(!r.isValid)throw new i(r.errors[0].message,"VALIDATION_ERROR")}}async confirmPayment(e,t){let{clientSecret:r,isUsingStripePaymentElement:n,isUsingIndividualFormElements:a}=t,s;return n?s=await this.stripeAdapter.confirmPayment(e,r):a&&(s=await this.stripeAdapter.confirmCardPayment(e,r)),this.formatPaymentResult(s)}formatPaymentResult(e){return {success:e.paymentIntent.status==="succeeded",paymentIntentId:e.paymentIntent.id,status:e.paymentIntent.status}}};var p=class{constructor(e="http://localhost:3333"){this.baseUrl=e;}async initialisePayment(e){let{merchantId:t,paymentData:r}=e;try{let n=await fetch(`${this.baseUrl}/api/initialise-payment`,{method:"POST",headers:{"Content-Type":"application/json","x-api-key":"example.api.key"},body:JSON.stringify({merchantId:t,paymentData:{...r,paymentMethodType:"card"}})});if(!n.ok){let s=await n.json().catch(()=>({}));throw new i(s.error||`HTTP error! status: ${n.status}`,"CONFIGURATION_ERROR")}let a=await n.json();if(!a.clientSecret||!a.paymentIntentId)throw new i("Missing clientSecret or paymentIntentId in server response","CONFIGURATION_ERROR");return {paymentIntentId:a.paymentIntentId,clientSecret:a.clientSecret,connectAccountId:a.connectAccountId}}catch(n){throw n instanceof i?n:new i(n instanceof Error?n.message:"Unknown error occurred","CONFIGURATION_ERROR")}}async processPrePayment(e){try{let t=await fetch(`${this.baseUrl}/api/process-prepayment`,{method:"POST",headers:{"Content-Type":"application/json","x-forwarded-for":"example.ip.addr"},body:JSON.stringify({merchantId:e.merchantId,paymentIntentId:e.paymentIntentId,paymentMethodId:e.paymentMethodId,customerData:e.customerData,description:e.description,metadata:e.metadata})});if(!t.ok){let r=await t.json().catch(()=>({}));throw new i(r.error||`HTTP error! status: ${t.status}`,"CONFIGURATION_ERROR")}}catch(t){throw t instanceof i?t:new i(t instanceof Error?t.message:"Unknown error occurred","CONFIGURATION_ERROR")}}};var h=class h{constructor(e){this.stripeAdapter=null;this.elementsManager=null;this.paymentService=null;this.isUsingStripePaymentElement=false;this.isUsingIndividualFormElements=false;this.clientSecret=null;this.paymentIntentId=null;this.config=e,this.verapayService=new p,this.extensionsManager=new f;}async initialize(){this.validatePaymentInitialisation();let{clientSecret:e,paymentIntentId:t}=await this.verapayService.initialisePayment({merchantId:this.config.merchantId,paymentData:this.config.paymentData});this.clientSecret=e,this.paymentIntentId=t;let r=await loadStripe(h.STRIPE_PUBLISHABLE_KEY);if(!r)throw new i("Failed to load Stripe","CONFIGURATION_ERROR");this.stripeAdapter=new u(r),this.elementsManager=new E(r,this.config,e),this.paymentService=new g(this.stripeAdapter,this.elementsManager,this.verapayService);}async processPayment(e){await this.ensureInitialized();let t=await this.extensionsManager.runBeforePayment(e);try{let r=await this.paymentService.process(t,{merchantId:this.config.merchantId,paymentIntentId:this.paymentIntentId,clientSecret:this.clientSecret,isUsingStripePaymentElement:this.isUsingStripePaymentElement,isUsingIndividualFormElements:this.isUsingIndividualFormElements});return await this.extensionsManager.runAfterPayment(r),r}catch(r){throw await this.extensionsManager.runOnError(r),this.handlePaymentError(r)}}async mountPaymentForm(e){await this.ensureInitialized(),this.elementsManager.mountPaymentElement(e),this.isUsingStripePaymentElement=true;}async mountCardNumber(e){await this.ensureInitialized(),this.elementsManager.mountCardNumberElement(e),this.isUsingIndividualFormElements=true;}async mountCardExpiry(e){await this.ensureInitialized(),this.elementsManager.mountCardExpiryElement(e),this.isUsingIndividualFormElements=true;}async mountCardCvc(e){await this.ensureInitialized(),this.elementsManager.mountCardCvcElement(e),this.isUsingIndividualFormElements=true;}async mountAddress(e,t){await this.ensureInitialized(),this.elementsManager.mountAddressElement(e,t),this.isUsingIndividualFormElements=true;}addExtension(e){this.extensionsManager.add(e);}async ensureInitialized(){this.stripeAdapter||await this.initialize();}validatePaymentInitialisation(){let{amount:e,currency:t,partnerFee:r}=this.config.paymentData;if(!t)throw new l("Currency is required","currency");let n=t.toUpperCase(),a=this.toMoney(e,n,"amount");if(a.isZero()||a.isNegative())throw new l("Amount must be greater than 0","amount");if(r!==void 0&&this.toMoney(r,n,"partnerFee").isNegative())throw new l("partnerFee cannot be negative","partnerFee")}toMoney(e,t,r){try{return Money.fromInteger(e,t)}catch{throw new l(`${r} must be an integer in the smallest currency unit (e.g., cents for USD)`,r)}}handlePaymentError(e){return e instanceof i?e:new m(e.message||"Payment failed",e.code)}};h.STRIPE_PUBLISHABLE_KEY="pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq";var R=h;var I=class{validateCardNumber(e){let t=e.replace(/\D/g,"");if(t.length<13||t.length>19)return false;let r=0,n=false;for(let a=t.length-1;a>=0;a--){let s=parseInt(t[a],10);n&&(s*=2,s>9&&(s-=9)),r+=s,n=!n;}return r%10===0}detectCardType(e){let t=e.replace(/\D/g,"");return /^4/.test(t)?"visa":/^5[1-5]/.test(t)?"mastercard":/^3[47]/.test(t)?"amex":/^6(?:011|5)/.test(t)?"discover":"unknown"}validateExpiry(e,t){let r=new Date,n=r.getFullYear(),a=r.getMonth()+1;if(e<1||e>12)return false;let s=t<100?2e3+t:t;return !(s<n||s===n&&e<a)}validateCVC(e,t="unknown"){let r=e.replace(/\D/g,"");return t==="amex"?r.length===4:r.length===3||r.length===4}validateAll(e,t,r,n){let a=this.detectCardType(e);return {number:{isValid:this.validateCardNumber(e),cardType:a},expiry:{isValid:this.validateExpiry(t,r),month:t,year:r},cvc:{isValid:this.validateCVC(n,a),length:n.replace(/\D/g,"").length}}}};var P=class{static sanitizeCardNumber(e){return e.replace(/\D/g,"")}static formatCardNumber(e){return this.sanitizeCardNumber(e).replace(/(\d{4})/g,"$1 ").trim()}static sanitizeCVC(e){return e.replace(/\D/g,"").slice(0,4)}static sanitizeExpiry(e){let t=e.replace(/\D/g,"");return t.length===4?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,4),10)}:t.length===6?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,6),10)}:null}};var ue="0.0.1";
|
|
2
|
-
export{I as CardValidator,y as ErrorFormatter,P as InputSanitizer,
|
|
1
|
+
import {loadStripe}from'@stripe/stripe-js';import {Money}from'ts-money';var i=class o extends Error{constructor(e,t="PAYMENT_FAILED",r){super(e),this.name="VerapayError",this.code=t,this.details={code:t,message:e,formattedMessage:this.formatMessage(e,t),...r},Error.captureStackTrace&&Error.captureStackTrace(this,o);}formatMessage(e,t){return {VALIDATION_ERROR:"Please check your payment information and try again.",PAYMENT_FAILED:"Your payment could not be processed. Please try again.",AUTHENTICATION_FAILED:"Payment authentication failed. Please try again.",NETWORK_ERROR:"Network error. Please check your connection and try again.",STRIPE_ERROR:"Payment service error. Please try again later.",CONFIGURATION_ERROR:"Configuration error. Please contact support.",CARD_DECLINED:"Your card was declined. Please use a different payment method.",INSUFFICIENT_FUNDS:"Insufficient funds. Please use a different payment method.",EXPIRED_CARD:"Your card has expired. Please use a different payment method."}[t]||e}toJSON(){return {name:this.name,code:this.code,message:this.message,details:this.details}}};var m=class extends i{constructor(e,t,r){super(e,"VALIDATION_ERROR",{field:t,metadata:r}),this.name="ValidationError";}};var l=class o extends i{constructor(e,t,r){let n=o.mapStripeCode(t);super(e,n,{stripeCode:t,metadata:r}),this.name="PaymentError";}static mapStripeCode(e){return e?{card_declined:"CARD_DECLINED",insufficient_funds:"INSUFFICIENT_FUNDS",expired_card:"EXPIRED_CARD",incorrect_cvc:"VALIDATION_ERROR",processing_error:"PAYMENT_FAILED",authentication_failed:"AUTHENTICATION_FAILED"}[e]||"PAYMENT_FAILED":"PAYMENT_FAILED"}};var y=class{static formatForUser(e){return "formattedMessage"in e?e.formattedMessage:"details"in e&&e.details&&typeof e.details=="object"&&"formattedMessage"in e.details&&typeof e.details.formattedMessage=="string"?e.details.formattedMessage:"An unexpected error occurred. Please try again."}static formatForDeveloper(e){return "code"in e&&"message"in e?`[${e.code}] ${e.message}`:e.message||"Unknown error"}static toJSON(e){return "toJSON"in e&&typeof e.toJSON=="function"?e.toJSON():{name:e.name||"Error",message:e.message,..."code"in e&&{code:e.code},..."details"in e&&{details:e.details}}}};var u=class{constructor(e){this.stripe=e;}async confirmPayment(e,t){let r=await this.stripe.confirmPayment({clientSecret:t,confirmParams:{payment_method:e,return_url:window.location.href},redirect:"if_required"});if(r.error)throw new l(r.error.message||"Payment failed",r.error.code);return r}async confirmCardPayment(e,t){let r=await this.stripe.confirmCardPayment(t,{payment_method:e});if(r.error)throw new l(r.error.message||"Payment failed",r.error.code);return r}async createPaymentMethod(e,t=false){let r;if(!t)r=await this.stripe.createPaymentMethod({elements:e});else {let a=(await e.getElement("address",{mode:"billing"}).getValue()).value;r=await this.stripe.createPaymentMethod({type:"card",card:e.getElement("cardNumber"),billing_details:{name:a.name,address:{...a.address,line2:a.address.line2??void 0}}});}if(r.error||!r.paymentMethod)throw new l(r.error?.message||"Failed to create payment method",r.error?.code);return r.paymentMethod.id}};var d={showIcon:true,iconStyle:"solid",placeholders:{cardNumber:"1234 1234 1234 1234",cardExpiry:"MM / YY - TESTING",cardCvc:"CVC"},style:{base:{color:"#333333",fontFamily:"system-ui, -apple-system, sans-serif",fontSize:"16px","::placeholder":{color:"#aab7c4"}},complete:{color:"#333333"},empty:{},invalid:{color:"#df1b41"}}},v={cardNumber:"Card number",cardExpiry:"Expiry date",cardCvc:"CVC",address:"Address"},E=class{constructor(e,t,r){this.stripe=e;this.config=t;this.clientSecret=r;this.elements=null;this.mountedElements=new Map;this.elementStates=new Map;if(!r)throw new i("Client secret not initialized","CONFIGURATION_ERROR")}mountPaymentElement(e){if(!this.elements){let n={clientSecret:this.clientSecret,appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"};this.elements=this.stripe.elements(n);}if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let r=this.elements.create("payment",{layout:"tabs"});r.mount(e),this.mountedElements.set("payment",r);}mountCardNumberElement(e){this.mountIndividualFormElement(e,"cardNumber",this.cardElementOptions("cardNumber"));}mountCardExpiryElement(e){this.mountIndividualFormElement(e,"cardExpiry",this.cardElementOptions("cardExpiry"));}mountCardCvcElement(e){this.mountIndividualFormElement(e,"cardCvc",this.cardElementOptions("cardCvc"));}mountAddressElement(e,t){this.mountIndividualFormElement(e,"address",{mode:t});}cardElementOptions(e){let{elementsConfig:t}=this.config,r={placeholder:t?.placeholders?.[e]??d.placeholders[e],style:{base:{...d.style.base,...t?.style?.base},complete:{...d.style.complete,...t?.style?.complete},empty:{...d.style.empty,...t?.style?.empty},invalid:{...d.style.invalid,...t?.style?.invalid}}};return e==="cardNumber"&&(r.showIcon=t?.showIcon??d.showIcon,r.iconStyle=t?.iconStyle??d.iconStyle),r}mountIndividualFormElement(e,t,r){if(!document.querySelector(e))throw new i(`Element not found: ${e}`,"CONFIGURATION_ERROR");let a=this.createIndividualFormElement(t,r);a.mount(e),this.mountedElements.set(t,a),this.trackElementState(t,a);}createIndividualFormElement(e,t){return this.elements||(this.elements=this.stripe.elements({appearance:this.config.appearance,locale:this.config.locale,fonts:this.config.fonts,paymentMethodCreation:"manual"})),this.elements.create(e,t)}async validate(){let e=[];for(let[t,r]of this.elementStates.entries())r.complete||e.push({field:t,message:r.error??`${v[t]??t} failed validation`});return {isValid:e.length===0,errors:e}}getElements(){return this.elements}unmountAll(){for(let e of this.mountedElements.values())e.unmount();this.mountedElements.clear(),this.elementStates.clear();}trackElementState(e,t){this.elementStates.set(e,{complete:false});let r=n=>{this.elementStates.set(e,{complete:n.complete,error:n.error?.message});};t.on("change",r);}};var f=class{constructor(){this.extensions=[];}add(e){this.extensions.push(e);}async runBeforePayment(e){let t=e;for(let r of this.extensions)r.beforePayment&&(t=await r.beforePayment(t));return t}async runAfterPayment(e){await Promise.all(this.extensions.filter(t=>t.afterPayment).map(t=>t.afterPayment(e)));}async runOnError(e){await Promise.all(this.extensions.filter(t=>t.onPaymentError).map(t=>t.onPaymentError(e)));}};var g=class{constructor(e,t,r){this.stripeAdapter=e;this.elementsManager=t;this.verapayService=r;}async process(e,t){let r=this.elementsManager.getElements();await this.validatePaymentCanProceed(r,t),await r.submit();let n=await this.stripeAdapter.createPaymentMethod(r,t.isUsingIndividualFormElements);return await this.verapayService.processPrePayment({merchantId:t.merchantId,paymentIntentId:t.paymentIntentId,paymentMethodId:n,customerData:{email:e.customerEmail,firstName:e.customerFirstName,lastName:e.customerLastName},description:e.description,metadata:e.metadata}),this.confirmPayment(n,t)}async validatePaymentCanProceed(e,t){if(!e)throw new i("Payment form not mounted","CONFIGURATION_ERROR");if(t.isUsingStripePaymentElement&&t.isUsingIndividualFormElements)throw new i("Both forms of payment form in use");if(t.isUsingIndividualFormElements){let r=await this.elementsManager.validate();if(!r.isValid)throw new i(r.errors[0].message,"VALIDATION_ERROR")}}async confirmPayment(e,t){let{clientSecret:r,isUsingStripePaymentElement:n,isUsingIndividualFormElements:a}=t,s;return n?s=await this.stripeAdapter.confirmPayment(e,r):a&&(s=await this.stripeAdapter.confirmCardPayment(e,r)),this.formatPaymentResult(s)}formatPaymentResult(e){return {success:e.paymentIntent.status==="succeeded",paymentIntentId:e.paymentIntent.id,status:e.paymentIntent.status}}};var p=class{constructor(e="http://localhost:3333"){this.baseUrl=e;}async initialisePayment(e){let{merchantId:t,paymentData:r}=e;try{let n=await fetch(`${this.baseUrl}/api/initialise-payment`,{method:"POST",headers:{"Content-Type":"application/json","x-api-key":"example.api.key"},body:JSON.stringify({merchantId:t,paymentData:{...r,paymentMethodType:"card"}})});if(!n.ok){let s=await n.json().catch(()=>({}));throw new i(s.error||`HTTP error! status: ${n.status}`,"CONFIGURATION_ERROR")}let a=await n.json();if(!a.clientSecret||!a.paymentIntentId)throw new i("Missing clientSecret or paymentIntentId in server response","CONFIGURATION_ERROR");return {paymentIntentId:a.paymentIntentId,clientSecret:a.clientSecret,connectAccountId:a.connectAccountId}}catch(n){throw n instanceof i?n:new i(n instanceof Error?n.message:"Unknown error occurred","CONFIGURATION_ERROR")}}async processPrePayment(e){try{let t=await fetch(`${this.baseUrl}/api/process-prepayment`,{method:"POST",headers:{"Content-Type":"application/json","x-forwarded-for":"example.ip.addr"},body:JSON.stringify({merchantId:e.merchantId,paymentIntentId:e.paymentIntentId,paymentMethodId:e.paymentMethodId,customerData:e.customerData,description:e.description,metadata:e.metadata})});if(!t.ok){let r=await t.json().catch(()=>({}));throw new i(r.error||`HTTP error! status: ${t.status}`,"CONFIGURATION_ERROR")}}catch(t){throw t instanceof i?t:new i(t instanceof Error?t.message:"Unknown error occurred","CONFIGURATION_ERROR")}}};var h=class h{constructor(e){this.stripeAdapter=null;this.elementsManager=null;this.paymentService=null;this.isUsingStripePaymentElement=false;this.isUsingIndividualFormElements=false;this.clientSecret=null;this.paymentIntentId=null;this.config=e,this.verapayService=new p,this.extensionsManager=new f;}async initialize(){this.validatePaymentInitialisation();let{clientSecret:e,paymentIntentId:t}=await this.verapayService.initialisePayment({merchantId:this.config.merchantId,paymentData:this.config.paymentData});this.clientSecret=e,this.paymentIntentId=t;let r=await loadStripe(h.STRIPE_PUBLISHABLE_KEY);if(!r)throw new i("Failed to load Stripe","CONFIGURATION_ERROR");this.stripeAdapter=new u(r),this.elementsManager=new E(r,this.config,e),this.paymentService=new g(this.stripeAdapter,this.elementsManager,this.verapayService);}async processPayment(e){await this.ensureInitialized();let t=await this.extensionsManager.runBeforePayment(e);try{let r=await this.paymentService.process(t,{merchantId:this.config.merchantId,paymentIntentId:this.paymentIntentId,clientSecret:this.clientSecret,isUsingStripePaymentElement:this.isUsingStripePaymentElement,isUsingIndividualFormElements:this.isUsingIndividualFormElements});return await this.extensionsManager.runAfterPayment(r),r}catch(r){throw await this.extensionsManager.runOnError(r),this.handlePaymentError(r)}}async mountPaymentForm(e){await this.ensureInitialized(),this.elementsManager.mountPaymentElement(e),this.isUsingStripePaymentElement=true;}async mountCardNumber(e){await this.ensureInitialized(),this.elementsManager.mountCardNumberElement(e),this.isUsingIndividualFormElements=true;}async mountCardExpiry(e){await this.ensureInitialized(),this.elementsManager.mountCardExpiryElement(e),this.isUsingIndividualFormElements=true;}async mountCardCvc(e){await this.ensureInitialized(),this.elementsManager.mountCardCvcElement(e),this.isUsingIndividualFormElements=true;}async mountAddress(e,t){await this.ensureInitialized(),this.elementsManager.mountAddressElement(e,t),this.isUsingIndividualFormElements=true;}addExtension(e){this.extensionsManager.add(e);}async ensureInitialized(){this.stripeAdapter||await this.initialize();}validatePaymentInitialisation(){let{amount:e,currency:t,partnerFee:r}=this.config.paymentData;if(!t)throw new m("Currency is required","currency");let n=t.toUpperCase(),a=this.toMoney(e,n,"amount");if(a.isZero()||a.isNegative())throw new m("Amount must be greater than 0","amount");if(r!==void 0){let s=this.toMoney(r,n,"partnerFee");if(s.isNegative())throw new m("partnerFee cannot be negative","partnerFee");if(s.greaterThan(a))throw new m("partnerFee cannot exceed the payment amount","partnerFee")}}toMoney(e,t,r){try{return Money.fromInteger(e,t)}catch{throw new m(`${r} must be an integer in the smallest currency unit (e.g., cents for USD)`,r)}}handlePaymentError(e){return e instanceof i?e:new l(e.message||"Payment failed",e.code)}};h.STRIPE_PUBLISHABLE_KEY="pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq";var R=h;var I=class{validateCardNumber(e){let t=e.replace(/\D/g,"");if(t.length<13||t.length>19)return false;let r=0,n=false;for(let a=t.length-1;a>=0;a--){let s=parseInt(t[a],10);n&&(s*=2,s>9&&(s-=9)),r+=s,n=!n;}return r%10===0}detectCardType(e){let t=e.replace(/\D/g,"");return /^4/.test(t)?"visa":/^5[1-5]/.test(t)?"mastercard":/^3[47]/.test(t)?"amex":/^6(?:011|5)/.test(t)?"discover":"unknown"}validateExpiry(e,t){let r=new Date,n=r.getFullYear(),a=r.getMonth()+1;if(e<1||e>12)return false;let s=t<100?2e3+t:t;return !(s<n||s===n&&e<a)}validateCVC(e,t="unknown"){let r=e.replace(/\D/g,"");return t==="amex"?r.length===4:r.length===3||r.length===4}validateAll(e,t,r,n){let a=this.detectCardType(e);return {number:{isValid:this.validateCardNumber(e),cardType:a},expiry:{isValid:this.validateExpiry(t,r),month:t,year:r},cvc:{isValid:this.validateCVC(n,a),length:n.replace(/\D/g,"").length}}}};var P=class{static sanitizeCardNumber(e){return e.replace(/\D/g,"")}static formatCardNumber(e){return this.sanitizeCardNumber(e).replace(/(\d{4})/g,"$1 ").trim()}static sanitizeCVC(e){return e.replace(/\D/g,"").slice(0,4)}static sanitizeExpiry(e){let t=e.replace(/\D/g,"");return t.length===4?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,4),10)}:t.length===6?{month:parseInt(t.slice(0,2),10),year:parseInt(t.slice(2,6),10)}:null}};var ue="0.0.1";
|
|
2
|
+
export{I as CardValidator,y as ErrorFormatter,P as InputSanitizer,l as PaymentError,ue as VERSION,m as ValidationError,R as VerapayClient,i as VerapayError,p as VerapayService};//# sourceMappingURL=index.js.map
|
|
3
3
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/errors/VerapayError.ts","../src/errors/ValidationError.ts","../src/errors/PaymentError.ts","../src/errors/errorFormatter.ts","../src/client/StripeAdapter.ts","../src/client/ElementsManager.ts","../src/client/PaymentExtensionsManager.ts","../src/services/PaymentService.ts","../src/services/VerapayService.ts","../src/client/VerapayClient.ts","../src/validation/cardValidator.ts","../src/validation/inputSanitizer.ts","../src/index.ts"],"names":["VerapayError","_VerapayError","message","code","details","ValidationError","field","metadata","PaymentError","_PaymentError","stripeCode","ErrorFormatter","error","StripeAdapter","stripe","paymentMethodId","clientSecret","result","elements","isUsingIndividualFormElements","address","DEFAULT_CARD_ELEMENT_CONFIG","FIELD_LABELS","ElementsManager","config","selector","elementsConfig","element","mode","fieldType","options","formFieldType","errors","state","handleElementChange","event","PaymentExtensionsManager","extension","request","modifiedRequest","ext","PaymentService","stripeAdapter","elementsManager","verapayService","context","validation","isUsingStripePaymentElement","VerapayService","baseUrl","merchantId","paymentData","response","errorData","data","_VerapayClient","paymentIntentId","loadStripe","paymentResult","amount","currency","partnerFee","uppercaseCurrency","paymentAmount","value","fieldName","Money","VerapayClient","CardValidator","cardNumber","cleaned","sum","isEven","i","digit","month","year","now","currentYear","currentMonth","fullYear","cvc","cardType","expiryMonth","expiryYear","InputSanitizer","input","VERSION"],"mappings":"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","file":"index.js","sourcesContent":["import type { ErrorDetails } from '../types';\nimport { ErrorCode } from '../types';\n\nexport class VerapayError extends Error {\n public readonly code: ErrorCode;\n public readonly details: ErrorDetails;\n\n constructor(\n message: string,\n code: ErrorCode = ErrorCode.PAYMENT_FAILED,\n details?: Partial<ErrorDetails>\n ) {\n super(message);\n this.name = 'VerapayError';\n this.code = code;\n this.details = {\n code,\n message,\n formattedMessage: this.formatMessage(message, code),\n ...details,\n };\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, VerapayError);\n }\n }\n\n private formatMessage(message: string, code: ErrorCode): string {\n const messageMap: Record<ErrorCode, string> = {\n [ErrorCode.VALIDATION_ERROR]:\n 'Please check your payment information and try again.',\n [ErrorCode.PAYMENT_FAILED]:\n 'Your payment could not be processed. Please try again.',\n [ErrorCode.AUTHENTICATION_FAILED]:\n 'Payment authentication failed. Please try again.',\n [ErrorCode.NETWORK_ERROR]:\n 'Network error. Please check your connection and try again.',\n [ErrorCode.STRIPE_ERROR]:\n 'Payment service error. Please try again later.',\n [ErrorCode.CONFIGURATION_ERROR]:\n 'Configuration error. Please contact support.',\n [ErrorCode.CARD_DECLINED]:\n 'Your card was declined. Please use a different payment method.',\n [ErrorCode.INSUFFICIENT_FUNDS]:\n 'Insufficient funds. Please use a different payment method.',\n [ErrorCode.EXPIRED_CARD]:\n 'Your card has expired. Please use a different payment method.',\n };\n\n return messageMap[code] || message;\n }\n\n toJSON() {\n return {\n name: this.name,\n code: this.code,\n message: this.message,\n details: this.details,\n };\n }\n}\n","import { VerapayError } from './VerapayError';\nimport { ErrorCode } from '../types';\n\nexport class ValidationError extends VerapayError {\n constructor(message: string, field?: string, metadata?: Record<string, any>) {\n super(message, ErrorCode.VALIDATION_ERROR, {\n field,\n metadata,\n });\n this.name = 'ValidationError';\n }\n}\n","import { VerapayError } from './VerapayError';\nimport { ErrorCode } from '../types';\n\nexport class PaymentError extends VerapayError {\n constructor(\n message: string,\n stripeCode?: string,\n metadata?: Record<string, any>\n ) {\n const code = PaymentError.mapStripeCode(stripeCode);\n super(message, code, {\n stripeCode,\n metadata,\n });\n this.name = 'PaymentError';\n }\n\n private static mapStripeCode(stripeCode?: string): ErrorCode {\n if (!stripeCode) return ErrorCode.PAYMENT_FAILED;\n\n const codeMap: Record<string, ErrorCode> = {\n card_declined: ErrorCode.CARD_DECLINED,\n insufficient_funds: ErrorCode.INSUFFICIENT_FUNDS,\n expired_card: ErrorCode.EXPIRED_CARD,\n incorrect_cvc: ErrorCode.VALIDATION_ERROR,\n processing_error: ErrorCode.PAYMENT_FAILED,\n authentication_failed: ErrorCode.AUTHENTICATION_FAILED,\n };\n\n return codeMap[stripeCode] || ErrorCode.PAYMENT_FAILED;\n }\n}\n","import type { ErrorDetails } from '../types';\n\nexport class ErrorFormatter {\n static formatForUser(error: Error | ErrorDetails): string {\n if ('formattedMessage' in error) {\n return error.formattedMessage;\n }\n if (\n 'details' in error &&\n error.details &&\n typeof error.details === 'object' &&\n 'formattedMessage' in error.details &&\n typeof error.details.formattedMessage === 'string'\n ) {\n return error.details.formattedMessage;\n }\n return 'An unexpected error occurred. Please try again.';\n }\n\n static formatForDeveloper(error: Error | ErrorDetails): string {\n if ('code' in error && 'message' in error) {\n return `[${error.code}] ${error.message}`;\n }\n return error.message || 'Unknown error';\n }\n\n static toJSON(error: Error | ErrorDetails): Record<string, any> {\n if ('toJSON' in error && typeof error.toJSON === 'function') {\n return error.toJSON();\n }\n\n return {\n name: (error as Error).name || 'Error',\n message: error.message,\n ...('code' in error && { code: error.code }),\n ...('details' in error && { details: error.details }),\n };\n }\n}\n","import type { PaymentIntent, Stripe, StripeElements } from '@stripe/stripe-js';\nimport { PaymentError } from '../errors';\n\nexport class StripeAdapter {\n constructor(private stripe: Stripe) {}\n\n async confirmPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmPayment({\n clientSecret,\n confirmParams: {\n payment_method: paymentMethodId,\n return_url: window.location.href,\n },\n redirect: 'if_required',\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async confirmCardPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmCardPayment(clientSecret, {\n payment_method: paymentMethodId,\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async createPaymentMethod(\n elements: StripeElements,\n isUsingIndividualFormElements: boolean = false\n ): Promise<string> {\n let result;\n\n if (!isUsingIndividualFormElements) {\n result = await this.stripe.createPaymentMethod({\n elements,\n });\n } else {\n // @ts-ignore - Stripe types don't include mode parameter for getElement\n const addressElement = await elements.getElement('address', { mode: 'billing' })!.getValue();\n const address = addressElement!.value;\n\n result = await this.stripe.createPaymentMethod({\n type: 'card',\n card: elements.getElement('cardNumber')!,\n billing_details: {\n name: address.name,\n address: {\n ...address.address,\n line2: address.address.line2 ?? undefined,\n },\n },\n });\n }\n\n if (result.error || !result.paymentMethod) {\n throw new PaymentError(\n result.error?.message || 'Failed to create payment method',\n result.error?.code\n );\n }\n\n return result.paymentMethod.id;\n }\n}\n","import type {\n Stripe,\n StripeElements,\n StripeElement,\n StripePaymentElement,\n StripeCardNumberElement,\n} from '@stripe/stripe-js';\nimport type { VerapayConfig, ValidationError, ValidationResult } from '../types';\nimport { VerapayError, ErrorCode } from '../errors';\n\ntype ElementState = { complete: boolean; error?: string }\n\nconst DEFAULT_CARD_ELEMENT_CONFIG = {\n showIcon: true,\n iconStyle: 'solid' as const,\n placeholders: {\n cardNumber: '1234 1234 1234 1234',\n cardExpiry: 'MM / YY',\n cardCvc: 'CVC',\n },\n style: {\n base: {\n color: '#333333',\n fontFamily: 'system-ui, -apple-system, sans-serif',\n fontSize: '16px',\n '::placeholder': { color: '#aab7c4' },\n },\n complete: {\n color: '#333333',\n },\n empty: {},\n invalid: {\n color: '#df1b41',\n },\n },\n}\n\nconst FIELD_LABELS: Record<string, string> = {\n cardNumber: 'Card number',\n cardExpiry: 'Expiry date',\n cardCvc: 'CVC',\n address: 'Address',\n}\n\nexport class ElementsManager {\n private elements: StripeElements | null = null;\n private mountedElements: Map<string, StripeElement> = new Map();\n private elementStates: Map<string, ElementState> = new Map();\n\n constructor(\n private stripe: Stripe,\n private config: VerapayConfig,\n private clientSecret: string\n ) {\n if (!clientSecret) {\n throw new VerapayError(\n 'Client secret not initialized',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n mountPaymentElement(selector: string): void {\n if (!this.elements) {\n const elementsConfig = {\n clientSecret: this.clientSecret,\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n };\n\n this.elements = this.stripe.elements(elementsConfig);\n }\n\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.elements.create('payment', {\n layout: 'tabs',\n }) as StripePaymentElement;\n\n element.mount(selector);\n this.mountedElements.set('payment', element);\n }\n\n mountCardNumberElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardNumber', this.cardElementOptions('cardNumber'));\n }\n\n mountCardExpiryElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardExpiry', this.cardElementOptions('cardExpiry'));\n }\n\n mountCardCvcElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardCvc', this.cardElementOptions('cardCvc'));\n }\n\n mountAddressElement(selector: string, mode: 'billing' | 'shipping'): void {\n this.mountIndividualFormElement(selector, 'address', { mode });\n }\n\n private cardElementOptions(fieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc'): Record<string, unknown> {\n const { elementsConfig } = this.config;\n const options: Record<string, unknown> = {\n placeholder: elementsConfig?.placeholders?.[fieldType] ?? DEFAULT_CARD_ELEMENT_CONFIG.placeholders[fieldType],\n style: {\n base: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.base, ...elementsConfig?.style?.base },\n complete: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.complete, ...elementsConfig?.style?.complete },\n empty: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.empty, ...elementsConfig?.style?.empty },\n invalid: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.invalid, ...elementsConfig?.style?.invalid },\n },\n };\n\n if (fieldType === 'cardNumber') {\n options.showIcon = elementsConfig?.showIcon ?? DEFAULT_CARD_ELEMENT_CONFIG.showIcon;\n options.iconStyle = elementsConfig?.iconStyle ?? DEFAULT_CARD_ELEMENT_CONFIG.iconStyle;\n }\n\n return options;\n }\n\n private mountIndividualFormElement(selector: string, formFieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc' | 'address', options?: Record<string, unknown>) {\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.createIndividualFormElement(formFieldType, options) as StripeCardNumberElement;\n element.mount(selector);\n\n this.mountedElements.set(formFieldType, element);\n this.trackElementState(formFieldType, element);\n }\n\n private createIndividualFormElement(\n formFieldType: any,\n options?: Record<string, unknown>\n ): StripeElement {\n if (!this.elements) {\n // For individual card elements, don't pass clientSecret\n // It's only needed when creating Payment Element or confirming payment\n this.elements = this.stripe.elements({\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n });\n }\n\n return this.elements.create(formFieldType, options);\n }\n\n async validate(): Promise<ValidationResult> {\n const errors: ValidationError[] = []\n\n for (const [field, state] of this.elementStates.entries()) {\n if (!state.complete) {\n errors.push({\n field,\n message: state.error ?? `${FIELD_LABELS[field] ?? field} failed validation`,\n })\n }\n }\n\n return { isValid: errors.length === 0, errors }\n }\n\n getElements(): StripeElements | null {\n return this.elements;\n }\n\n unmountAll(): void {\n for (const element of this.mountedElements.values()) {\n element.unmount();\n }\n this.mountedElements.clear();\n this.elementStates.clear();\n }\n\n private trackElementState(field: string, element: StripeElement): void {\n this.elementStates.set(field, { complete: false })\n\n const handleElementChange = (event: { complete: boolean; error?: { message: string } }) => {\n this.elementStates.set(field, { complete: event.complete, error: event.error?.message })\n };\n\n (element as any).on('change', handleElementChange)\n }\n}\n","import type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport type { PaymentExtension } from '../extensions'\n\nexport class PaymentExtensionsManager {\n private extensions: PaymentExtension[] = []\n\n add(extension: PaymentExtension): void {\n this.extensions.push(extension)\n }\n\n async runBeforePayment(request: ProcessPaymentRequest): Promise<ProcessPaymentRequest> {\n let modifiedRequest = request\n for (const ext of this.extensions) {\n if (ext.beforePayment) {\n modifiedRequest = await ext.beforePayment(modifiedRequest)\n }\n }\n return modifiedRequest\n }\n\n async runAfterPayment(result: PaymentResult): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.afterPayment)\n .map((ext) => ext.afterPayment!(result)),\n )\n }\n\n async runOnError(error: Error): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.onPaymentError)\n .map((ext) => ext.onPaymentError!(error)),\n )\n }\n}\n","import { StripeAdapter } from '../client/StripeAdapter'\nimport { ElementsManager } from '../client/ElementsManager'\nimport { ErrorCode, VerapayError } from '../errors'\nimport { VerapayService } from './VerapayService'\nimport type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport { StripeElements } from '@stripe/stripe-js';\n\nexport interface ProcessPaymentContext {\n merchantId: string\n paymentIntentId: string\n clientSecret: string\n isUsingStripePaymentElement: boolean\n isUsingIndividualFormElements: boolean\n}\n\nexport class PaymentService {\n constructor(\n private stripeAdapter: StripeAdapter,\n private elementsManager: ElementsManager,\n private verapayService: VerapayService,\n ) {}\n\n async process(request: ProcessPaymentRequest, context: ProcessPaymentContext): Promise<PaymentResult> {\n const elements = this.elementsManager.getElements()\n\n await this.validatePaymentCanProceed(elements, context);\n\n await elements!.submit()\n\n const paymentMethodId = await this.stripeAdapter.createPaymentMethod(\n elements!,\n context.isUsingIndividualFormElements,\n )\n\n await this.verapayService.processPrePayment({\n merchantId: context.merchantId,\n paymentIntentId: context.paymentIntentId,\n paymentMethodId,\n customerData: {\n email: request.customerEmail,\n firstName: request.customerFirstName,\n lastName: request.customerLastName,\n },\n description: request.description,\n metadata: request.metadata,\n })\n\n return this.confirmPayment(paymentMethodId, context)\n }\n\n private async validatePaymentCanProceed(elements: StripeElements | null, context: ProcessPaymentContext) {\n if (!elements) {\n throw new VerapayError('Payment form not mounted', ErrorCode.CONFIGURATION_ERROR)\n }\n\n if (context.isUsingStripePaymentElement && context.isUsingIndividualFormElements) {\n throw new VerapayError('Both forms of payment form in use');\n }\n\n if (context.isUsingIndividualFormElements) {\n const validation = await this.elementsManager.validate()\n if (!validation.isValid) {\n throw new VerapayError(validation.errors[0].message, ErrorCode.VALIDATION_ERROR)\n }\n }\n }\n\n private async confirmPayment(\n paymentMethodId: string,\n context: ProcessPaymentContext,\n ): Promise<PaymentResult> {\n const { clientSecret, isUsingStripePaymentElement, isUsingIndividualFormElements } = context\n\n let result\n\n if (isUsingStripePaymentElement) {\n result = await this.stripeAdapter.confirmPayment(paymentMethodId, clientSecret)\n } else if (isUsingIndividualFormElements) {\n result = await this.stripeAdapter.confirmCardPayment(paymentMethodId, clientSecret)\n }\n\n return this.formatPaymentResult(result)\n }\n\n private formatPaymentResult(result: any): PaymentResult {\n return {\n success: result.paymentIntent.status === 'succeeded',\n paymentIntentId: result.paymentIntent.id,\n status: result.paymentIntent.status,\n }\n }\n}\n","import { ErrorCode, VerapayError } from '../errors';\nimport { PaymentData } from '../types';\n\nexport interface InitialisePaymentRequest {\n merchantId: string;\n paymentData: PaymentData;\n}\n\nexport interface InitialisePaymentResponse {\n paymentIntentId: string;\n clientSecret: string;\n connectAccountId: string;\n}\n\nexport interface ProcessPrePaymentRequest {\n merchantId: string;\n paymentIntentId: string;\n paymentMethodId: string;\n customerData: Record<string, any>;\n description?: string;\n metadata?: Record<string, string>;\n}\n\nexport class VerapayService {\n private readonly baseUrl: string;\n\n constructor(baseUrl: string = 'http://localhost:3333') {\n this.baseUrl = baseUrl;\n }\n\n async initialisePayment(\n request: InitialisePaymentRequest\n ): Promise<InitialisePaymentResponse> {\n const { merchantId, paymentData } = request;\n\n try {\n const response = await fetch(`${this.baseUrl}/api/initialise-payment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-api-key': 'example.api.key',\n },\n body: JSON.stringify({\n merchantId,\n paymentData: { ...paymentData, paymentMethodType: 'card' },\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const data = await response.json();\n\n if (!data.clientSecret || !data.paymentIntentId) {\n throw new VerapayError(\n 'Missing clientSecret or paymentIntentId in server response',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n return {\n paymentIntentId: data.paymentIntentId,\n clientSecret: data.clientSecret,\n connectAccountId: data.connectAccountId,\n };\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n async processPrePayment(request: ProcessPrePaymentRequest): Promise<void> {\n try {\n const response = await fetch(`${this.baseUrl}/api/process-prepayment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-forwarded-for': 'example.ip.addr',\n },\n body: JSON.stringify({\n merchantId: request.merchantId,\n paymentIntentId: request.paymentIntentId,\n paymentMethodId: request.paymentMethodId,\n customerData: request.customerData,\n description: request.description,\n metadata: request.metadata,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n}\n","import { loadStripe } from '@stripe/stripe-js';\nimport { Money } from 'ts-money';\nimport { StripeAdapter } from './StripeAdapter';\nimport { ElementsManager } from './ElementsManager';\nimport type { PaymentExtension } from '../extensions';\nimport { PaymentExtensionsManager } from './PaymentExtensionsManager';\nimport { PaymentService } from '../services/PaymentService';\nimport {\n ErrorCode,\n VerapayError,\n PaymentError,\n ValidationError,\n} from '../errors';\nimport { VerapayService } from '../services/VerapayService';\nimport type {\n VerapayConfig,\n ProcessPaymentRequest,\n PaymentResult,\n} from '../types';\n\nexport class VerapayClient {\n private static readonly STRIPE_PUBLISHABLE_KEY =\n 'pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq';\n\n private config: VerapayConfig;\n private verapayService: VerapayService;\n private extensionsManager: PaymentExtensionsManager;\n\n private stripeAdapter: StripeAdapter | null = null;\n private elementsManager: ElementsManager | null = null;\n private paymentService: PaymentService | null = null;\n\n private isUsingStripePaymentElement: boolean = false;\n private isUsingIndividualFormElements: boolean = false;\n\n private clientSecret: string | null = null;\n private paymentIntentId: string | null = null;\n\n constructor(config: VerapayConfig) {\n this.config = config;\n this.verapayService = new VerapayService();\n this.extensionsManager = new PaymentExtensionsManager();\n }\n\n async initialize(): Promise<void> {\n this.validatePaymentInitialisation()\n\n const { clientSecret, paymentIntentId } =\n await this.verapayService.initialisePayment({\n merchantId: this.config.merchantId,\n paymentData: this.config.paymentData\n });\n\n this.clientSecret = clientSecret;\n this.paymentIntentId = paymentIntentId;\n\n const stripe = await loadStripe(VerapayClient.STRIPE_PUBLISHABLE_KEY);\n\n if (!stripe) {\n throw new VerapayError(\n 'Failed to load Stripe',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n this.stripeAdapter = new StripeAdapter(stripe);\n this.elementsManager = new ElementsManager(\n stripe,\n this.config,\n clientSecret\n );\n this.paymentService = new PaymentService(\n this.stripeAdapter,\n this.elementsManager,\n this.verapayService\n );\n }\n\n async processPayment(request: ProcessPaymentRequest): Promise<PaymentResult> {\n await this.ensureInitialized();\n\n let modifiedRequest =\n await this.extensionsManager.runBeforePayment(request);\n\n try {\n const paymentResult = await this.paymentService!.process(\n modifiedRequest,\n {\n merchantId: this.config.merchantId,\n paymentIntentId: this.paymentIntentId!,\n clientSecret: this.clientSecret!,\n isUsingStripePaymentElement: this.isUsingStripePaymentElement,\n isUsingIndividualFormElements: this.isUsingIndividualFormElements,\n }\n );\n\n await this.extensionsManager.runAfterPayment(paymentResult);\n\n return paymentResult;\n } catch (error) {\n await this.extensionsManager.runOnError(error as Error);\n throw this.handlePaymentError(error);\n }\n }\n\n async mountPaymentForm(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountPaymentElement(selector);\n this.isUsingStripePaymentElement = true;\n }\n\n async mountCardNumber(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardNumberElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardExpiry(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardExpiryElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardCvc(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardCvcElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountAddress(\n selector: string,\n mode: 'billing' | 'shipping'\n ): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountAddressElement(selector, mode);\n this.isUsingIndividualFormElements = true;\n }\n\n addExtension(extension: PaymentExtension): void {\n this.extensionsManager.add(extension);\n }\n\n private async ensureInitialized(): Promise<void> {\n if (!this.stripeAdapter) {\n await this.initialize();\n }\n }\n\n private validatePaymentInitialisation(): void {\n const { amount, currency, partnerFee } = this.config.paymentData;\n\n if (!currency) {\n throw new ValidationError('Currency is required', 'currency');\n }\n\n const uppercaseCurrency = currency.toUpperCase();\n\n const paymentAmount = this.toMoney(amount, uppercaseCurrency, 'amount');\n\n if (paymentAmount.isZero() || paymentAmount.isNegative()) {\n throw new ValidationError('Amount must be greater than 0', 'amount');\n }\n\n if (partnerFee !== undefined) {\n const partnerFeeAmount = this.toMoney(partnerFee, uppercaseCurrency, 'partnerFee');\n\n if (partnerFeeAmount.isNegative()) {\n throw new ValidationError('partnerFee cannot be negative', 'partnerFee');\n }\n }\n }\n\n private toMoney(value: number, currency: string, fieldName: string): Money {\n try {\n return Money.fromInteger(value, currency);\n } catch {\n throw new ValidationError(\n `${fieldName} must be an integer in the smallest currency unit (e.g., cents for USD)`,\n fieldName\n );\n }\n }\n\n private handlePaymentError(error: any): Error {\n if (error instanceof VerapayError) {\n return error;\n }\n return new PaymentError(error.message || 'Payment failed', error.code);\n }\n}\n","import type { CardValidation } from '../types';\n\nexport class CardValidator {\n validateCardNumber(cardNumber: string): boolean {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (cleaned.length < 13 || cleaned.length > 19) {\n return false;\n }\n\n let sum = 0;\n let isEven = false;\n\n for (let i = cleaned.length - 1; i >= 0; i--) {\n let digit = parseInt(cleaned[i], 10);\n\n if (isEven) {\n digit *= 2;\n if (digit > 9) {\n digit -= 9;\n }\n }\n\n sum += digit;\n isEven = !isEven;\n }\n\n return sum % 10 === 0;\n }\n\n detectCardType(cardNumber: string): string {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (/^4/.test(cleaned)) return 'visa';\n if (/^5[1-5]/.test(cleaned)) return 'mastercard';\n if (/^3[47]/.test(cleaned)) return 'amex';\n if (/^6(?:011|5)/.test(cleaned)) return 'discover';\n\n return 'unknown';\n }\n\n validateExpiry(month: number, year: number): boolean {\n const now = new Date();\n const currentYear = now.getFullYear();\n const currentMonth = now.getMonth() + 1;\n\n if (month < 1 || month > 12) {\n return false;\n }\n\n const fullYear = year < 100 ? 2000 + year : year;\n\n if (fullYear < currentYear) {\n return false;\n }\n\n if (fullYear === currentYear && month < currentMonth) {\n return false;\n }\n\n return true;\n }\n\n validateCVC(cvc: string, cardType: string = 'unknown'): boolean {\n const cleaned = cvc.replace(/\\D/g, '');\n\n if (cardType === 'amex') {\n return cleaned.length === 4;\n }\n\n return cleaned.length === 3 || cleaned.length === 4;\n }\n\n validateAll(\n cardNumber: string,\n expiryMonth: number,\n expiryYear: number,\n cvc: string\n ): CardValidation {\n const cardType = this.detectCardType(cardNumber);\n\n return {\n number: {\n isValid: this.validateCardNumber(cardNumber),\n cardType: cardType as any,\n },\n expiry: {\n isValid: this.validateExpiry(expiryMonth, expiryYear),\n month: expiryMonth,\n year: expiryYear,\n },\n cvc: {\n isValid: this.validateCVC(cvc, cardType),\n length: cvc.replace(/\\D/g, '').length,\n },\n };\n }\n}\n","export class InputSanitizer {\n static sanitizeCardNumber(input: string): string {\n return input.replace(/\\D/g, '');\n }\n\n static formatCardNumber(input: string): string {\n const cleaned = this.sanitizeCardNumber(input);\n return cleaned.replace(/(\\d{4})/g, '$1 ').trim();\n }\n\n static sanitizeCVC(input: string): string {\n return input.replace(/\\D/g, '').slice(0, 4);\n }\n\n static sanitizeExpiry(input: string): { month: number; year: number } | null {\n const cleaned = input.replace(/\\D/g, '');\n\n if (cleaned.length === 4) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 4), 10),\n };\n } else if (cleaned.length === 6) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 6), 10),\n };\n }\n\n return null;\n }\n}\n","export { VerapayClient } from './client/VerapayClient';\nexport { VerapayService } from './services/VerapayService';\n\nexport type {\n InitialisePaymentRequest,\n InitialisePaymentResponse,\n ProcessPrePaymentRequest,\n} from './services/VerapayService';\n\nexport type {\n VerapayConfig,\n ElementsConfig,\n ProcessPaymentRequest,\n PaymentResult,\n CardValidation,\n ErrorDetails,\n ErrorCode,\n} from './types';\n\nexport {\n VerapayError,\n ValidationError,\n PaymentError,\n ErrorFormatter,\n} from './errors';\n\nexport { CardValidator, InputSanitizer } from './validation';\n\nexport type {\n PaymentExtension,\n DatabaseExtension,\n AnalyticsExtension,\n} from './extensions';\n\nexport const VERSION = '0.0.1';\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/errors/verapay-error.ts","../src/errors/validation-error.ts","../src/errors/payment-error.ts","../src/errors/error-formatter.ts","../src/client/stripe-adapter.ts","../src/client/elements-manager.ts","../src/client/payment-extensions-manager.ts","../src/services/payment-service.ts","../src/services/verapay-service.ts","../src/client/verapay-client.ts","../src/validation/card-validator.ts","../src/validation/input-sanitizer.ts","../src/index.ts"],"names":["VerapayError","_VerapayError","message","code","details","ValidationError","field","metadata","PaymentError","_PaymentError","stripeCode","ErrorFormatter","error","StripeAdapter","stripe","paymentMethodId","clientSecret","result","elements","isUsingIndividualFormElements","address","DEFAULT_CARD_ELEMENT_CONFIG","FIELD_LABELS","ElementsManager","config","selector","elementsConfig","element","mode","fieldType","options","formFieldType","errors","state","handleElementChange","event","PaymentExtensionsManager","extension","request","modifiedRequest","ext","PaymentService","stripeAdapter","elementsManager","verapayService","context","validation","isUsingStripePaymentElement","VerapayService","baseUrl","merchantId","paymentData","response","errorData","data","_VerapayClient","paymentIntentId","loadStripe","paymentResult","amount","currency","partnerFee","uppercaseCurrency","paymentAmount","partnerFeeAmount","value","fieldName","Money","VerapayClient","CardValidator","cardNumber","cleaned","sum","isEven","i","digit","month","year","now","currentYear","currentMonth","fullYear","cvc","cardType","expiryMonth","expiryYear","InputSanitizer","input","VERSION"],"mappings":"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","file":"index.js","sourcesContent":["import type { ErrorDetails } from '../types';\nimport { ErrorCode } from '../types';\n\nexport class VerapayError extends Error {\n public readonly code: ErrorCode;\n public readonly details: ErrorDetails;\n\n constructor(\n message: string,\n code: ErrorCode = ErrorCode.PAYMENT_FAILED,\n details?: Partial<ErrorDetails>\n ) {\n super(message);\n this.name = 'VerapayError';\n this.code = code;\n this.details = {\n code,\n message,\n formattedMessage: this.formatMessage(message, code),\n ...details,\n };\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, VerapayError);\n }\n }\n\n private formatMessage(message: string, code: ErrorCode): string {\n const messageMap: Record<ErrorCode, string> = {\n [ErrorCode.VALIDATION_ERROR]:\n 'Please check your payment information and try again.',\n [ErrorCode.PAYMENT_FAILED]:\n 'Your payment could not be processed. Please try again.',\n [ErrorCode.AUTHENTICATION_FAILED]:\n 'Payment authentication failed. Please try again.',\n [ErrorCode.NETWORK_ERROR]:\n 'Network error. Please check your connection and try again.',\n [ErrorCode.STRIPE_ERROR]:\n 'Payment service error. Please try again later.',\n [ErrorCode.CONFIGURATION_ERROR]:\n 'Configuration error. Please contact support.',\n [ErrorCode.CARD_DECLINED]:\n 'Your card was declined. Please use a different payment method.',\n [ErrorCode.INSUFFICIENT_FUNDS]:\n 'Insufficient funds. Please use a different payment method.',\n [ErrorCode.EXPIRED_CARD]:\n 'Your card has expired. Please use a different payment method.',\n };\n\n return messageMap[code] || message;\n }\n\n toJSON() {\n return {\n name: this.name,\n code: this.code,\n message: this.message,\n details: this.details,\n };\n }\n}\n","import { VerapayError } from './verapay-error';\nimport { ErrorCode } from '../types';\n\nexport class ValidationError extends VerapayError {\n constructor(message: string, field?: string, metadata?: Record<string, any>) {\n super(message, ErrorCode.VALIDATION_ERROR, {\n field,\n metadata,\n });\n this.name = 'ValidationError';\n }\n}\n","import { VerapayError } from './verapay-error';\nimport { ErrorCode } from '../types';\n\nexport class PaymentError extends VerapayError {\n constructor(\n message: string,\n stripeCode?: string,\n metadata?: Record<string, any>\n ) {\n const code = PaymentError.mapStripeCode(stripeCode);\n super(message, code, {\n stripeCode,\n metadata,\n });\n this.name = 'PaymentError';\n }\n\n private static mapStripeCode(stripeCode?: string): ErrorCode {\n if (!stripeCode) return ErrorCode.PAYMENT_FAILED;\n\n const codeMap: Record<string, ErrorCode> = {\n card_declined: ErrorCode.CARD_DECLINED,\n insufficient_funds: ErrorCode.INSUFFICIENT_FUNDS,\n expired_card: ErrorCode.EXPIRED_CARD,\n incorrect_cvc: ErrorCode.VALIDATION_ERROR,\n processing_error: ErrorCode.PAYMENT_FAILED,\n authentication_failed: ErrorCode.AUTHENTICATION_FAILED,\n };\n\n return codeMap[stripeCode] || ErrorCode.PAYMENT_FAILED;\n }\n}\n","import type { ErrorDetails } from '../types';\n\nexport class ErrorFormatter {\n static formatForUser(error: Error | ErrorDetails): string {\n if ('formattedMessage' in error) {\n return error.formattedMessage;\n }\n if (\n 'details' in error &&\n error.details &&\n typeof error.details === 'object' &&\n 'formattedMessage' in error.details &&\n typeof error.details.formattedMessage === 'string'\n ) {\n return error.details.formattedMessage;\n }\n return 'An unexpected error occurred. Please try again.';\n }\n\n static formatForDeveloper(error: Error | ErrorDetails): string {\n if ('code' in error && 'message' in error) {\n return `[${error.code}] ${error.message}`;\n }\n return error.message || 'Unknown error';\n }\n\n static toJSON(error: Error | ErrorDetails): Record<string, any> {\n if ('toJSON' in error && typeof error.toJSON === 'function') {\n return error.toJSON();\n }\n\n return {\n name: (error as Error).name || 'Error',\n message: error.message,\n ...('code' in error && { code: error.code }),\n ...('details' in error && { details: error.details }),\n };\n }\n}\n","import type { PaymentIntent, Stripe, StripeElements } from '@stripe/stripe-js';\nimport { PaymentError } from '../errors';\n\nexport class StripeAdapter {\n constructor(private stripe: Stripe) {}\n\n async confirmPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmPayment({\n clientSecret,\n confirmParams: {\n payment_method: paymentMethodId,\n return_url: window.location.href,\n },\n redirect: 'if_required',\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async confirmCardPayment(\n paymentMethodId: string,\n clientSecret: string\n ): Promise<{ paymentIntent: PaymentIntent }> {\n const result = await this.stripe.confirmCardPayment(clientSecret, {\n payment_method: paymentMethodId,\n });\n\n if (result.error) {\n throw new PaymentError(\n result.error.message || 'Payment failed',\n result.error.code\n );\n }\n\n return result as { paymentIntent: PaymentIntent };\n }\n\n async createPaymentMethod(\n elements: StripeElements,\n isUsingIndividualFormElements: boolean = false\n ): Promise<string> {\n let result;\n\n if (!isUsingIndividualFormElements) {\n result = await this.stripe.createPaymentMethod({\n elements,\n });\n } else {\n // @ts-ignore - Stripe types don't include mode parameter for getElement\n const addressElement = await elements.getElement('address', { mode: 'billing' })!.getValue();\n const address = addressElement!.value;\n\n result = await this.stripe.createPaymentMethod({\n type: 'card',\n card: elements.getElement('cardNumber')!,\n billing_details: {\n name: address.name,\n address: {\n ...address.address,\n line2: address.address.line2 ?? undefined,\n },\n },\n });\n }\n\n if (result.error || !result.paymentMethod) {\n throw new PaymentError(\n result.error?.message || 'Failed to create payment method',\n result.error?.code\n );\n }\n\n return result.paymentMethod.id;\n }\n}\n","import type {\n Stripe,\n StripeElements,\n StripeElement,\n StripePaymentElement,\n StripeCardNumberElement,\n} from '@stripe/stripe-js';\nimport type { VerapayConfig, ValidationError, ValidationResult } from '../types';\nimport { VerapayError, ErrorCode } from '../errors';\n\ntype ElementState = { complete: boolean; error?: string }\n\nconst DEFAULT_CARD_ELEMENT_CONFIG = {\n showIcon: true,\n iconStyle: 'solid' as const,\n placeholders: {\n cardNumber: '1234 1234 1234 1234',\n cardExpiry: 'MM / YY - TESTING',\n cardCvc: 'CVC',\n },\n style: {\n base: {\n color: '#333333',\n fontFamily: 'system-ui, -apple-system, sans-serif',\n fontSize: '16px',\n '::placeholder': { color: '#aab7c4' },\n },\n complete: {\n color: '#333333',\n },\n empty: {},\n invalid: {\n color: '#df1b41',\n },\n },\n}\n\nconst FIELD_LABELS: Record<string, string> = {\n cardNumber: 'Card number',\n cardExpiry: 'Expiry date',\n cardCvc: 'CVC',\n address: 'Address',\n}\n\nexport class ElementsManager {\n private elements: StripeElements | null = null;\n private mountedElements: Map<string, StripeElement> = new Map();\n private elementStates: Map<string, ElementState> = new Map();\n\n constructor(\n private stripe: Stripe,\n private config: VerapayConfig,\n private clientSecret: string\n ) {\n if (!clientSecret) {\n throw new VerapayError(\n 'Client secret not initialized',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n mountPaymentElement(selector: string): void {\n if (!this.elements) {\n const elementsConfig = {\n clientSecret: this.clientSecret,\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n };\n\n this.elements = this.stripe.elements(elementsConfig);\n }\n\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.elements.create('payment', {\n layout: 'tabs',\n }) as StripePaymentElement;\n\n element.mount(selector);\n this.mountedElements.set('payment', element);\n }\n\n mountCardNumberElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardNumber', this.cardElementOptions('cardNumber'));\n }\n\n mountCardExpiryElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardExpiry', this.cardElementOptions('cardExpiry'));\n }\n\n mountCardCvcElement(selector: string): void {\n this.mountIndividualFormElement(selector, 'cardCvc', this.cardElementOptions('cardCvc'));\n }\n\n mountAddressElement(selector: string, mode: 'billing' | 'shipping'): void {\n this.mountIndividualFormElement(selector, 'address', { mode });\n }\n\n private cardElementOptions(fieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc'): Record<string, unknown> {\n const { elementsConfig } = this.config;\n const options: Record<string, unknown> = {\n placeholder: elementsConfig?.placeholders?.[fieldType] ?? DEFAULT_CARD_ELEMENT_CONFIG.placeholders[fieldType],\n style: {\n base: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.base, ...elementsConfig?.style?.base },\n complete: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.complete, ...elementsConfig?.style?.complete },\n empty: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.empty, ...elementsConfig?.style?.empty },\n invalid: { ...DEFAULT_CARD_ELEMENT_CONFIG.style.invalid, ...elementsConfig?.style?.invalid },\n },\n };\n\n if (fieldType === 'cardNumber') {\n options.showIcon = elementsConfig?.showIcon ?? DEFAULT_CARD_ELEMENT_CONFIG.showIcon;\n options.iconStyle = elementsConfig?.iconStyle ?? DEFAULT_CARD_ELEMENT_CONFIG.iconStyle;\n }\n\n return options;\n }\n\n private mountIndividualFormElement(selector: string, formFieldType: 'cardNumber' | 'cardExpiry' | 'cardCvc' | 'address', options?: Record<string, unknown>) {\n const container = document.querySelector(selector);\n\n if (!container) {\n throw new VerapayError(\n `Element not found: ${selector}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const element = this.createIndividualFormElement(formFieldType, options) as StripeCardNumberElement;\n element.mount(selector);\n\n this.mountedElements.set(formFieldType, element);\n this.trackElementState(formFieldType, element);\n }\n\n private createIndividualFormElement(\n formFieldType: any,\n options?: Record<string, unknown>\n ): StripeElement {\n if (!this.elements) {\n // For individual card elements, don't pass clientSecret\n // It's only needed when creating Payment Element or confirming payment\n this.elements = this.stripe.elements({\n appearance: this.config.appearance,\n locale: this.config.locale,\n fonts: this.config.fonts,\n paymentMethodCreation: 'manual',\n });\n }\n\n return this.elements.create(formFieldType, options);\n }\n\n async validate(): Promise<ValidationResult> {\n const errors: ValidationError[] = []\n\n for (const [field, state] of this.elementStates.entries()) {\n if (!state.complete) {\n errors.push({\n field,\n message: state.error ?? `${FIELD_LABELS[field] ?? field} failed validation`,\n })\n }\n }\n\n return { isValid: errors.length === 0, errors }\n }\n\n getElements(): StripeElements | null {\n return this.elements;\n }\n\n unmountAll(): void {\n for (const element of this.mountedElements.values()) {\n element.unmount();\n }\n this.mountedElements.clear();\n this.elementStates.clear();\n }\n\n private trackElementState(field: string, element: StripeElement): void {\n this.elementStates.set(field, { complete: false })\n\n const handleElementChange = (event: { complete: boolean; error?: { message: string } }) => {\n this.elementStates.set(field, { complete: event.complete, error: event.error?.message })\n };\n\n (element as any).on('change', handleElementChange)\n }\n}\n","import type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport type { PaymentExtension } from '../extensions'\n\nexport class PaymentExtensionsManager {\n private extensions: PaymentExtension[] = []\n\n add(extension: PaymentExtension): void {\n this.extensions.push(extension)\n }\n\n async runBeforePayment(request: ProcessPaymentRequest): Promise<ProcessPaymentRequest> {\n let modifiedRequest = request\n for (const ext of this.extensions) {\n if (ext.beforePayment) {\n modifiedRequest = await ext.beforePayment(modifiedRequest)\n }\n }\n return modifiedRequest\n }\n\n async runAfterPayment(result: PaymentResult): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.afterPayment)\n .map((ext) => ext.afterPayment!(result)),\n )\n }\n\n async runOnError(error: Error): Promise<void> {\n await Promise.all(\n this.extensions\n .filter((ext) => ext.onPaymentError)\n .map((ext) => ext.onPaymentError!(error)),\n )\n }\n}\n","import { StripeAdapter } from '../client/stripe-adapter'\nimport { ElementsManager } from '../client/elements-manager'\nimport { ErrorCode, VerapayError } from '../errors'\nimport { VerapayService } from './verapay-service'\nimport type { ProcessPaymentRequest, PaymentResult } from '../types'\nimport { StripeElements } from '@stripe/stripe-js';\n\nexport interface ProcessPaymentContext {\n merchantId: string\n paymentIntentId: string\n clientSecret: string\n isUsingStripePaymentElement: boolean\n isUsingIndividualFormElements: boolean\n}\n\nexport class PaymentService {\n constructor(\n private stripeAdapter: StripeAdapter,\n private elementsManager: ElementsManager,\n private verapayService: VerapayService,\n ) {}\n\n async process(request: ProcessPaymentRequest, context: ProcessPaymentContext): Promise<PaymentResult> {\n const elements = this.elementsManager.getElements()\n\n await this.validatePaymentCanProceed(elements, context);\n\n await elements!.submit()\n\n const paymentMethodId = await this.stripeAdapter.createPaymentMethod(\n elements!,\n context.isUsingIndividualFormElements,\n )\n\n await this.verapayService.processPrePayment({\n merchantId: context.merchantId,\n paymentIntentId: context.paymentIntentId,\n paymentMethodId,\n customerData: {\n email: request.customerEmail,\n firstName: request.customerFirstName,\n lastName: request.customerLastName,\n },\n description: request.description,\n metadata: request.metadata,\n })\n\n return this.confirmPayment(paymentMethodId, context)\n }\n\n private async validatePaymentCanProceed(elements: StripeElements | null, context: ProcessPaymentContext) {\n if (!elements) {\n throw new VerapayError('Payment form not mounted', ErrorCode.CONFIGURATION_ERROR)\n }\n\n if (context.isUsingStripePaymentElement && context.isUsingIndividualFormElements) {\n throw new VerapayError('Both forms of payment form in use');\n }\n\n if (context.isUsingIndividualFormElements) {\n const validation = await this.elementsManager.validate()\n if (!validation.isValid) {\n throw new VerapayError(validation.errors[0].message, ErrorCode.VALIDATION_ERROR)\n }\n }\n }\n\n private async confirmPayment(\n paymentMethodId: string,\n context: ProcessPaymentContext,\n ): Promise<PaymentResult> {\n const { clientSecret, isUsingStripePaymentElement, isUsingIndividualFormElements } = context\n\n let result\n\n if (isUsingStripePaymentElement) {\n result = await this.stripeAdapter.confirmPayment(paymentMethodId, clientSecret)\n } else if (isUsingIndividualFormElements) {\n result = await this.stripeAdapter.confirmCardPayment(paymentMethodId, clientSecret)\n }\n\n return this.formatPaymentResult(result)\n }\n\n private formatPaymentResult(result: any): PaymentResult {\n return {\n success: result.paymentIntent.status === 'succeeded',\n paymentIntentId: result.paymentIntent.id,\n status: result.paymentIntent.status,\n }\n }\n}\n","import { ErrorCode, VerapayError } from '../errors';\nimport { PaymentData } from '../types';\n\nexport interface InitialisePaymentRequest {\n merchantId: string;\n paymentData: PaymentData;\n}\n\nexport interface InitialisePaymentResponse {\n paymentIntentId: string;\n clientSecret: string;\n connectAccountId: string;\n}\n\nexport interface ProcessPrePaymentRequest {\n merchantId: string;\n paymentIntentId: string;\n paymentMethodId: string;\n customerData: Record<string, any>;\n description?: string;\n metadata?: Record<string, string>;\n}\n\nexport class VerapayService {\n private readonly baseUrl: string;\n\n constructor(baseUrl: string = 'http://localhost:3333') {\n this.baseUrl = baseUrl;\n }\n\n async initialisePayment(\n request: InitialisePaymentRequest\n ): Promise<InitialisePaymentResponse> {\n const { merchantId, paymentData } = request;\n\n try {\n const response = await fetch(`${this.baseUrl}/api/initialise-payment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-api-key': 'example.api.key',\n },\n body: JSON.stringify({\n merchantId,\n paymentData: { ...paymentData, paymentMethodType: 'card' },\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n const data = await response.json();\n\n if (!data.clientSecret || !data.paymentIntentId) {\n throw new VerapayError(\n 'Missing clientSecret or paymentIntentId in server response',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n return {\n paymentIntentId: data.paymentIntentId,\n clientSecret: data.clientSecret,\n connectAccountId: data.connectAccountId,\n };\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n\n async processPrePayment(request: ProcessPrePaymentRequest): Promise<void> {\n try {\n const response = await fetch(`${this.baseUrl}/api/process-prepayment`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'x-forwarded-for': 'example.ip.addr',\n },\n body: JSON.stringify({\n merchantId: request.merchantId,\n paymentIntentId: request.paymentIntentId,\n paymentMethodId: request.paymentMethodId,\n customerData: request.customerData,\n description: request.description,\n metadata: request.metadata,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new VerapayError(\n errorData.error || `HTTP error! status: ${response.status}`,\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n } catch (error) {\n if (error instanceof VerapayError) {\n throw error;\n }\n throw new VerapayError(\n error instanceof Error ? error.message : 'Unknown error occurred',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n }\n}\n","import { loadStripe } from '@stripe/stripe-js';\nimport { Money } from 'ts-money';\nimport { StripeAdapter } from './stripe-adapter';\nimport { ElementsManager } from './elements-manager';\nimport type { PaymentExtension } from '../extensions';\nimport { PaymentExtensionsManager } from './payment-extensions-manager';\nimport { PaymentService } from '../services/payment-service';\nimport {\n ErrorCode,\n VerapayError,\n PaymentError,\n ValidationError,\n} from '../errors';\nimport { VerapayService } from '../services/verapay-service';\nimport type {\n VerapayConfig,\n ProcessPaymentRequest,\n PaymentResult,\n} from '../types';\n\nexport class VerapayClient {\n private static readonly STRIPE_PUBLISHABLE_KEY =\n 'pk_test_51T6ts0GU0Zq3ZuYLSciVz44jEsdaUBd4HRHIQCFSRt7VfBJt9vTJGJAXKYMynC64Ot0cCw9XjTGxCd8ZC44tfMkl00jWhD2UNq';\n\n private config: VerapayConfig;\n private verapayService: VerapayService;\n private extensionsManager: PaymentExtensionsManager;\n\n private stripeAdapter: StripeAdapter | null = null;\n private elementsManager: ElementsManager | null = null;\n private paymentService: PaymentService | null = null;\n\n private isUsingStripePaymentElement: boolean = false;\n private isUsingIndividualFormElements: boolean = false;\n\n private clientSecret: string | null = null;\n private paymentIntentId: string | null = null;\n\n constructor(config: VerapayConfig) {\n this.config = config;\n this.verapayService = new VerapayService();\n this.extensionsManager = new PaymentExtensionsManager();\n }\n\n async initialize(): Promise<void> {\n this.validatePaymentInitialisation()\n\n const { clientSecret, paymentIntentId } =\n await this.verapayService.initialisePayment({\n merchantId: this.config.merchantId,\n paymentData: this.config.paymentData\n });\n\n this.clientSecret = clientSecret;\n this.paymentIntentId = paymentIntentId;\n\n const stripe = await loadStripe(VerapayClient.STRIPE_PUBLISHABLE_KEY);\n\n if (!stripe) {\n throw new VerapayError(\n 'Failed to load Stripe',\n ErrorCode.CONFIGURATION_ERROR\n );\n }\n\n this.stripeAdapter = new StripeAdapter(stripe);\n this.elementsManager = new ElementsManager(\n stripe,\n this.config,\n clientSecret\n );\n this.paymentService = new PaymentService(\n this.stripeAdapter,\n this.elementsManager,\n this.verapayService\n );\n }\n\n async processPayment(request: ProcessPaymentRequest): Promise<PaymentResult> {\n await this.ensureInitialized();\n\n let modifiedRequest =\n await this.extensionsManager.runBeforePayment(request);\n\n try {\n const paymentResult = await this.paymentService!.process(\n modifiedRequest,\n {\n merchantId: this.config.merchantId,\n paymentIntentId: this.paymentIntentId!,\n clientSecret: this.clientSecret!,\n isUsingStripePaymentElement: this.isUsingStripePaymentElement,\n isUsingIndividualFormElements: this.isUsingIndividualFormElements,\n }\n );\n\n await this.extensionsManager.runAfterPayment(paymentResult);\n\n return paymentResult;\n } catch (error) {\n await this.extensionsManager.runOnError(error as Error);\n throw this.handlePaymentError(error);\n }\n }\n\n async mountPaymentForm(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountPaymentElement(selector);\n this.isUsingStripePaymentElement = true;\n }\n\n async mountCardNumber(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardNumberElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardExpiry(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardExpiryElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountCardCvc(selector: string): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountCardCvcElement(selector);\n this.isUsingIndividualFormElements = true;\n }\n\n async mountAddress(\n selector: string,\n mode: 'billing' | 'shipping'\n ): Promise<void> {\n await this.ensureInitialized();\n this.elementsManager!.mountAddressElement(selector, mode);\n this.isUsingIndividualFormElements = true;\n }\n\n addExtension(extension: PaymentExtension): void {\n this.extensionsManager.add(extension);\n }\n\n private async ensureInitialized(): Promise<void> {\n if (!this.stripeAdapter) {\n await this.initialize();\n }\n }\n\n private validatePaymentInitialisation(): void {\n const { amount, currency, partnerFee } = this.config.paymentData;\n\n if (!currency) {\n throw new ValidationError('Currency is required', 'currency');\n }\n\n const uppercaseCurrency = currency.toUpperCase();\n\n const paymentAmount = this.toMoney(amount, uppercaseCurrency, 'amount');\n\n if (paymentAmount.isZero() || paymentAmount.isNegative()) {\n throw new ValidationError('Amount must be greater than 0', 'amount');\n }\n\n if (partnerFee !== undefined) {\n const partnerFeeAmount = this.toMoney(partnerFee, uppercaseCurrency, 'partnerFee');\n\n if (partnerFeeAmount.isNegative()) {\n throw new ValidationError('partnerFee cannot be negative', 'partnerFee');\n }\n\n if (partnerFeeAmount.greaterThan(paymentAmount)) {\n throw new ValidationError('partnerFee cannot exceed the payment amount', 'partnerFee');\n }\n }\n }\n\n private toMoney(value: number, currency: string, fieldName: string): Money {\n try {\n return Money.fromInteger(value, currency);\n } catch {\n throw new ValidationError(\n `${fieldName} must be an integer in the smallest currency unit (e.g., cents for USD)`,\n fieldName\n );\n }\n }\n\n private handlePaymentError(error: any): Error {\n if (error instanceof VerapayError) {\n return error;\n }\n return new PaymentError(error.message || 'Payment failed', error.code);\n }\n}\n","import type { CardValidation } from '../types';\n\nexport class CardValidator {\n validateCardNumber(cardNumber: string): boolean {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (cleaned.length < 13 || cleaned.length > 19) {\n return false;\n }\n\n let sum = 0;\n let isEven = false;\n\n for (let i = cleaned.length - 1; i >= 0; i--) {\n let digit = parseInt(cleaned[i], 10);\n\n if (isEven) {\n digit *= 2;\n if (digit > 9) {\n digit -= 9;\n }\n }\n\n sum += digit;\n isEven = !isEven;\n }\n\n return sum % 10 === 0;\n }\n\n detectCardType(cardNumber: string): string {\n const cleaned = cardNumber.replace(/\\D/g, '');\n\n if (/^4/.test(cleaned)) return 'visa';\n if (/^5[1-5]/.test(cleaned)) return 'mastercard';\n if (/^3[47]/.test(cleaned)) return 'amex';\n if (/^6(?:011|5)/.test(cleaned)) return 'discover';\n\n return 'unknown';\n }\n\n validateExpiry(month: number, year: number): boolean {\n const now = new Date();\n const currentYear = now.getFullYear();\n const currentMonth = now.getMonth() + 1;\n\n if (month < 1 || month > 12) {\n return false;\n }\n\n const fullYear = year < 100 ? 2000 + year : year;\n\n if (fullYear < currentYear) {\n return false;\n }\n\n if (fullYear === currentYear && month < currentMonth) {\n return false;\n }\n\n return true;\n }\n\n validateCVC(cvc: string, cardType: string = 'unknown'): boolean {\n const cleaned = cvc.replace(/\\D/g, '');\n\n if (cardType === 'amex') {\n return cleaned.length === 4;\n }\n\n return cleaned.length === 3 || cleaned.length === 4;\n }\n\n validateAll(\n cardNumber: string,\n expiryMonth: number,\n expiryYear: number,\n cvc: string\n ): CardValidation {\n const cardType = this.detectCardType(cardNumber);\n\n return {\n number: {\n isValid: this.validateCardNumber(cardNumber),\n cardType: cardType as any,\n },\n expiry: {\n isValid: this.validateExpiry(expiryMonth, expiryYear),\n month: expiryMonth,\n year: expiryYear,\n },\n cvc: {\n isValid: this.validateCVC(cvc, cardType),\n length: cvc.replace(/\\D/g, '').length,\n },\n };\n }\n}\n","export class InputSanitizer {\n static sanitizeCardNumber(input: string): string {\n return input.replace(/\\D/g, '');\n }\n\n static formatCardNumber(input: string): string {\n const cleaned = this.sanitizeCardNumber(input);\n return cleaned.replace(/(\\d{4})/g, '$1 ').trim();\n }\n\n static sanitizeCVC(input: string): string {\n return input.replace(/\\D/g, '').slice(0, 4);\n }\n\n static sanitizeExpiry(input: string): { month: number; year: number } | null {\n const cleaned = input.replace(/\\D/g, '');\n\n if (cleaned.length === 4) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 4), 10),\n };\n } else if (cleaned.length === 6) {\n return {\n month: parseInt(cleaned.slice(0, 2), 10),\n year: parseInt(cleaned.slice(2, 6), 10),\n };\n }\n\n return null;\n }\n}\n","export { VerapayClient } from './client/verapay-client';\nexport { VerapayService } from './services/verapay-service';\n\nexport type {\n InitialisePaymentRequest,\n InitialisePaymentResponse,\n ProcessPrePaymentRequest,\n} from './services/verapay-service';\n\nexport type {\n VerapayConfig,\n ElementsConfig,\n ProcessPaymentRequest,\n PaymentResult,\n CardValidation,\n ErrorDetails,\n ErrorCode,\n} from './types';\n\nexport {\n VerapayError,\n ValidationError,\n PaymentError,\n ErrorFormatter,\n} from './errors';\n\nexport { CardValidator, InputSanitizer } from './validation';\n\nexport type {\n PaymentExtension,\n DatabaseExtension,\n AnalyticsExtension,\n} from './extensions';\n\nexport const VERSION = '0.0.1';\n"]}
|