@sixtyninecommerce/client 0.25.0 → 0.27.0
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 +21 -5
- package/dist/admin/http.d.ts.map +1 -1
- package/dist/admin/http.js +51 -69
- package/dist/admin/http.js.map +1 -1
- package/dist/commerce/quotes.d.ts.map +1 -1
- package/dist/commerce/quotes.js +14 -1
- package/dist/commerce/quotes.js.map +1 -1
- package/dist/content/forms.d.ts.map +1 -1
- package/dist/content/forms.js +13 -5
- package/dist/content/forms.js.map +1 -1
- package/dist/core/context.d.ts.map +1 -1
- package/dist/core/context.js +91 -34
- package/dist/core/context.js.map +1 -1
- package/dist/core/http.d.ts +11 -0
- package/dist/core/http.d.ts.map +1 -1
- package/dist/core/http.js +139 -363
- package/dist/core/http.js.map +1 -1
- package/dist/errors.d.ts +85 -24
- package/dist/errors.d.ts.map +1 -1
- package/dist/errors.js +93 -31
- package/dist/errors.js.map +1 -1
- package/dist/events/envelope.d.ts +4 -56
- package/dist/events/envelope.d.ts.map +1 -1
- package/dist/events/envelope.js +6 -12
- package/dist/events/envelope.js.map +1 -1
- package/dist/events/index.d.ts +1 -1
- package/dist/events/index.d.ts.map +1 -1
- package/dist/events/payloads.d.ts +11 -172
- package/dist/events/payloads.d.ts.map +1 -1
- package/dist/events/payloads.js +10 -12
- package/dist/events/payloads.js.map +1 -1
- package/dist/index.d.ts +7 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -1
- package/dist/types.d.ts +8 -0
- package/dist/types.d.ts.map +1 -1
- package/package.json +4 -1
- package/dist/core/headers.d.ts +0 -5
- package/dist/core/headers.d.ts.map +0 -1
- package/dist/core/headers.js +0 -29
- package/dist/core/headers.js.map +0 -1
package/README.md
CHANGED
|
@@ -410,19 +410,35 @@ import { PRESETS, getResponsiveImageData } from '@sixtyninecommerce/client/media
|
|
|
410
410
|
|
|
411
411
|
## Error Handling
|
|
412
412
|
|
|
413
|
-
|
|
413
|
+
Every error this SDK throws is a `StorefrontError`, and every `StorefrontError` is a
|
|
414
|
+
`PlatformError` from [`@sixtyninecommerce/core`](https://www.npmjs.com/package/@sixtyninecommerce/core)
|
|
415
|
+
— the same hierarchy `@sixtyninecommerce/admin` throws, so one `catch` covers both SDKs and one
|
|
416
|
+
`error.code` is what you branch on. Both SDKs depend on `core` by range, so npm resolves one copy
|
|
417
|
+
of it; a tree forced to hold two copies loses the cross-package `instanceof`, as it would for any
|
|
418
|
+
shared base class.
|
|
414
419
|
|
|
415
420
|
```typescript
|
|
416
|
-
import { MutationError } from '@sixtyninecommerce/client';
|
|
421
|
+
import { MutationError, PlatformError, StorefrontError } from '@sixtyninecommerce/client';
|
|
417
422
|
|
|
418
423
|
try {
|
|
419
424
|
await client.commerce.addToCart(variantId, 100);
|
|
420
425
|
} catch (error) {
|
|
421
426
|
if (error instanceof MutationError) {
|
|
422
|
-
// error.
|
|
423
|
-
// error.
|
|
424
|
-
// error.
|
|
427
|
+
// error.code — "INSUFFICIENT_STOCK", the REASON, when the engine sent one
|
|
428
|
+
// error.errorCode — "INSUFFICIENT_STOCK_ERROR", the Vendure ErrorResult type
|
|
429
|
+
// error.message — "Only 3 items available"
|
|
430
|
+
// error.fields — { quantityAvailable: 3 }
|
|
431
|
+
// error.lines — the cart rows the shopper has to fix
|
|
432
|
+
} else if (error instanceof StorefrontError) {
|
|
433
|
+
// error.code / error.status — the platform code and HTTP status
|
|
434
|
+
// error.statusCode — the same status, `undefined` when there was none
|
|
435
|
+
// error.details — [{ field?, code, message }]
|
|
436
|
+
// error.retryAfterSeconds — set on a 429
|
|
437
|
+
// error.traceId — W3C trace id, on failures the service ANSWERED
|
|
438
|
+
// (not on a timeout, abort or network failure)
|
|
439
|
+
// error.problem — the RFC 9457 body, when the service sent one
|
|
425
440
|
}
|
|
441
|
+
// `error instanceof PlatformError` is true for both.
|
|
426
442
|
}
|
|
427
443
|
```
|
|
428
444
|
|
package/dist/admin/http.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"http.d.ts","sourceRoot":"","sources":["../../src/admin/http.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"http.d.ts","sourceRoot":"","sources":["../../src/admin/http.ts"],"names":[],"mappings":"AAOA,OAAO,EAAE,KAAK,WAAW,EAAsC,MAAM,cAAc,CAAC;AACpF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAElD;;;;;;GAMG;AAEH,MAAM,WAAW,eAAe;IAC9B,kDAAkD;IAClD,OAAO,EAAE,MAAM,CAAC;IAChB,+DAA+D;IAC/D,OAAO,EAAE,WAAW,CAAC;IACrB,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,EAAE,OAAO,UAAU,CAAC,KAAK,CAAC;CAChC;AAED,MAAM,WAAW,SAAS;IACxB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,OAAO,EAAE,OAAO,CAAC,EAAE,cAAc,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;CAChG;AAID,wBAAgB,eAAe,CAAC,MAAM,EAAE,eAAe,GAAG,SAAS,CA6ElE"}
|
package/dist/admin/http.js
CHANGED
|
@@ -1,80 +1,62 @@
|
|
|
1
|
+
import { createTransport, } from '@sixtyninecommerce/core';
|
|
1
2
|
import { REQUEST_TIMEOUT_MS } from '../constants.js';
|
|
2
|
-
import { StorefrontError } from '../errors.js';
|
|
3
|
-
|
|
4
|
-
async function toAdminError(response, service) {
|
|
5
|
-
let body = {};
|
|
6
|
-
try {
|
|
7
|
-
const parsed = await response.json();
|
|
8
|
-
if (parsed && typeof parsed === 'object') {
|
|
9
|
-
body = parsed;
|
|
10
|
-
}
|
|
11
|
-
}
|
|
12
|
-
catch {
|
|
13
|
-
// Non-JSON error body — fall back to the status line.
|
|
14
|
-
}
|
|
15
|
-
const rawMessage = body.message;
|
|
16
|
-
const message = Array.isArray(rawMessage)
|
|
17
|
-
? rawMessage.join('; ')
|
|
18
|
-
: typeof rawMessage === 'string' && rawMessage.length > 0
|
|
19
|
-
? rawMessage
|
|
20
|
-
: `${service} returned ${String(response.status)}: ${response.statusText}`;
|
|
21
|
-
const details = Array.isArray(body.details) ? body.details : undefined;
|
|
22
|
-
const retryAfterSeconds = typeof body.retry_after_seconds === 'number' ? body.retry_after_seconds : undefined;
|
|
23
|
-
return new StorefrontError(message, service, response.status, undefined, details, retryAfterSeconds);
|
|
24
|
-
}
|
|
3
|
+
import { StorefrontError, toStorefrontError } from '../errors.js';
|
|
4
|
+
const METHODS = new Set(['GET', 'POST', 'PUT', 'PATCH', 'DELETE']);
|
|
25
5
|
export function createAdminHttp(config) {
|
|
6
|
+
if (config.service === 'vendure') {
|
|
7
|
+
throw new StorefrontError('The admin authoring client talks to the CMS and the plugins service only.', 'vendure');
|
|
8
|
+
}
|
|
9
|
+
const service = config.service;
|
|
26
10
|
const base = config.baseUrl.replace(/\/+$/, '');
|
|
11
|
+
/**
|
|
12
|
+
* The channel, known by ID ONLY.
|
|
13
|
+
*
|
|
14
|
+
* An admin session addresses a tenant by channel id and never holds that
|
|
15
|
+
* channel's public token — which is why `pluginsHeaders` stamps no
|
|
16
|
+
* `vendure-token` for an empty one. The other fields are unused on this path:
|
|
17
|
+
* nothing here reads a currency or a language off the channel.
|
|
18
|
+
*/
|
|
19
|
+
const channel = {
|
|
20
|
+
id: config.channelId,
|
|
21
|
+
code: config.channelId,
|
|
22
|
+
token: '',
|
|
23
|
+
defaultLanguageCode: '',
|
|
24
|
+
defaultCurrencyCode: '',
|
|
25
|
+
pricesIncludeTax: false,
|
|
26
|
+
customFields: {},
|
|
27
|
+
};
|
|
28
|
+
const transport = createTransport({
|
|
29
|
+
// Both point at the one service this client was built for; `service` below
|
|
30
|
+
// is what picks between them.
|
|
31
|
+
urls: { vendureUrl: base, cmsUrl: base, pluginsUrl: base },
|
|
32
|
+
principal: { kind: 'bearer', token: config.adminToken },
|
|
33
|
+
tenant: { scope: { kind: 'channel', code: config.channelId } },
|
|
34
|
+
channels: { resolve: () => Promise.resolve(channel), invalidate: () => undefined },
|
|
35
|
+
fetch: config.fetch,
|
|
36
|
+
timeoutMs: REQUEST_TIMEOUT_MS,
|
|
37
|
+
// One attempt, as this surface has always had: these are authoring writes
|
|
38
|
+
// against endpoints that do not deduplicate, and `redirects.import` is a
|
|
39
|
+
// bulk upsert nobody wants run twice behind their back.
|
|
40
|
+
retry: { attempts: 1 },
|
|
41
|
+
// The authoring methods read and write the services' own wire spelling
|
|
42
|
+
// (`old_path`, `created_at`); converting underneath them would rename
|
|
43
|
+
// every key they pass and read.
|
|
44
|
+
convertCase: false,
|
|
45
|
+
});
|
|
27
46
|
async function request(method, path, body, options) {
|
|
28
|
-
const
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
let externalListener = null;
|
|
32
|
-
if (external) {
|
|
33
|
-
if (external.aborted) {
|
|
34
|
-
controller.abort();
|
|
35
|
-
}
|
|
36
|
-
else {
|
|
37
|
-
externalListener = () => controller.abort();
|
|
38
|
-
external.addEventListener('abort', externalListener);
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
const headers = {
|
|
42
|
-
'x-channel-id': config.channelId,
|
|
43
|
-
Authorization: `Bearer ${config.adminToken}`,
|
|
44
|
-
};
|
|
45
|
-
const init = { method, headers, signal: controller.signal };
|
|
46
|
-
if (body !== undefined) {
|
|
47
|
-
headers['Content-Type'] = 'application/json';
|
|
48
|
-
init.body = JSON.stringify(body);
|
|
47
|
+
const verb = method.toUpperCase();
|
|
48
|
+
if (!METHODS.has(verb)) {
|
|
49
|
+
throw new StorefrontError(`Unsupported HTTP method "${method}" for the admin authoring client.`, service);
|
|
49
50
|
}
|
|
50
51
|
try {
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
if (response.status === 204) {
|
|
57
|
-
return undefined;
|
|
58
|
-
}
|
|
59
|
-
const text = await response.text();
|
|
60
|
-
return (text ? JSON.parse(text) : undefined);
|
|
52
|
+
return await transport.rest(service, {
|
|
53
|
+
method: verb,
|
|
54
|
+
path,
|
|
55
|
+
...(body !== undefined ? { body } : {}),
|
|
56
|
+
}, options?.signal ? { signal: options.signal } : undefined);
|
|
61
57
|
}
|
|
62
58
|
catch (error) {
|
|
63
|
-
|
|
64
|
-
throw error;
|
|
65
|
-
if (error.name === 'AbortError') {
|
|
66
|
-
if (external?.aborted) {
|
|
67
|
-
throw new StorefrontError('Request aborted by caller', config.service);
|
|
68
|
-
}
|
|
69
|
-
throw new StorefrontError('Request timed out (15s)', config.service);
|
|
70
|
-
}
|
|
71
|
-
throw new StorefrontError(`${config.service} admin request failed: ${error.message}`, config.service);
|
|
72
|
-
}
|
|
73
|
-
finally {
|
|
74
|
-
clearTimeout(timeout);
|
|
75
|
-
if (externalListener && external) {
|
|
76
|
-
external.removeEventListener('abort', externalListener);
|
|
77
|
-
}
|
|
59
|
+
throw toStorefrontError(error, service);
|
|
78
60
|
}
|
|
79
61
|
}
|
|
80
62
|
return { request };
|
package/dist/admin/http.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"http.js","sourceRoot":"","sources":["../../src/admin/http.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"http.js","sourceRoot":"","sources":["../../src/admin/http.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"quotes.d.ts","sourceRoot":"","sources":["../../src/commerce/quotes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAElD,OAAO,KAAK,EACV,uBAAuB,EACvB,KAAK,EACL,KAAK,EACL,SAAS,EACT,gBAAgB,EACjB,MAAM,aAAa,CAAC;
|
|
1
|
+
{"version":3,"file":"quotes.d.ts","sourceRoot":"","sources":["../../src/commerce/quotes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAElD,OAAO,KAAK,EACV,uBAAuB,EACvB,KAAK,EACL,KAAK,EACL,SAAS,EACT,gBAAgB,EACjB,MAAM,aAAa,CAAC;AAiDrB,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,UAAU;0BAqCpB,gBAAgB,GAAG,OAAO,CAAC,SAAS,CAAC;mBAS5C,MAAM,GAAG,OAAO,CAAC,KAAK,GAAG,IAAI,CAAC;8BASnB,uBAAuB,GAAG,OAAO,CAAC,KAAK,CAAC;oBASlD,MAAM,GAAG,OAAO,CAAC,KAAK,CAAC;sBAKrB,MAAM,WAAW,MAAM,GAAG,OAAO,CAAC,KAAK,CAAC;EASnE"}
|
package/dist/commerce/quotes.js
CHANGED
|
@@ -19,7 +19,20 @@ import { ACCEPT_QUOTE, CANCEL_MY_QUOTE, CANCEL_MY_QUOTE_LEGACY, CREATE_QUOTE_REQ
|
|
|
19
19
|
function isUnknownFieldRejection(error) {
|
|
20
20
|
if (!(error instanceof StorefrontError))
|
|
21
21
|
return false;
|
|
22
|
-
|
|
22
|
+
if (error.service !== 'vendure')
|
|
23
|
+
return false;
|
|
24
|
+
// NOT every 400. `BAD_USER_INPUT` and `USER_INPUT_ERROR` are also mapped to
|
|
25
|
+
// 400, and those are EXECUTION-time refusals — `getMyQuote` on somebody
|
|
26
|
+
// else's quote is one — where the document did run. Re-issuing the legacy
|
|
27
|
+
// document there doubles the request, reports the second attempt's error
|
|
28
|
+
// instead of the first, and for a mutation replays a write that only
|
|
29
|
+
// `@Transaction()` rolled back. The two codes below both mean the document
|
|
30
|
+
// was refused before execution:
|
|
31
|
+
// BAD_REQUEST — an HTTP 400 with no GraphQL body, which is how graphql-js
|
|
32
|
+
// answers a validation failure;
|
|
33
|
+
// GRAPHQL_VALIDATION_FAILED — the same refusal as a coded `errors[]` entry.
|
|
34
|
+
return (error.errorCode === 'BAD_REQUEST' ||
|
|
35
|
+
error.errorCode === 'GRAPHQL_VALIDATION_FAILED' ||
|
|
23
36
|
/Cannot query field/i.test(error.message));
|
|
24
37
|
}
|
|
25
38
|
export function createQuotesMethods(http) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"quotes.js","sourceRoot":"","sources":["../../src/commerce/quotes.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,eAAe,EAAE,MAAM,cAAc,CAAC;AAQ/C,OAAO,EACL,YAAY,EACZ,eAAe,EACf,sBAAsB,EACtB,oBAAoB,EACpB,2BAA2B,EAC3B,QAAQ,EACR,eAAe,EACf,SAAS,EACT,gBAAgB,GACjB,MAAM,cAAc,CAAC;AAEtB;;;;;;;;;;;;;;;GAeG;AACH,SAAS,uBAAuB,CAAC,KAAc;IAC7C,IAAI,CAAC,CAAC,KAAK,YAAY,eAAe,CAAC;QAAE,OAAO,KAAK,CAAC;IACtD,OAAO,
|
|
1
|
+
{"version":3,"file":"quotes.js","sourceRoot":"","sources":["../../src/commerce/quotes.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"forms.d.ts","sourceRoot":"","sources":["../../src/content/forms.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAElD,OAAO,KAAK,EACV,cAAc,EACd,uBAAuB,EACvB,qBAAqB,EACrB,eAAe,EACf,cAAc,EAEd,oBAAoB,EACpB,cAAc,EACd,YAAY,EACb,MAAM,aAAa,CAAC;AAGrB,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,UAAU,EAAE,GAAG,EAAE,YAAY;IAcjE;;;;OAIG;wBACuB,eAAe,GAAG,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;gBAUlE,MAAM,YAAY,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;IAK5E,6DAA6D;wBACnC,MAAM,YAAY,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;IASpF;;;OAGG;gCAC+B,cAAc,GAAG,OAAO,CAAC,uBAAuB,EAAE,CAAC;IASrF;;;;;OAKG;uCACsC,cAAc,GAAG,OAAO,CAAC,qBAAqB,CAAC;mBASlF,MAAM,UACF,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,YACrB,cAAc,GACvB,OAAO,CAAC,oBAAoB,CAAC;
|
|
1
|
+
{"version":3,"file":"forms.d.ts","sourceRoot":"","sources":["../../src/content/forms.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAElD,OAAO,KAAK,EACV,cAAc,EACd,uBAAuB,EACvB,qBAAqB,EACrB,eAAe,EACf,cAAc,EAEd,oBAAoB,EACpB,cAAc,EACd,YAAY,EACb,MAAM,aAAa,CAAC;AAGrB,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,UAAU,EAAE,GAAG,EAAE,YAAY;IAcjE;;;;OAIG;wBACuB,eAAe,GAAG,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;gBAUlE,MAAM,YAAY,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;IAK5E,6DAA6D;wBACnC,MAAM,YAAY,cAAc,GAAG,OAAO,CAAC,cAAc,CAAC;IASpF;;;OAGG;gCAC+B,cAAc,GAAG,OAAO,CAAC,uBAAuB,EAAE,CAAC;IASrF;;;;;OAKG;uCACsC,cAAc,GAAG,OAAO,CAAC,qBAAqB,CAAC;mBASlF,MAAM,UACF,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,YACrB,cAAc,GACvB,OAAO,CAAC,oBAAoB,CAAC;EAyCnC"}
|
package/dist/content/forms.js
CHANGED
|
@@ -76,11 +76,19 @@ export function createFormMethods(http, ctx) {
|
|
|
76
76
|
return { success: true, id: result.data.id, createdAt: result.data.created_at };
|
|
77
77
|
}
|
|
78
78
|
catch (error) {
|
|
79
|
-
if (error instanceof StorefrontError &&
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
79
|
+
if (error instanceof StorefrontError && error.statusCode === 400) {
|
|
80
|
+
// Every detail must name a field. The CMS's validation pipe fills it
|
|
81
|
+
// in on all of them (`forms.service.ts`), so a set where one does not
|
|
82
|
+
// is not the field-level refusal this branch resolves — surfacing a
|
|
83
|
+
// partial list would hide whatever the unnamed detail said, and
|
|
84
|
+
// `FormSubmissionResult.errors` has nowhere to put it.
|
|
85
|
+
const fieldErrors = error.details.filter((detail) => typeof detail.field === 'string' && detail.field !== '');
|
|
86
|
+
if (fieldErrors.length > 0 && fieldErrors.length === error.details.length) {
|
|
87
|
+
return {
|
|
88
|
+
success: false,
|
|
89
|
+
errors: fieldErrors.map(({ field, code, message }) => ({ field, code, message })),
|
|
90
|
+
};
|
|
91
|
+
}
|
|
84
92
|
}
|
|
85
93
|
throw error;
|
|
86
94
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"forms.js","sourceRoot":"","sources":["../../src/content/forms.ts"],"names":[],"mappings":"AACA,OAAO,
|
|
1
|
+
{"version":3,"file":"forms.js","sourceRoot":"","sources":["../../src/content/forms.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../src/core/context.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../src/core/context.ts"],"names":[],"mappings":"AAaA,OAAO,KAAK,EAGV,YAAY,EACZ,sBAAsB,EACvB,MAAM,aAAa,CAAC;AAErB,wBAAsB,kBAAkB,CAAC,MAAM,EAAE,sBAAsB,GAAG,OAAO,CAAC,YAAY,CAAC,CAoE9F"}
|
package/dist/core/context.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
+
import { createChannelResolver, PlatformError, } from '@sixtyninecommerce/core';
|
|
1
2
|
import { DEFAULT_CMS_URL, DEFAULT_PLUGINS_URL, DEFAULT_VENDURE_URL, INIT_TIMEOUT_MS, } from '../constants.js';
|
|
2
|
-
import { StorefrontError } from '../errors.js';
|
|
3
|
+
import { StorefrontError, toStorefrontError } from '../errors.js';
|
|
3
4
|
export async function createStoreContext(config) {
|
|
4
5
|
if (!config.storeCode) {
|
|
5
6
|
throw new StorefrontError('storeCode is required', 'cms');
|
|
@@ -17,13 +18,25 @@ export async function createStoreContext(config) {
|
|
|
17
18
|
const vendureUrl = (config.vendureUrl ?? DEFAULT_VENDURE_URL).replace(/\/+$/, '');
|
|
18
19
|
const cmsUrl = (config.cmsUrl ?? DEFAULT_CMS_URL).replace(/\/+$/, '');
|
|
19
20
|
const pluginsUrl = (config.pluginsUrl ?? DEFAULT_PLUGINS_URL).replace(/\/+$/, '');
|
|
21
|
+
// One resolver for the life of the client, shared with the transport: it
|
|
22
|
+
// caches the channel, collapses concurrent resolutions into one request, and
|
|
23
|
+
// — the reason it is not just this one startup call — can go BACK to the CMS
|
|
24
|
+
// when a request is refused with CHANNEL_NOT_FOUND, so a channel whose token
|
|
25
|
+
// rotated under a running storefront heals itself instead of failing until
|
|
26
|
+
// the process restarts (spec §6.2, §15.1).
|
|
27
|
+
const channels = staleIfError(createChannelResolver({
|
|
28
|
+
cmsUrl,
|
|
29
|
+
fetch: fetchFn,
|
|
30
|
+
timeoutMs: INIT_TIMEOUT_MS,
|
|
31
|
+
}));
|
|
20
32
|
// Single startup roundtrip — the CMS /channels/by-code/:code endpoint now
|
|
21
33
|
// also returns custom_fields (proxied from Vendure with a server-side cache).
|
|
22
|
-
const channel = await resolveChannel(
|
|
34
|
+
const channel = await resolveChannel(channels, config.storeCode, cmsUrl);
|
|
23
35
|
const rawCdnDomain = channel.customFields.cdnDomain;
|
|
24
36
|
const channelCdnDomain = typeof rawCdnDomain === 'string' && rawCdnDomain.trim() !== '' ? rawCdnDomain.trim() : null;
|
|
25
37
|
return {
|
|
26
38
|
channel,
|
|
39
|
+
channels,
|
|
27
40
|
cdnUrl: channelCdnDomain ? `https://${channelCdnDomain}` : cdnUrl,
|
|
28
41
|
channelCdnDomain,
|
|
29
42
|
vendureUrl,
|
|
@@ -47,42 +60,86 @@ export async function createStoreContext(config) {
|
|
|
47
60
|
cacheTags: config.cacheTags ?? true,
|
|
48
61
|
};
|
|
49
62
|
}
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
63
|
+
/**
|
|
64
|
+
* Keep serving the channel we last resolved when the CMS cannot be reached.
|
|
65
|
+
*
|
|
66
|
+
* Re-resolution happens on the TTL, mid-traffic, and this SDK's channel was
|
|
67
|
+
* previously read once at boot and never again — so without this a 30-second
|
|
68
|
+
* CMS restart turns every product page, cart mutation and checkout call into a
|
|
69
|
+
* CMS error on a storefront whose Vendure is perfectly healthy. The retry
|
|
70
|
+
* budget (2 attempts, 200ms) does not cover a deploy.
|
|
71
|
+
*
|
|
72
|
+
* Only a TRANSPORT failure falls back. `CHANNEL_NOT_FOUND` is an answer, not an
|
|
73
|
+
* outage: it means the code is gone, it is what the rename self-heal keys on,
|
|
74
|
+
* and swallowing it would pin a storefront to a channel the platform has
|
|
75
|
+
* deleted. A malformed body is refused for the same reason — it is a reply.
|
|
76
|
+
*
|
|
77
|
+
* Nothing is cached here beyond the last GOOD answer: the wrapped resolver
|
|
78
|
+
* still owns the TTL, the in-flight collapsing and its own cache, so the next
|
|
79
|
+
* call after the CMS returns goes back to it and picks up a rotated token.
|
|
80
|
+
*/
|
|
81
|
+
const UNREACHABLE_CODES = new Set([
|
|
82
|
+
'CHANNEL_RESOLUTION_TIMEOUT',
|
|
83
|
+
'CHANNEL_RESOLUTION_FAILED',
|
|
84
|
+
]);
|
|
85
|
+
/** Did the CMS fail to ANSWER, as opposed to answering something we dislike? */
|
|
86
|
+
function cmsUnreachable(error) {
|
|
87
|
+
if (!(error instanceof PlatformError))
|
|
88
|
+
return false;
|
|
89
|
+
// Every 5xx, not just the retryable ones. `retryable` answers "is asking
|
|
90
|
+
// again worthwhile" — it is false for a 500 — but the question here is "did
|
|
91
|
+
// the CMS tell us anything ABOUT THIS CHANNEL", and a 500 (an exhausted
|
|
92
|
+
// Postgres pool, a throwing handler) tells us nothing. The two exclusions
|
|
93
|
+
// are both replies about the channel: a 404 says the code is gone, and
|
|
94
|
+
// `CHANNEL_RESOLUTION_MALFORMED` is a body from a CMS that is up and needs
|
|
95
|
+
// upgrading — serving a stale channel past either would hide it.
|
|
96
|
+
return UNREACHABLE_CODES.has(error.code) || error.status >= 500;
|
|
97
|
+
}
|
|
98
|
+
function staleIfError(inner) {
|
|
99
|
+
let lastGood;
|
|
100
|
+
return {
|
|
101
|
+
async resolve(code) {
|
|
102
|
+
try {
|
|
103
|
+
const info = await inner.resolve(code);
|
|
104
|
+
lastGood = info;
|
|
105
|
+
return info;
|
|
106
|
+
}
|
|
107
|
+
catch (error) {
|
|
108
|
+
if (lastGood === undefined || !cmsUnreachable(error))
|
|
109
|
+
throw error;
|
|
110
|
+
return lastGood;
|
|
111
|
+
}
|
|
112
|
+
},
|
|
113
|
+
invalidate(code) {
|
|
114
|
+
inner.invalidate(code);
|
|
115
|
+
},
|
|
116
|
+
};
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Resolve the channel, and say what to DO about each way it can fail.
|
|
120
|
+
*
|
|
121
|
+
* `core` reports the failure accurately (`CHANNEL_NOT_FOUND`,
|
|
122
|
+
* `CHANNEL_RESOLUTION_TIMEOUT`, …); this is the one call a storefront author
|
|
123
|
+
* makes by hand, usually while wiring the SDK up for the first time, so the
|
|
124
|
+
* three failures they are actually going to hit name the thing to check.
|
|
125
|
+
*/
|
|
126
|
+
async function resolveChannel(channels, storeCode, cmsUrl) {
|
|
53
127
|
try {
|
|
54
|
-
const
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
throw new StorefrontError(`Store code "${storeCode}" not found. Check storeCode matches a channel code in the dashboard.`, 'cms', 404);
|
|
59
|
-
}
|
|
60
|
-
if (!response.ok) {
|
|
61
|
-
throw new StorefrontError(`CMS returned ${String(response.status)}: ${response.statusText}`, 'cms', response.status);
|
|
62
|
-
}
|
|
63
|
-
const json = (await response.json());
|
|
64
|
-
return {
|
|
65
|
-
id: json.data.id,
|
|
66
|
-
code: json.data.code,
|
|
67
|
-
token: json.data.token,
|
|
68
|
-
defaultLanguageCode: json.data.default_language_code,
|
|
69
|
-
defaultCurrencyCode: json.data.default_currency_code,
|
|
70
|
-
// Older CMS deployments omit this field — default to false (tax-exclusive
|
|
71
|
-
// storage, Vendure's default) rather than guessing gross.
|
|
72
|
-
pricesIncludeTax: json.data.prices_include_tax === true,
|
|
73
|
-
customFields: json.data.custom_fields ?? {},
|
|
74
|
-
};
|
|
128
|
+
const resolved = await channels.resolve(storeCode);
|
|
129
|
+
// `core` types the bag as `Record<string, unknown>`; this package's
|
|
130
|
+
// `ChannelCustomFields` names the keys it reads out of the same JSON.
|
|
131
|
+
return { ...resolved, customFields: resolved.customFields };
|
|
75
132
|
}
|
|
76
133
|
catch (error) {
|
|
77
|
-
if (error instanceof
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
134
|
+
if (error instanceof PlatformError) {
|
|
135
|
+
if (error.code === 'CHANNEL_NOT_FOUND') {
|
|
136
|
+
throw new StorefrontError(`Store code "${storeCode}" not found. Check storeCode matches a channel code in the dashboard.`, 'cms', 404, error.code);
|
|
137
|
+
}
|
|
138
|
+
if (error.code === 'CHANNEL_RESOLUTION_TIMEOUT') {
|
|
139
|
+
throw new StorefrontError(`Timed out connecting to CMS at ${cmsUrl}. Is the service running?`, 'cms', undefined, error.code);
|
|
140
|
+
}
|
|
81
141
|
}
|
|
82
|
-
throw
|
|
83
|
-
}
|
|
84
|
-
finally {
|
|
85
|
-
clearTimeout(timeoutId);
|
|
142
|
+
throw toStorefrontError(error, 'cms');
|
|
86
143
|
}
|
|
87
144
|
}
|
|
88
145
|
//# sourceMappingURL=context.js.map
|
package/dist/core/context.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.js","sourceRoot":"","sources":["../../src/core/context.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,eAAe,EACf,mBAAmB,EACnB,mBAAmB,EACnB,eAAe,GAChB,MAAM,iBAAiB,CAAC;AACzB,OAAO,EAAE,eAAe,EAAE,MAAM,cAAc,CAAC;
|
|
1
|
+
{"version":3,"file":"context.js","sourceRoot":"","sources":["../../src/core/context.ts"],"names":[],"mappings":"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"}
|
package/dist/core/http.d.ts
CHANGED
|
@@ -1,3 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The storefront SDK's HTTP layer, on `@sixtyninecommerce/core`'s transport.
|
|
3
|
+
*
|
|
4
|
+
* Everything generic — header stamping, the retry policy, the abort/timeout
|
|
5
|
+
* link, RFC 9457 and Vendure error mapping, the session-token rotation, the
|
|
6
|
+
* `traceparent` — is `core`'s. What stays here is what is genuinely the
|
|
7
|
+
* STOREFRONT's: the `next: { tags }` cache tagging, the `onAuthExpired`
|
|
8
|
+
* disambiguation probe, and the wire shapes this package's modules read
|
|
9
|
+
* (`createdAt` is `created_at` here and always has been, so case conversion is
|
|
10
|
+
* off).
|
|
11
|
+
*/
|
|
1
12
|
import type { StoreContext } from '../types.js';
|
|
2
13
|
/** Optional per-request controls. */
|
|
3
14
|
export interface RequestOptions {
|
package/dist/core/http.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"http.d.ts","sourceRoot":"","sources":["../../src/core/http.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"http.d.ts","sourceRoot":"","sources":["../../src/core/http.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAWH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAEhD,qCAAqC;AACrC,MAAM,WAAW,cAAc;IAC7B,mFAAmF;IACnF,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB,0FAA0F;IAC1F,SAAS,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAC9B;;;OAGG;IACH,YAAY,CAAC,EAAE;QAAE,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;QAAC,QAAQ,CAAC,IAAI,EAAE,SAAS,MAAM,EAAE,CAAA;KAAE,CAAC;CACjF;AAED,qFAAqF;AACrF,wBAAgB,UAAU,CACxB,OAAO,EAAE,cAAc,GAAG,SAAS,EACnC,SAAS,EAAE,MAAM,EACjB,IAAI,GAAE,SAAS,MAAM,EAAO,GAC3B,cAAc,CAEhB;AA8BD,MAAM,WAAW,UAAU;IACzB,OAAO,CAAC,CAAC,GAAG,OAAO,EACjB,KAAK,EAAE,MAAM,EACb,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACnC,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,CAAC,CAAC,CAAC;IACd,aAAa,CAAC,CAAC,GAAG,OAAO,EACvB,KAAK,EAAE,MAAM,EACb,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAClC,KAAK,EAAE,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,EACxB,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,CAAC,CAAC,CAAC;IACd,MAAM,CAAC,CAAC,GAAG,OAAO,EAChB,IAAI,EAAE,MAAM,EACZ,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC/B,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,CAAC,CAAC,CAAC;IACd,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,OAAO,CAAC,EAAE,cAAc,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;IACxF,UAAU,CAAC,CAAC,GAAG,OAAO,EACpB,IAAI,EAAE,MAAM,EACZ,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC/B,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,CAAC,CAAC,CAAC;CACf;AAuDD,wBAAgB,gBAAgB,CAAC,GAAG,EAAE,YAAY,GAAG,UAAU,CA2M9D"}
|