@porulle/adapter-stripe 0.10.5 → 0.10.8
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/dist/index.d.ts.map +1 -1
- package/dist/index.js +32 -6
- package/package.json +2 -2
- package/src/index.ts +36 -6
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,QAAQ,CAAC;AAC5B,OAAO,EAGL,KAAK,cAAc,EAMpB,MAAM,eAAe,CAAC;AAEvB,MAAM,WAAW,oBAAoB;IACnC,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,CAAC,gBAAgB,CAAC;CACtC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,QAAQ,CAAC;AAC5B,OAAO,EAGL,KAAK,cAAc,EAMpB,MAAM,eAAe,CAAC;AAEvB,MAAM,WAAW,oBAAoB;IACnC,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,CAAC,gBAAgB,CAAC;CACtC;AAqBD,wBAAgB,aAAa,CAAC,OAAO,EAAE,oBAAoB,GAAG,cAAc,CAoJ3E"}
|
package/dist/index.js
CHANGED
|
@@ -1,8 +1,31 @@
|
|
|
1
1
|
import Stripe from "stripe";
|
|
2
2
|
import { Err, Ok, } from "@porulle/core";
|
|
3
|
+
function providerErrorMessage(error, fallback) {
|
|
4
|
+
if (error && typeof error === "object") {
|
|
5
|
+
const candidate = error;
|
|
6
|
+
for (const nested of [candidate.error, candidate.cause, candidate.reason]) {
|
|
7
|
+
if (nested && nested !== error) {
|
|
8
|
+
const message = providerErrorMessage(nested, "");
|
|
9
|
+
if (message)
|
|
10
|
+
return message;
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
if (typeof candidate.message === "string" && candidate.message && candidate.message !== "[object ErrorEvent]") {
|
|
14
|
+
return candidate.message;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
if (error instanceof Error && error.message && error.message !== "[object ErrorEvent]") {
|
|
18
|
+
return error.message;
|
|
19
|
+
}
|
|
20
|
+
return fallback;
|
|
21
|
+
}
|
|
3
22
|
export function stripePayment(options) {
|
|
4
23
|
const stripe = new Stripe(options.secretKey, {
|
|
5
24
|
apiVersion: options.apiVersion ?? "2025-08-27.basil",
|
|
25
|
+
// Stripe's fetch transport works in Cloudflare Workers and remains valid in
|
|
26
|
+
// Node/Bun. The default Node HTTP client can surface opaque ErrorEvents in
|
|
27
|
+
// workerd before a request ever reaches Stripe.
|
|
28
|
+
httpClient: Stripe.createFetchHttpClient(globalThis.fetch.bind(globalThis)),
|
|
6
29
|
});
|
|
7
30
|
return {
|
|
8
31
|
providerId: "stripe",
|
|
@@ -41,7 +64,7 @@ export function stripePayment(options) {
|
|
|
41
64
|
catch (error) {
|
|
42
65
|
return Err({
|
|
43
66
|
code: "PAYMENT_INTENT_CREATE_FAILED",
|
|
44
|
-
message: error
|
|
67
|
+
message: providerErrorMessage(error, "Stripe payment intent creation failed."),
|
|
45
68
|
});
|
|
46
69
|
}
|
|
47
70
|
},
|
|
@@ -57,7 +80,7 @@ export function stripePayment(options) {
|
|
|
57
80
|
catch (error) {
|
|
58
81
|
return Err({
|
|
59
82
|
code: "PAYMENT_CAPTURE_FAILED",
|
|
60
|
-
message: error
|
|
83
|
+
message: providerErrorMessage(error, "Stripe capture failed."),
|
|
61
84
|
});
|
|
62
85
|
}
|
|
63
86
|
},
|
|
@@ -81,7 +104,7 @@ export function stripePayment(options) {
|
|
|
81
104
|
catch (error) {
|
|
82
105
|
return Err({
|
|
83
106
|
code: "PAYMENT_REFUND_FAILED",
|
|
84
|
-
message: error
|
|
107
|
+
message: providerErrorMessage(error, "Stripe refund failed."),
|
|
85
108
|
});
|
|
86
109
|
}
|
|
87
110
|
},
|
|
@@ -93,7 +116,7 @@ export function stripePayment(options) {
|
|
|
93
116
|
catch (error) {
|
|
94
117
|
return Err({
|
|
95
118
|
code: "PAYMENT_CANCEL_FAILED",
|
|
96
|
-
message: error
|
|
119
|
+
message: providerErrorMessage(error, "Stripe cancellation failed."),
|
|
97
120
|
});
|
|
98
121
|
}
|
|
99
122
|
},
|
|
@@ -113,7 +136,10 @@ export function stripePayment(options) {
|
|
|
113
136
|
});
|
|
114
137
|
}
|
|
115
138
|
const body = await request.text();
|
|
116
|
-
|
|
139
|
+
// Workers expose Web Crypto through an asynchronous provider. Stripe's
|
|
140
|
+
// synchronous verifier throws under workerd even for a valid signature.
|
|
141
|
+
// The async verifier works across Workers, Node, and Bun.
|
|
142
|
+
const event = await stripe.webhooks.constructEventAsync(body, signature, options.webhookSecret);
|
|
117
143
|
return Ok({
|
|
118
144
|
id: event.id,
|
|
119
145
|
type: event.type,
|
|
@@ -123,7 +149,7 @@ export function stripePayment(options) {
|
|
|
123
149
|
catch (error) {
|
|
124
150
|
return Err({
|
|
125
151
|
code: "WEBHOOK_VERIFICATION_FAILED",
|
|
126
|
-
message: error
|
|
152
|
+
message: providerErrorMessage(error, "Stripe webhook verification failed."),
|
|
127
153
|
});
|
|
128
154
|
}
|
|
129
155
|
},
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@porulle/adapter-stripe",
|
|
3
|
-
"version": "0.10.
|
|
3
|
+
"version": "0.10.8",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"exports": {
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
},
|
|
13
13
|
"dependencies": {
|
|
14
14
|
"stripe": "^18.5.0",
|
|
15
|
-
"@porulle/core": "0.10.
|
|
15
|
+
"@porulle/core": "0.10.8"
|
|
16
16
|
},
|
|
17
17
|
"devDependencies": {
|
|
18
18
|
"@types/node": "^24.5.2",
|
package/src/index.ts
CHANGED
|
@@ -16,9 +16,32 @@ export interface StripeAdapterOptions {
|
|
|
16
16
|
apiVersion?: Stripe.LatestApiVersion;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
+
function providerErrorMessage(error: unknown, fallback: string): string {
|
|
20
|
+
if (error && typeof error === "object") {
|
|
21
|
+
const candidate = error as { error?: unknown; cause?: unknown; reason?: unknown; message?: unknown };
|
|
22
|
+
for (const nested of [candidate.error, candidate.cause, candidate.reason]) {
|
|
23
|
+
if (nested && nested !== error) {
|
|
24
|
+
const message = providerErrorMessage(nested, "");
|
|
25
|
+
if (message) return message;
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
if (typeof candidate.message === "string" && candidate.message && candidate.message !== "[object ErrorEvent]") {
|
|
29
|
+
return candidate.message;
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
if (error instanceof Error && error.message && error.message !== "[object ErrorEvent]") {
|
|
33
|
+
return error.message;
|
|
34
|
+
}
|
|
35
|
+
return fallback;
|
|
36
|
+
}
|
|
37
|
+
|
|
19
38
|
export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
20
39
|
const stripe = new Stripe(options.secretKey, {
|
|
21
40
|
apiVersion: options.apiVersion ?? "2025-08-27.basil",
|
|
41
|
+
// Stripe's fetch transport works in Cloudflare Workers and remains valid in
|
|
42
|
+
// Node/Bun. The default Node HTTP client can surface opaque ErrorEvents in
|
|
43
|
+
// workerd before a request ever reaches Stripe.
|
|
44
|
+
httpClient: Stripe.createFetchHttpClient(globalThis.fetch.bind(globalThis)),
|
|
22
45
|
});
|
|
23
46
|
|
|
24
47
|
return {
|
|
@@ -62,7 +85,7 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
62
85
|
} catch (error) {
|
|
63
86
|
return Err({
|
|
64
87
|
code: "PAYMENT_INTENT_CREATE_FAILED",
|
|
65
|
-
message: error
|
|
88
|
+
message: providerErrorMessage(error, "Stripe payment intent creation failed."),
|
|
66
89
|
});
|
|
67
90
|
}
|
|
68
91
|
},
|
|
@@ -78,7 +101,7 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
78
101
|
} catch (error) {
|
|
79
102
|
return Err({
|
|
80
103
|
code: "PAYMENT_CAPTURE_FAILED",
|
|
81
|
-
message: error
|
|
104
|
+
message: providerErrorMessage(error, "Stripe capture failed."),
|
|
82
105
|
});
|
|
83
106
|
}
|
|
84
107
|
},
|
|
@@ -103,7 +126,7 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
103
126
|
} catch (error) {
|
|
104
127
|
return Err({
|
|
105
128
|
code: "PAYMENT_REFUND_FAILED",
|
|
106
|
-
message: error
|
|
129
|
+
message: providerErrorMessage(error, "Stripe refund failed."),
|
|
107
130
|
});
|
|
108
131
|
}
|
|
109
132
|
},
|
|
@@ -115,7 +138,7 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
115
138
|
} catch (error) {
|
|
116
139
|
return Err({
|
|
117
140
|
code: "PAYMENT_CANCEL_FAILED",
|
|
118
|
-
message: error
|
|
141
|
+
message: providerErrorMessage(error, "Stripe cancellation failed."),
|
|
119
142
|
});
|
|
120
143
|
}
|
|
121
144
|
},
|
|
@@ -138,7 +161,14 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
138
161
|
}
|
|
139
162
|
|
|
140
163
|
const body = await request.text();
|
|
141
|
-
|
|
164
|
+
// Workers expose Web Crypto through an asynchronous provider. Stripe's
|
|
165
|
+
// synchronous verifier throws under workerd even for a valid signature.
|
|
166
|
+
// The async verifier works across Workers, Node, and Bun.
|
|
167
|
+
const event = await stripe.webhooks.constructEventAsync(
|
|
168
|
+
body,
|
|
169
|
+
signature,
|
|
170
|
+
options.webhookSecret,
|
|
171
|
+
);
|
|
142
172
|
|
|
143
173
|
return Ok({
|
|
144
174
|
id: event.id,
|
|
@@ -148,7 +178,7 @@ export function stripePayment(options: StripeAdapterOptions): PaymentAdapter {
|
|
|
148
178
|
} catch (error) {
|
|
149
179
|
return Err({
|
|
150
180
|
code: "WEBHOOK_VERIFICATION_FAILED",
|
|
151
|
-
message: error
|
|
181
|
+
message: providerErrorMessage(error, "Stripe webhook verification failed."),
|
|
152
182
|
});
|
|
153
183
|
}
|
|
154
184
|
},
|