@01.software/sdk 0.1.5 → 0.1.7
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 +93 -7
- package/dist/{auth-DNaV-5wt.d.ts → auth-Cl6xQinU.d.cts} +12 -1
- package/dist/{auth-DMvniYSs.d.cts → auth-u5YEtV1J.d.ts} +12 -1
- package/dist/auth.cjs.map +1 -1
- package/dist/auth.d.cts +2 -2
- package/dist/auth.d.ts +2 -2
- package/dist/auth.js.map +1 -1
- package/dist/index.cjs +817 -296
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +342 -46
- package/dist/index.d.ts +342 -46
- package/dist/index.js +817 -296
- package/dist/index.js.map +1 -1
- package/dist/metadata.cjs +70 -0
- package/dist/metadata.cjs.map +1 -0
- package/dist/metadata.d.cts +18 -0
- package/dist/metadata.d.ts +18 -0
- package/dist/metadata.js +50 -0
- package/dist/metadata.js.map +1 -0
- package/dist/{payload-types-BAZCcssT.d.cts → payload-types-9ZTBbiqb.d.cts} +864 -11
- package/dist/{payload-types-BAZCcssT.d.ts → payload-types-9ZTBbiqb.d.ts} +864 -11
- package/dist/{webhook-DdNkaI-f.d.cts → webhook-Cdv7bup2.d.cts} +2 -2
- package/dist/{webhook-CYJ0OPds.d.ts → webhook-c_A4J8UH.d.ts} +2 -2
- package/dist/webhook.cjs +6 -4
- package/dist/webhook.cjs.map +1 -1
- package/dist/webhook.d.cts +2 -2
- package/dist/webhook.d.ts +2 -2
- package/dist/webhook.js +6 -4
- package/dist/webhook.js.map +1 -1
- package/package.json +11 -1
package/dist/index.cjs
CHANGED
|
@@ -83,11 +83,14 @@ __export(src_exports, {
|
|
|
83
83
|
ApiError: () => ApiError,
|
|
84
84
|
BrowserClient: () => BrowserClient,
|
|
85
85
|
COLLECTIONS: () => COLLECTIONS,
|
|
86
|
+
CartApi: () => CartApi,
|
|
86
87
|
CollectionClient: () => CollectionClient,
|
|
87
88
|
CollectionQueryBuilder: () => CollectionQueryBuilder,
|
|
88
89
|
ConfigError: () => ConfigError,
|
|
90
|
+
CustomerAuth: () => CustomerAuth,
|
|
89
91
|
NetworkError: () => NetworkError,
|
|
90
92
|
OrderApi: () => OrderApi,
|
|
93
|
+
ProductApi: () => ProductApi,
|
|
91
94
|
QueryHooks: () => QueryHooks,
|
|
92
95
|
RichTextContent: () => RichTextContent,
|
|
93
96
|
ServerClient: () => ServerClient,
|
|
@@ -100,6 +103,7 @@ __export(src_exports, {
|
|
|
100
103
|
createServerClient: () => createServerClient,
|
|
101
104
|
createServerToken: () => createServerToken,
|
|
102
105
|
createTypedWebhookHandler: () => createTypedWebhookHandler,
|
|
106
|
+
customerKeys: () => customerKeys,
|
|
103
107
|
decodeServerToken: () => decodeServerToken,
|
|
104
108
|
formatOrderName: () => formatOrderName,
|
|
105
109
|
generateOrderNumber: () => generateOrderNumber,
|
|
@@ -120,119 +124,8 @@ __export(src_exports, {
|
|
|
120
124
|
});
|
|
121
125
|
module.exports = __toCommonJS(src_exports);
|
|
122
126
|
|
|
123
|
-
// src/core/
|
|
124
|
-
var
|
|
125
|
-
constructor(api, collection) {
|
|
126
|
-
this.api = api;
|
|
127
|
-
this.collection = collection;
|
|
128
|
-
}
|
|
129
|
-
/**
|
|
130
|
-
* Find documents (list query)
|
|
131
|
-
* GET /api/{collection}
|
|
132
|
-
* @returns Payload CMS find response with docs array and pagination
|
|
133
|
-
*/
|
|
134
|
-
find(options) {
|
|
135
|
-
return __async(this, null, function* () {
|
|
136
|
-
return this.api.requestFind(
|
|
137
|
-
`/api/${String(this.collection)}`,
|
|
138
|
-
options
|
|
139
|
-
);
|
|
140
|
-
});
|
|
141
|
-
}
|
|
142
|
-
/**
|
|
143
|
-
* Find document by ID
|
|
144
|
-
* GET /api/{collection}/{id}
|
|
145
|
-
* @returns Document object directly (no wrapper)
|
|
146
|
-
*/
|
|
147
|
-
findById(id, options) {
|
|
148
|
-
return __async(this, null, function* () {
|
|
149
|
-
return this.api.requestFindById(
|
|
150
|
-
`/api/${String(this.collection)}/${String(id)}`,
|
|
151
|
-
options
|
|
152
|
-
);
|
|
153
|
-
});
|
|
154
|
-
}
|
|
155
|
-
/**
|
|
156
|
-
* Create a new document
|
|
157
|
-
* POST /api/{collection}
|
|
158
|
-
* @returns Payload CMS mutation response with doc and message
|
|
159
|
-
*/
|
|
160
|
-
create(data) {
|
|
161
|
-
return __async(this, null, function* () {
|
|
162
|
-
return this.api.requestCreate(
|
|
163
|
-
`/api/${String(this.collection)}`,
|
|
164
|
-
data
|
|
165
|
-
);
|
|
166
|
-
});
|
|
167
|
-
}
|
|
168
|
-
/**
|
|
169
|
-
* Update a document by ID
|
|
170
|
-
* PATCH /api/{collection}/{id}
|
|
171
|
-
* @returns Payload CMS mutation response with doc and message
|
|
172
|
-
*/
|
|
173
|
-
update(id, data) {
|
|
174
|
-
return __async(this, null, function* () {
|
|
175
|
-
return this.api.requestUpdate(
|
|
176
|
-
`/api/${String(this.collection)}/${String(id)}`,
|
|
177
|
-
data
|
|
178
|
-
);
|
|
179
|
-
});
|
|
180
|
-
}
|
|
181
|
-
/**
|
|
182
|
-
* Count documents
|
|
183
|
-
* GET /api/{collection}/count
|
|
184
|
-
* @returns Count response with totalDocs
|
|
185
|
-
*/
|
|
186
|
-
count(options) {
|
|
187
|
-
return __async(this, null, function* () {
|
|
188
|
-
return this.api.requestCount(
|
|
189
|
-
`/api/${String(this.collection)}/count`,
|
|
190
|
-
options
|
|
191
|
-
);
|
|
192
|
-
});
|
|
193
|
-
}
|
|
194
|
-
/**
|
|
195
|
-
* Update multiple documents (bulk update)
|
|
196
|
-
* PATCH /api/{collection}
|
|
197
|
-
* @returns Payload CMS find response with updated docs
|
|
198
|
-
*/
|
|
199
|
-
updateMany(where, data) {
|
|
200
|
-
return __async(this, null, function* () {
|
|
201
|
-
return this.api.requestUpdateMany(
|
|
202
|
-
`/api/${String(this.collection)}`,
|
|
203
|
-
{ where, data }
|
|
204
|
-
);
|
|
205
|
-
});
|
|
206
|
-
}
|
|
207
|
-
/**
|
|
208
|
-
* Delete a document by ID
|
|
209
|
-
* DELETE /api/{collection}/{id}
|
|
210
|
-
* @returns Deleted document object directly (no wrapper)
|
|
211
|
-
*/
|
|
212
|
-
remove(id) {
|
|
213
|
-
return __async(this, null, function* () {
|
|
214
|
-
return this.api.requestDelete(
|
|
215
|
-
`/api/${String(this.collection)}/${String(id)}`
|
|
216
|
-
);
|
|
217
|
-
});
|
|
218
|
-
}
|
|
219
|
-
/**
|
|
220
|
-
* Delete multiple documents (bulk delete)
|
|
221
|
-
* DELETE /api/{collection}
|
|
222
|
-
* @returns Payload CMS find response with deleted docs
|
|
223
|
-
*/
|
|
224
|
-
removeMany(where) {
|
|
225
|
-
return __async(this, null, function* () {
|
|
226
|
-
return this.api.requestDeleteMany(
|
|
227
|
-
`/api/${String(this.collection)}`,
|
|
228
|
-
{ where }
|
|
229
|
-
);
|
|
230
|
-
});
|
|
231
|
-
}
|
|
232
|
-
};
|
|
233
|
-
|
|
234
|
-
// src/core/collection/http-client.ts
|
|
235
|
-
var import_qs_esm = require("qs-esm");
|
|
127
|
+
// src/core/internal/utils/index.ts
|
|
128
|
+
var import_jose = require("jose");
|
|
236
129
|
|
|
237
130
|
// src/core/internal/errors/index.ts
|
|
238
131
|
var SDKError = class _SDKError extends Error {
|
|
@@ -333,112 +226,6 @@ var createConfigError = (message, details, userMessage, suggestion) => new Confi
|
|
|
333
226
|
var createTimeoutError = (message, details, userMessage, suggestion) => new TimeoutError(message, details, userMessage, suggestion);
|
|
334
227
|
var createUsageLimitError = (message, usage, details, userMessage, suggestion) => new UsageLimitError(message, usage, details, userMessage, suggestion);
|
|
335
228
|
|
|
336
|
-
// src/core/collection/http-client.ts
|
|
337
|
-
var HttpClient = class {
|
|
338
|
-
constructor(clientKey, secretKey, baseUrl) {
|
|
339
|
-
if (!clientKey) {
|
|
340
|
-
throw createValidationError("clientKey is required.");
|
|
341
|
-
}
|
|
342
|
-
this.clientKey = clientKey;
|
|
343
|
-
this.secretKey = secretKey;
|
|
344
|
-
this.baseUrl = baseUrl;
|
|
345
|
-
this.defaultOptions = { clientKey, secretKey, baseUrl };
|
|
346
|
-
}
|
|
347
|
-
buildUrl(endpoint, options) {
|
|
348
|
-
if (!options) return endpoint;
|
|
349
|
-
const queryString = (0, import_qs_esm.stringify)(options, { addQueryPrefix: true });
|
|
350
|
-
return queryString ? `${endpoint}${queryString}` : endpoint;
|
|
351
|
-
}
|
|
352
|
-
assertJsonResponse(response) {
|
|
353
|
-
const contentType = response.headers.get("content-type");
|
|
354
|
-
if (!(contentType == null ? void 0 : contentType.includes("application/json"))) {
|
|
355
|
-
throw createApiError("Response is not in JSON format.", response.status, { contentType });
|
|
356
|
-
}
|
|
357
|
-
}
|
|
358
|
-
/**
|
|
359
|
-
* Parse Payload CMS find response (list query)
|
|
360
|
-
* Returns native Payload response structure
|
|
361
|
-
*/
|
|
362
|
-
parseFindResponse(response) {
|
|
363
|
-
return __async(this, null, function* () {
|
|
364
|
-
var _a, _b;
|
|
365
|
-
const contentType = response.headers.get("content-type");
|
|
366
|
-
try {
|
|
367
|
-
this.assertJsonResponse(response);
|
|
368
|
-
const jsonData = yield response.json();
|
|
369
|
-
if (jsonData.docs === void 0) {
|
|
370
|
-
throw createApiError("Invalid find response.", response.status, { jsonData });
|
|
371
|
-
}
|
|
372
|
-
return {
|
|
373
|
-
docs: jsonData.docs,
|
|
374
|
-
totalDocs: jsonData.totalDocs || 0,
|
|
375
|
-
limit: jsonData.limit || 20,
|
|
376
|
-
totalPages: jsonData.totalPages || 0,
|
|
377
|
-
page: jsonData.page || 1,
|
|
378
|
-
pagingCounter: jsonData.pagingCounter || 1,
|
|
379
|
-
hasPrevPage: jsonData.hasPrevPage || false,
|
|
380
|
-
hasNextPage: jsonData.hasNextPage || false,
|
|
381
|
-
prevPage: (_a = jsonData.prevPage) != null ? _a : null,
|
|
382
|
-
nextPage: (_b = jsonData.nextPage) != null ? _b : null
|
|
383
|
-
};
|
|
384
|
-
} catch (error) {
|
|
385
|
-
throw createApiError("Failed to parse response.", response.status, {
|
|
386
|
-
contentType,
|
|
387
|
-
error: error instanceof Error ? error.message : error
|
|
388
|
-
});
|
|
389
|
-
}
|
|
390
|
-
});
|
|
391
|
-
}
|
|
392
|
-
/**
|
|
393
|
-
* Parse Payload CMS mutation response (create/update)
|
|
394
|
-
* Returns native Payload response structure
|
|
395
|
-
*/
|
|
396
|
-
parseMutationResponse(response) {
|
|
397
|
-
return __async(this, null, function* () {
|
|
398
|
-
const contentType = response.headers.get("content-type");
|
|
399
|
-
try {
|
|
400
|
-
this.assertJsonResponse(response);
|
|
401
|
-
const jsonData = yield response.json();
|
|
402
|
-
if (jsonData.doc === void 0) {
|
|
403
|
-
throw createApiError("Invalid mutation response.", response.status, { jsonData });
|
|
404
|
-
}
|
|
405
|
-
return {
|
|
406
|
-
message: jsonData.message || "",
|
|
407
|
-
doc: jsonData.doc,
|
|
408
|
-
errors: jsonData.errors
|
|
409
|
-
};
|
|
410
|
-
} catch (error) {
|
|
411
|
-
throw createApiError("Failed to parse response.", response.status, {
|
|
412
|
-
contentType,
|
|
413
|
-
error: error instanceof Error ? error.message : error
|
|
414
|
-
});
|
|
415
|
-
}
|
|
416
|
-
});
|
|
417
|
-
}
|
|
418
|
-
/**
|
|
419
|
-
* Parse Payload CMS document response (findById/delete)
|
|
420
|
-
* Returns document directly without wrapper
|
|
421
|
-
*/
|
|
422
|
-
parseDocumentResponse(response) {
|
|
423
|
-
return __async(this, null, function* () {
|
|
424
|
-
const contentType = response.headers.get("content-type");
|
|
425
|
-
try {
|
|
426
|
-
this.assertJsonResponse(response);
|
|
427
|
-
const jsonData = yield response.json();
|
|
428
|
-
return jsonData;
|
|
429
|
-
} catch (error) {
|
|
430
|
-
throw createApiError("Failed to parse response.", response.status, {
|
|
431
|
-
contentType,
|
|
432
|
-
error: error instanceof Error ? error.message : error
|
|
433
|
-
});
|
|
434
|
-
}
|
|
435
|
-
});
|
|
436
|
-
}
|
|
437
|
-
};
|
|
438
|
-
|
|
439
|
-
// src/core/internal/utils/index.ts
|
|
440
|
-
var import_jose = require("jose");
|
|
441
|
-
|
|
442
229
|
// src/core/client/types.ts
|
|
443
230
|
var API_URLS = {
|
|
444
231
|
local: "http://localhost:3000",
|
|
@@ -464,6 +251,7 @@ function resolveApiUrl(config) {
|
|
|
464
251
|
var DEFAULT_TIMEOUT = 3e4;
|
|
465
252
|
var DEFAULT_RETRYABLE_STATUSES = [408, 429, 500, 502, 503, 504];
|
|
466
253
|
var NON_RETRYABLE_STATUSES = [401, 403, 404, 422];
|
|
254
|
+
var SAFE_METHODS = ["GET", "HEAD", "OPTIONS"];
|
|
467
255
|
function createServerToken(clientKey, secretKey, expiresIn = "1h") {
|
|
468
256
|
return __async(this, null, function* () {
|
|
469
257
|
if (!clientKey || !secretKey) {
|
|
@@ -567,6 +355,7 @@ function _fetch(url, options) {
|
|
|
567
355
|
const _a = options || {}, {
|
|
568
356
|
clientKey,
|
|
569
357
|
secretKey,
|
|
358
|
+
customerToken,
|
|
570
359
|
timeout = DEFAULT_TIMEOUT,
|
|
571
360
|
baseUrl = API_URLS.production,
|
|
572
361
|
debug,
|
|
@@ -574,6 +363,7 @@ function _fetch(url, options) {
|
|
|
574
363
|
} = _a, requestInit = __objRest(_a, [
|
|
575
364
|
"clientKey",
|
|
576
365
|
"secretKey",
|
|
366
|
+
"customerToken",
|
|
577
367
|
"timeout",
|
|
578
368
|
"baseUrl",
|
|
579
369
|
"debug",
|
|
@@ -587,6 +377,8 @@ function _fetch(url, options) {
|
|
|
587
377
|
let authToken;
|
|
588
378
|
if (secretKey && clientKey) {
|
|
589
379
|
authToken = yield createServerToken(clientKey, secretKey);
|
|
380
|
+
} else if (customerToken) {
|
|
381
|
+
authToken = customerToken;
|
|
590
382
|
}
|
|
591
383
|
let lastError;
|
|
592
384
|
for (let attempt = 0; attempt <= retryConfig.maxRetries; attempt++) {
|
|
@@ -601,9 +393,14 @@ function _fetch(url, options) {
|
|
|
601
393
|
if (!headers.has("Content-Type") && requestInit.body) {
|
|
602
394
|
headers.set("Content-Type", "application/json");
|
|
603
395
|
}
|
|
396
|
+
const redactedHeaders = Object.fromEntries(headers.entries());
|
|
397
|
+
if (redactedHeaders["authorization"]) {
|
|
398
|
+
const token = redactedHeaders["authorization"];
|
|
399
|
+
redactedHeaders["authorization"] = token.length > 15 ? `${token.slice(0, 15)}...****` : "****";
|
|
400
|
+
}
|
|
604
401
|
debugLog(debug, "request", url, {
|
|
605
402
|
method: requestInit.method || "GET",
|
|
606
|
-
headers:
|
|
403
|
+
headers: redactedHeaders,
|
|
607
404
|
attempt: attempt + 1
|
|
608
405
|
});
|
|
609
406
|
const controller = new AbortController();
|
|
@@ -647,7 +444,8 @@ function _fetch(url, options) {
|
|
|
647
444
|
`Request failed (status: ${response.status})`,
|
|
648
445
|
getErrorSuggestion(response.status)
|
|
649
446
|
);
|
|
650
|
-
|
|
447
|
+
const method = (requestInit.method || "GET").toUpperCase();
|
|
448
|
+
if (attempt < retryConfig.maxRetries && SAFE_METHODS.includes(method) && retryConfig.retryableStatuses.includes(response.status)) {
|
|
651
449
|
lastError = error;
|
|
652
450
|
const retryDelay = retryConfig.retryDelay(attempt);
|
|
653
451
|
debugLog(debug, "error", `Retrying in ${retryDelay}ms...`, error);
|
|
@@ -659,6 +457,8 @@ function _fetch(url, options) {
|
|
|
659
457
|
return response;
|
|
660
458
|
} catch (error) {
|
|
661
459
|
debugLog(debug, "error", url, error);
|
|
460
|
+
const method = (requestInit.method || "GET").toUpperCase();
|
|
461
|
+
const isSafe = SAFE_METHODS.includes(method);
|
|
662
462
|
if (error instanceof Error && error.name === "AbortError") {
|
|
663
463
|
const timeoutError = createTimeoutError(
|
|
664
464
|
`Request timed out after ${timeout}ms.`,
|
|
@@ -666,7 +466,7 @@ function _fetch(url, options) {
|
|
|
666
466
|
"The request timed out.",
|
|
667
467
|
"Please check your network connection or try again later."
|
|
668
468
|
);
|
|
669
|
-
if (attempt < retryConfig.maxRetries) {
|
|
469
|
+
if (isSafe && attempt < retryConfig.maxRetries) {
|
|
670
470
|
lastError = timeoutError;
|
|
671
471
|
yield delay(retryConfig.retryDelay(attempt));
|
|
672
472
|
continue;
|
|
@@ -681,7 +481,7 @@ function _fetch(url, options) {
|
|
|
681
481
|
"Network connection failed.",
|
|
682
482
|
"Please check your internet connection and try again."
|
|
683
483
|
);
|
|
684
|
-
if (attempt < retryConfig.maxRetries) {
|
|
484
|
+
if (isSafe && attempt < retryConfig.maxRetries) {
|
|
685
485
|
lastError = networkError;
|
|
686
486
|
yield delay(retryConfig.retryDelay(attempt));
|
|
687
487
|
continue;
|
|
@@ -689,7 +489,7 @@ function _fetch(url, options) {
|
|
|
689
489
|
throw networkError;
|
|
690
490
|
}
|
|
691
491
|
if (error instanceof NetworkError || error instanceof TimeoutError) {
|
|
692
|
-
if (attempt < retryConfig.maxRetries && error.status && !NON_RETRYABLE_STATUSES.includes(error.status) && retryConfig.retryableStatuses.includes(error.status)) {
|
|
492
|
+
if (isSafe && attempt < retryConfig.maxRetries && error.status && !NON_RETRYABLE_STATUSES.includes(error.status) && retryConfig.retryableStatuses.includes(error.status)) {
|
|
693
493
|
lastError = error;
|
|
694
494
|
yield delay(retryConfig.retryDelay(attempt));
|
|
695
495
|
continue;
|
|
@@ -703,7 +503,7 @@ function _fetch(url, options) {
|
|
|
703
503
|
"An unknown error occurred.",
|
|
704
504
|
"Please try again later."
|
|
705
505
|
);
|
|
706
|
-
if (attempt < retryConfig.maxRetries) {
|
|
506
|
+
if (isSafe && attempt < retryConfig.maxRetries) {
|
|
707
507
|
lastError = unknownError;
|
|
708
508
|
yield delay(retryConfig.retryDelay(attempt));
|
|
709
509
|
continue;
|
|
@@ -711,14 +511,427 @@ function _fetch(url, options) {
|
|
|
711
511
|
throw unknownError;
|
|
712
512
|
}
|
|
713
513
|
}
|
|
714
|
-
throw lastError;
|
|
514
|
+
throw lastError != null ? lastError : new NetworkError("Request failed after retries");
|
|
715
515
|
});
|
|
716
516
|
}
|
|
717
517
|
|
|
518
|
+
// src/core/api/order-api.ts
|
|
519
|
+
var OrderApi = class {
|
|
520
|
+
constructor(options) {
|
|
521
|
+
if (!options.clientKey) {
|
|
522
|
+
throw createConfigError("clientKey is required for OrderApi.");
|
|
523
|
+
}
|
|
524
|
+
if (!options.secretKey) {
|
|
525
|
+
throw createConfigError("secretKey is required for OrderApi.");
|
|
526
|
+
}
|
|
527
|
+
this.clientKey = options.clientKey;
|
|
528
|
+
this.secretKey = options.secretKey;
|
|
529
|
+
this.baseUrl = options.baseUrl;
|
|
530
|
+
}
|
|
531
|
+
request(endpoint, body) {
|
|
532
|
+
return __async(this, null, function* () {
|
|
533
|
+
const response = yield _fetch(endpoint, {
|
|
534
|
+
method: "POST",
|
|
535
|
+
clientKey: this.clientKey,
|
|
536
|
+
secretKey: this.secretKey,
|
|
537
|
+
baseUrl: this.baseUrl,
|
|
538
|
+
body: JSON.stringify(body)
|
|
539
|
+
});
|
|
540
|
+
let data;
|
|
541
|
+
try {
|
|
542
|
+
data = yield response.json();
|
|
543
|
+
} catch (e) {
|
|
544
|
+
throw createApiError(
|
|
545
|
+
`Invalid JSON response from ${endpoint}`,
|
|
546
|
+
response.status,
|
|
547
|
+
void 0,
|
|
548
|
+
"Server returned an invalid response.",
|
|
549
|
+
"Check if the API endpoint is available."
|
|
550
|
+
);
|
|
551
|
+
}
|
|
552
|
+
if (data.error) {
|
|
553
|
+
const errorMessage = typeof data.error === "string" ? data.error : "Unknown API error";
|
|
554
|
+
throw createApiError(
|
|
555
|
+
errorMessage,
|
|
556
|
+
response.status,
|
|
557
|
+
data,
|
|
558
|
+
errorMessage,
|
|
559
|
+
"An error occurred while processing the request."
|
|
560
|
+
);
|
|
561
|
+
}
|
|
562
|
+
return data;
|
|
563
|
+
});
|
|
564
|
+
}
|
|
565
|
+
createOrder(params) {
|
|
566
|
+
return this.request("/api/orders/create", params);
|
|
567
|
+
}
|
|
568
|
+
updateOrder(params) {
|
|
569
|
+
return this.request("/api/orders/update", params);
|
|
570
|
+
}
|
|
571
|
+
getOrder(params) {
|
|
572
|
+
return this.request("/api/orders/get", params);
|
|
573
|
+
}
|
|
574
|
+
updateTransaction(params) {
|
|
575
|
+
return this.request("/api/transactions/update", params);
|
|
576
|
+
}
|
|
577
|
+
checkout(params) {
|
|
578
|
+
return this.request("/api/orders/checkout", params);
|
|
579
|
+
}
|
|
580
|
+
createFulfillment(params) {
|
|
581
|
+
return this.request("/api/orders/create-fulfillment", params);
|
|
582
|
+
}
|
|
583
|
+
returnWithRefund(params) {
|
|
584
|
+
return this.request("/api/returns/return-refund", params);
|
|
585
|
+
}
|
|
586
|
+
createReturn(params) {
|
|
587
|
+
return this.request("/api/returns/create", params);
|
|
588
|
+
}
|
|
589
|
+
updateReturn(params) {
|
|
590
|
+
return this.request("/api/returns/update", params);
|
|
591
|
+
}
|
|
592
|
+
};
|
|
593
|
+
|
|
594
|
+
// src/core/api/cart-api.ts
|
|
595
|
+
var CartApi = class {
|
|
596
|
+
constructor(options) {
|
|
597
|
+
if (!options.clientKey) {
|
|
598
|
+
throw createConfigError("clientKey is required for CartApi.");
|
|
599
|
+
}
|
|
600
|
+
if (!options.secretKey && !options.customerToken) {
|
|
601
|
+
throw createConfigError("Either secretKey or customerToken is required for CartApi.");
|
|
602
|
+
}
|
|
603
|
+
this.clientKey = options.clientKey;
|
|
604
|
+
this.secretKey = options.secretKey;
|
|
605
|
+
this.customerToken = options.customerToken;
|
|
606
|
+
this.baseUrl = options.baseUrl;
|
|
607
|
+
}
|
|
608
|
+
request(endpoint, body) {
|
|
609
|
+
return __async(this, null, function* () {
|
|
610
|
+
const token = typeof this.customerToken === "function" ? this.customerToken() : this.customerToken;
|
|
611
|
+
const response = yield _fetch(endpoint, {
|
|
612
|
+
method: "POST",
|
|
613
|
+
clientKey: this.clientKey,
|
|
614
|
+
secretKey: this.secretKey,
|
|
615
|
+
customerToken: token != null ? token : void 0,
|
|
616
|
+
baseUrl: this.baseUrl,
|
|
617
|
+
body: JSON.stringify(body)
|
|
618
|
+
});
|
|
619
|
+
let data;
|
|
620
|
+
try {
|
|
621
|
+
data = yield response.json();
|
|
622
|
+
} catch (e) {
|
|
623
|
+
throw createApiError(
|
|
624
|
+
`Invalid JSON response from ${endpoint}`,
|
|
625
|
+
response.status,
|
|
626
|
+
void 0,
|
|
627
|
+
"Server returned an invalid response.",
|
|
628
|
+
"Check if the API endpoint is available."
|
|
629
|
+
);
|
|
630
|
+
}
|
|
631
|
+
if (data.error) {
|
|
632
|
+
const errorMessage = typeof data.error === "string" ? data.error : "Unknown API error";
|
|
633
|
+
throw createApiError(
|
|
634
|
+
errorMessage,
|
|
635
|
+
response.status,
|
|
636
|
+
data,
|
|
637
|
+
errorMessage,
|
|
638
|
+
"An error occurred while processing the request."
|
|
639
|
+
);
|
|
640
|
+
}
|
|
641
|
+
return data;
|
|
642
|
+
});
|
|
643
|
+
}
|
|
644
|
+
addItem(params) {
|
|
645
|
+
return this.request("/api/carts/add-item", params);
|
|
646
|
+
}
|
|
647
|
+
updateItem(params) {
|
|
648
|
+
return this.request("/api/carts/update-item", params);
|
|
649
|
+
}
|
|
650
|
+
removeItem(params) {
|
|
651
|
+
return this.request("/api/carts/remove-item", params);
|
|
652
|
+
}
|
|
653
|
+
};
|
|
654
|
+
|
|
655
|
+
// src/core/api/product-api.ts
|
|
656
|
+
var ProductApi = class {
|
|
657
|
+
constructor(options) {
|
|
658
|
+
if (!options.clientKey) {
|
|
659
|
+
throw createConfigError("clientKey is required for ProductApi.");
|
|
660
|
+
}
|
|
661
|
+
if (!options.secretKey) {
|
|
662
|
+
throw createConfigError("secretKey is required for ProductApi.");
|
|
663
|
+
}
|
|
664
|
+
this.clientKey = options.clientKey;
|
|
665
|
+
this.secretKey = options.secretKey;
|
|
666
|
+
this.baseUrl = options.baseUrl;
|
|
667
|
+
}
|
|
668
|
+
request(endpoint, body) {
|
|
669
|
+
return __async(this, null, function* () {
|
|
670
|
+
const response = yield _fetch(endpoint, {
|
|
671
|
+
method: "POST",
|
|
672
|
+
clientKey: this.clientKey,
|
|
673
|
+
secretKey: this.secretKey,
|
|
674
|
+
baseUrl: this.baseUrl,
|
|
675
|
+
body: JSON.stringify(body)
|
|
676
|
+
});
|
|
677
|
+
let data;
|
|
678
|
+
try {
|
|
679
|
+
data = yield response.json();
|
|
680
|
+
} catch (e) {
|
|
681
|
+
throw createApiError(
|
|
682
|
+
`Invalid JSON response from ${endpoint}`,
|
|
683
|
+
response.status,
|
|
684
|
+
void 0,
|
|
685
|
+
"Server returned an invalid response.",
|
|
686
|
+
"Check if the API endpoint is available."
|
|
687
|
+
);
|
|
688
|
+
}
|
|
689
|
+
if (data.error) {
|
|
690
|
+
const errorMessage = typeof data.error === "string" ? data.error : "Unknown API error";
|
|
691
|
+
throw createApiError(
|
|
692
|
+
errorMessage,
|
|
693
|
+
response.status,
|
|
694
|
+
data,
|
|
695
|
+
errorMessage,
|
|
696
|
+
"An error occurred while processing the request."
|
|
697
|
+
);
|
|
698
|
+
}
|
|
699
|
+
return data;
|
|
700
|
+
});
|
|
701
|
+
}
|
|
702
|
+
stockCheck(params) {
|
|
703
|
+
return this.request("/api/products/stock-check", params);
|
|
704
|
+
}
|
|
705
|
+
};
|
|
706
|
+
|
|
707
|
+
// src/core/collection/query-builder.ts
|
|
708
|
+
var CollectionQueryBuilder = class {
|
|
709
|
+
constructor(api, collection) {
|
|
710
|
+
this.api = api;
|
|
711
|
+
this.collection = collection;
|
|
712
|
+
}
|
|
713
|
+
/**
|
|
714
|
+
* Find documents (list query)
|
|
715
|
+
* GET /api/{collection}
|
|
716
|
+
* @returns Payload CMS find response with docs array and pagination
|
|
717
|
+
*/
|
|
718
|
+
find(options) {
|
|
719
|
+
return __async(this, null, function* () {
|
|
720
|
+
return this.api.requestFind(
|
|
721
|
+
`/api/${String(this.collection)}`,
|
|
722
|
+
options
|
|
723
|
+
);
|
|
724
|
+
});
|
|
725
|
+
}
|
|
726
|
+
/**
|
|
727
|
+
* Find document by ID
|
|
728
|
+
* GET /api/{collection}/{id}
|
|
729
|
+
* @returns Document object directly (no wrapper)
|
|
730
|
+
*/
|
|
731
|
+
findById(id, options) {
|
|
732
|
+
return __async(this, null, function* () {
|
|
733
|
+
return this.api.requestFindById(
|
|
734
|
+
`/api/${String(this.collection)}/${String(id)}`,
|
|
735
|
+
options
|
|
736
|
+
);
|
|
737
|
+
});
|
|
738
|
+
}
|
|
739
|
+
/**
|
|
740
|
+
* Create a new document
|
|
741
|
+
* POST /api/{collection}
|
|
742
|
+
* @returns Payload CMS mutation response with doc and message
|
|
743
|
+
*/
|
|
744
|
+
create(data) {
|
|
745
|
+
return __async(this, null, function* () {
|
|
746
|
+
return this.api.requestCreate(
|
|
747
|
+
`/api/${String(this.collection)}`,
|
|
748
|
+
data
|
|
749
|
+
);
|
|
750
|
+
});
|
|
751
|
+
}
|
|
752
|
+
/**
|
|
753
|
+
* Update a document by ID
|
|
754
|
+
* PATCH /api/{collection}/{id}
|
|
755
|
+
* @returns Payload CMS mutation response with doc and message
|
|
756
|
+
*/
|
|
757
|
+
update(id, data) {
|
|
758
|
+
return __async(this, null, function* () {
|
|
759
|
+
return this.api.requestUpdate(
|
|
760
|
+
`/api/${String(this.collection)}/${String(id)}`,
|
|
761
|
+
data
|
|
762
|
+
);
|
|
763
|
+
});
|
|
764
|
+
}
|
|
765
|
+
/**
|
|
766
|
+
* Count documents
|
|
767
|
+
* GET /api/{collection}/count
|
|
768
|
+
* @returns Count response with totalDocs
|
|
769
|
+
*/
|
|
770
|
+
count(options) {
|
|
771
|
+
return __async(this, null, function* () {
|
|
772
|
+
return this.api.requestCount(
|
|
773
|
+
`/api/${String(this.collection)}/count`,
|
|
774
|
+
options
|
|
775
|
+
);
|
|
776
|
+
});
|
|
777
|
+
}
|
|
778
|
+
/**
|
|
779
|
+
* Update multiple documents (bulk update)
|
|
780
|
+
* PATCH /api/{collection}
|
|
781
|
+
* @returns Payload CMS find response with updated docs
|
|
782
|
+
*/
|
|
783
|
+
updateMany(where, data) {
|
|
784
|
+
return __async(this, null, function* () {
|
|
785
|
+
return this.api.requestUpdateMany(
|
|
786
|
+
`/api/${String(this.collection)}`,
|
|
787
|
+
{ where, data }
|
|
788
|
+
);
|
|
789
|
+
});
|
|
790
|
+
}
|
|
791
|
+
/**
|
|
792
|
+
* Delete a document by ID
|
|
793
|
+
* DELETE /api/{collection}/{id}
|
|
794
|
+
* @returns Deleted document object directly (no wrapper)
|
|
795
|
+
*/
|
|
796
|
+
remove(id) {
|
|
797
|
+
return __async(this, null, function* () {
|
|
798
|
+
return this.api.requestDelete(
|
|
799
|
+
`/api/${String(this.collection)}/${String(id)}`
|
|
800
|
+
);
|
|
801
|
+
});
|
|
802
|
+
}
|
|
803
|
+
/**
|
|
804
|
+
* Delete multiple documents (bulk delete)
|
|
805
|
+
* DELETE /api/{collection}
|
|
806
|
+
* @returns Payload CMS find response with deleted docs
|
|
807
|
+
*/
|
|
808
|
+
removeMany(where) {
|
|
809
|
+
return __async(this, null, function* () {
|
|
810
|
+
return this.api.requestDeleteMany(
|
|
811
|
+
`/api/${String(this.collection)}`,
|
|
812
|
+
{ where }
|
|
813
|
+
);
|
|
814
|
+
});
|
|
815
|
+
}
|
|
816
|
+
};
|
|
817
|
+
|
|
818
|
+
// src/core/collection/http-client.ts
|
|
819
|
+
var import_qs_esm = require("qs-esm");
|
|
820
|
+
var HttpClient = class {
|
|
821
|
+
constructor(clientKey, secretKey, baseUrl, getCustomerToken) {
|
|
822
|
+
if (!clientKey) {
|
|
823
|
+
throw createValidationError("clientKey is required.");
|
|
824
|
+
}
|
|
825
|
+
this.clientKey = clientKey;
|
|
826
|
+
this.secretKey = secretKey;
|
|
827
|
+
this.baseUrl = baseUrl;
|
|
828
|
+
this.getCustomerToken = getCustomerToken;
|
|
829
|
+
}
|
|
830
|
+
get defaultOptions() {
|
|
831
|
+
var _a;
|
|
832
|
+
const opts = { clientKey: this.clientKey, secretKey: this.secretKey, baseUrl: this.baseUrl };
|
|
833
|
+
const token = (_a = this.getCustomerToken) == null ? void 0 : _a.call(this);
|
|
834
|
+
if (token) {
|
|
835
|
+
opts.customerToken = token;
|
|
836
|
+
}
|
|
837
|
+
return opts;
|
|
838
|
+
}
|
|
839
|
+
buildUrl(endpoint, options) {
|
|
840
|
+
if (!options) return endpoint;
|
|
841
|
+
const queryString = (0, import_qs_esm.stringify)(options, { addQueryPrefix: true });
|
|
842
|
+
return queryString ? `${endpoint}${queryString}` : endpoint;
|
|
843
|
+
}
|
|
844
|
+
assertJsonResponse(response) {
|
|
845
|
+
const contentType = response.headers.get("content-type");
|
|
846
|
+
if (!(contentType == null ? void 0 : contentType.includes("application/json"))) {
|
|
847
|
+
throw createApiError("Response is not in JSON format.", response.status, { contentType });
|
|
848
|
+
}
|
|
849
|
+
}
|
|
850
|
+
/**
|
|
851
|
+
* Parse Payload CMS find response (list query)
|
|
852
|
+
* Returns native Payload response structure
|
|
853
|
+
*/
|
|
854
|
+
parseFindResponse(response) {
|
|
855
|
+
return __async(this, null, function* () {
|
|
856
|
+
var _a, _b;
|
|
857
|
+
const contentType = response.headers.get("content-type");
|
|
858
|
+
try {
|
|
859
|
+
this.assertJsonResponse(response);
|
|
860
|
+
const jsonData = yield response.json();
|
|
861
|
+
if (jsonData.docs === void 0) {
|
|
862
|
+
throw createApiError("Invalid find response.", response.status, { jsonData });
|
|
863
|
+
}
|
|
864
|
+
return {
|
|
865
|
+
docs: jsonData.docs,
|
|
866
|
+
totalDocs: jsonData.totalDocs || 0,
|
|
867
|
+
limit: jsonData.limit || 20,
|
|
868
|
+
totalPages: jsonData.totalPages || 0,
|
|
869
|
+
page: jsonData.page || 1,
|
|
870
|
+
pagingCounter: jsonData.pagingCounter || 1,
|
|
871
|
+
hasPrevPage: jsonData.hasPrevPage || false,
|
|
872
|
+
hasNextPage: jsonData.hasNextPage || false,
|
|
873
|
+
prevPage: (_a = jsonData.prevPage) != null ? _a : null,
|
|
874
|
+
nextPage: (_b = jsonData.nextPage) != null ? _b : null
|
|
875
|
+
};
|
|
876
|
+
} catch (error) {
|
|
877
|
+
throw createApiError("Failed to parse response.", response.status, {
|
|
878
|
+
contentType,
|
|
879
|
+
error: error instanceof Error ? error.message : error
|
|
880
|
+
});
|
|
881
|
+
}
|
|
882
|
+
});
|
|
883
|
+
}
|
|
884
|
+
/**
|
|
885
|
+
* Parse Payload CMS mutation response (create/update)
|
|
886
|
+
* Returns native Payload response structure
|
|
887
|
+
*/
|
|
888
|
+
parseMutationResponse(response) {
|
|
889
|
+
return __async(this, null, function* () {
|
|
890
|
+
const contentType = response.headers.get("content-type");
|
|
891
|
+
try {
|
|
892
|
+
this.assertJsonResponse(response);
|
|
893
|
+
const jsonData = yield response.json();
|
|
894
|
+
if (jsonData.doc === void 0) {
|
|
895
|
+
throw createApiError("Invalid mutation response.", response.status, { jsonData });
|
|
896
|
+
}
|
|
897
|
+
return {
|
|
898
|
+
message: jsonData.message || "",
|
|
899
|
+
doc: jsonData.doc,
|
|
900
|
+
errors: jsonData.errors
|
|
901
|
+
};
|
|
902
|
+
} catch (error) {
|
|
903
|
+
throw createApiError("Failed to parse response.", response.status, {
|
|
904
|
+
contentType,
|
|
905
|
+
error: error instanceof Error ? error.message : error
|
|
906
|
+
});
|
|
907
|
+
}
|
|
908
|
+
});
|
|
909
|
+
}
|
|
910
|
+
/**
|
|
911
|
+
* Parse Payload CMS document response (findById/delete)
|
|
912
|
+
* Returns document directly without wrapper
|
|
913
|
+
*/
|
|
914
|
+
parseDocumentResponse(response) {
|
|
915
|
+
return __async(this, null, function* () {
|
|
916
|
+
const contentType = response.headers.get("content-type");
|
|
917
|
+
try {
|
|
918
|
+
this.assertJsonResponse(response);
|
|
919
|
+
const jsonData = yield response.json();
|
|
920
|
+
return jsonData;
|
|
921
|
+
} catch (error) {
|
|
922
|
+
throw createApiError("Failed to parse response.", response.status, {
|
|
923
|
+
contentType,
|
|
924
|
+
error: error instanceof Error ? error.message : error
|
|
925
|
+
});
|
|
926
|
+
}
|
|
927
|
+
});
|
|
928
|
+
}
|
|
929
|
+
};
|
|
930
|
+
|
|
718
931
|
// src/core/collection/collection-client.ts
|
|
719
932
|
var CollectionClient = class extends HttpClient {
|
|
720
|
-
constructor(clientKey, secretKey, baseUrl) {
|
|
721
|
-
super(clientKey, secretKey, baseUrl);
|
|
933
|
+
constructor(clientKey, secretKey, baseUrl, getCustomerToken) {
|
|
934
|
+
super(clientKey, secretKey, baseUrl, getCustomerToken);
|
|
722
935
|
}
|
|
723
936
|
from(collection) {
|
|
724
937
|
return new CollectionQueryBuilder(this, collection);
|
|
@@ -843,7 +1056,19 @@ var COLLECTIONS = [
|
|
|
843
1056
|
"order-products",
|
|
844
1057
|
"returns",
|
|
845
1058
|
"return-products",
|
|
1059
|
+
"exchanges",
|
|
1060
|
+
"exchange-products",
|
|
1061
|
+
"fulfillments",
|
|
1062
|
+
"fulfillment-items",
|
|
846
1063
|
"transactions",
|
|
1064
|
+
"customers",
|
|
1065
|
+
"customer-addresses",
|
|
1066
|
+
"customer-groups",
|
|
1067
|
+
"customer-group-images",
|
|
1068
|
+
"carts",
|
|
1069
|
+
"cart-items",
|
|
1070
|
+
"discounts",
|
|
1071
|
+
"shipping-policies",
|
|
847
1072
|
"documents",
|
|
848
1073
|
"document-categories",
|
|
849
1074
|
"document-images",
|
|
@@ -861,12 +1086,205 @@ var COLLECTIONS = [
|
|
|
861
1086
|
"media"
|
|
862
1087
|
];
|
|
863
1088
|
|
|
1089
|
+
// src/core/customer/customer-auth.ts
|
|
1090
|
+
var DEFAULT_TIMEOUT2 = 15e3;
|
|
1091
|
+
var CustomerAuth = class {
|
|
1092
|
+
constructor(clientKey, baseUrl, options) {
|
|
1093
|
+
var _a;
|
|
1094
|
+
this.clientKey = clientKey;
|
|
1095
|
+
this.baseUrl = baseUrl;
|
|
1096
|
+
this.token = (_a = options == null ? void 0 : options.token) != null ? _a : null;
|
|
1097
|
+
this.onTokenChange = options == null ? void 0 : options.onTokenChange;
|
|
1098
|
+
}
|
|
1099
|
+
/**
|
|
1100
|
+
* Register a new customer account
|
|
1101
|
+
*/
|
|
1102
|
+
register(data) {
|
|
1103
|
+
return __async(this, null, function* () {
|
|
1104
|
+
return this.requestJson("/api/customers/register", {
|
|
1105
|
+
method: "POST",
|
|
1106
|
+
body: JSON.stringify(data)
|
|
1107
|
+
});
|
|
1108
|
+
});
|
|
1109
|
+
}
|
|
1110
|
+
/**
|
|
1111
|
+
* Login with email and password. Stores the token internally.
|
|
1112
|
+
*/
|
|
1113
|
+
login(data) {
|
|
1114
|
+
return __async(this, null, function* () {
|
|
1115
|
+
const result = yield this.requestJson("/api/customers/login", {
|
|
1116
|
+
method: "POST",
|
|
1117
|
+
body: JSON.stringify(data)
|
|
1118
|
+
});
|
|
1119
|
+
this.setToken(result.token);
|
|
1120
|
+
return result;
|
|
1121
|
+
});
|
|
1122
|
+
}
|
|
1123
|
+
/**
|
|
1124
|
+
* Refresh the current token. Requires a valid (non-expired) token.
|
|
1125
|
+
*/
|
|
1126
|
+
refreshToken() {
|
|
1127
|
+
return __async(this, null, function* () {
|
|
1128
|
+
if (!this.token) throw new ApiError("Not authenticated", 401);
|
|
1129
|
+
const result = yield this.requestJson("/api/customers/refresh", {
|
|
1130
|
+
method: "POST",
|
|
1131
|
+
headers: { Authorization: `Bearer ${this.token}` }
|
|
1132
|
+
});
|
|
1133
|
+
this.setToken(result.token);
|
|
1134
|
+
return result;
|
|
1135
|
+
});
|
|
1136
|
+
}
|
|
1137
|
+
/**
|
|
1138
|
+
* Clear the stored token
|
|
1139
|
+
*/
|
|
1140
|
+
logout() {
|
|
1141
|
+
this.setToken(null);
|
|
1142
|
+
}
|
|
1143
|
+
/**
|
|
1144
|
+
* Get the current authenticated customer's profile
|
|
1145
|
+
*/
|
|
1146
|
+
me() {
|
|
1147
|
+
return __async(this, null, function* () {
|
|
1148
|
+
var _a;
|
|
1149
|
+
if (!this.token) return null;
|
|
1150
|
+
try {
|
|
1151
|
+
const data = yield this.requestJson("/api/customers/me", {
|
|
1152
|
+
method: "GET",
|
|
1153
|
+
headers: { Authorization: `Bearer ${this.token}` }
|
|
1154
|
+
});
|
|
1155
|
+
return (_a = data.customer) != null ? _a : null;
|
|
1156
|
+
} catch (error) {
|
|
1157
|
+
if (error instanceof ApiError && error.status === 401) {
|
|
1158
|
+
this.setToken(null);
|
|
1159
|
+
return null;
|
|
1160
|
+
}
|
|
1161
|
+
throw error;
|
|
1162
|
+
}
|
|
1163
|
+
});
|
|
1164
|
+
}
|
|
1165
|
+
/**
|
|
1166
|
+
* Request a password reset email
|
|
1167
|
+
*/
|
|
1168
|
+
forgotPassword(email) {
|
|
1169
|
+
return __async(this, null, function* () {
|
|
1170
|
+
yield this.requestJson("/api/customers/forgot-password", {
|
|
1171
|
+
method: "POST",
|
|
1172
|
+
body: JSON.stringify({ email })
|
|
1173
|
+
});
|
|
1174
|
+
});
|
|
1175
|
+
}
|
|
1176
|
+
/**
|
|
1177
|
+
* Reset password using a token from the reset email
|
|
1178
|
+
*/
|
|
1179
|
+
resetPassword(token, password) {
|
|
1180
|
+
return __async(this, null, function* () {
|
|
1181
|
+
yield this.requestJson("/api/customers/reset-password", {
|
|
1182
|
+
method: "POST",
|
|
1183
|
+
body: JSON.stringify({ token, password })
|
|
1184
|
+
});
|
|
1185
|
+
});
|
|
1186
|
+
}
|
|
1187
|
+
/**
|
|
1188
|
+
* Change the password of the currently authenticated customer
|
|
1189
|
+
*/
|
|
1190
|
+
changePassword(currentPassword, newPassword) {
|
|
1191
|
+
return __async(this, null, function* () {
|
|
1192
|
+
if (!this.token) throw new ApiError("Not authenticated", 401);
|
|
1193
|
+
yield this.requestJson("/api/customers/change-password", {
|
|
1194
|
+
method: "POST",
|
|
1195
|
+
headers: { Authorization: `Bearer ${this.token}` },
|
|
1196
|
+
body: JSON.stringify({ currentPassword, newPassword })
|
|
1197
|
+
});
|
|
1198
|
+
});
|
|
1199
|
+
}
|
|
1200
|
+
/**
|
|
1201
|
+
* Verify email using the verification token
|
|
1202
|
+
*/
|
|
1203
|
+
verifyEmail(token) {
|
|
1204
|
+
return __async(this, null, function* () {
|
|
1205
|
+
yield this.requestJson("/api/customers/verify-email", {
|
|
1206
|
+
method: "POST",
|
|
1207
|
+
body: JSON.stringify({ token })
|
|
1208
|
+
});
|
|
1209
|
+
});
|
|
1210
|
+
}
|
|
1211
|
+
/**
|
|
1212
|
+
* Get the current token (or null if not authenticated)
|
|
1213
|
+
*/
|
|
1214
|
+
getToken() {
|
|
1215
|
+
return this.token;
|
|
1216
|
+
}
|
|
1217
|
+
/**
|
|
1218
|
+
* Set the token manually (e.g. from SSR)
|
|
1219
|
+
*/
|
|
1220
|
+
setToken(token) {
|
|
1221
|
+
var _a;
|
|
1222
|
+
this.token = token;
|
|
1223
|
+
(_a = this.onTokenChange) == null ? void 0 : _a.call(this, token);
|
|
1224
|
+
}
|
|
1225
|
+
/**
|
|
1226
|
+
* Check if the customer is currently authenticated
|
|
1227
|
+
*/
|
|
1228
|
+
isAuthenticated() {
|
|
1229
|
+
return this.token !== null;
|
|
1230
|
+
}
|
|
1231
|
+
/**
|
|
1232
|
+
* Internal: make a request with timeout and error handling.
|
|
1233
|
+
* Auth endpoints don't retry — failures are final.
|
|
1234
|
+
*/
|
|
1235
|
+
requestJson(path, init) {
|
|
1236
|
+
return __async(this, null, function* () {
|
|
1237
|
+
const headers = new Headers(init.headers);
|
|
1238
|
+
headers.set("X-Client-Key", this.clientKey);
|
|
1239
|
+
if (!headers.has("Content-Type") && init.body) {
|
|
1240
|
+
headers.set("Content-Type", "application/json");
|
|
1241
|
+
}
|
|
1242
|
+
const controller = new AbortController();
|
|
1243
|
+
const timeoutId = setTimeout(() => controller.abort(), DEFAULT_TIMEOUT2);
|
|
1244
|
+
let res;
|
|
1245
|
+
try {
|
|
1246
|
+
res = yield fetch(`${this.baseUrl}${path}`, __spreadProps(__spreadValues({}, init), {
|
|
1247
|
+
headers,
|
|
1248
|
+
signal: controller.signal
|
|
1249
|
+
}));
|
|
1250
|
+
} catch (error) {
|
|
1251
|
+
clearTimeout(timeoutId);
|
|
1252
|
+
if (error instanceof Error && error.name === "AbortError") {
|
|
1253
|
+
throw new TimeoutError(
|
|
1254
|
+
`Request timed out after ${DEFAULT_TIMEOUT2}ms`,
|
|
1255
|
+
{ url: path, timeout: DEFAULT_TIMEOUT2 }
|
|
1256
|
+
);
|
|
1257
|
+
}
|
|
1258
|
+
throw new NetworkError(
|
|
1259
|
+
error instanceof Error ? error.message : "Network request failed",
|
|
1260
|
+
void 0,
|
|
1261
|
+
{ url: path },
|
|
1262
|
+
"Network connection failed.",
|
|
1263
|
+
"Please check your internet connection and try again."
|
|
1264
|
+
);
|
|
1265
|
+
}
|
|
1266
|
+
clearTimeout(timeoutId);
|
|
1267
|
+
if (!res.ok) {
|
|
1268
|
+
const body = yield res.json().catch(() => ({}));
|
|
1269
|
+
throw new ApiError(
|
|
1270
|
+
body.error || `HTTP ${res.status}`,
|
|
1271
|
+
res.status,
|
|
1272
|
+
body.details,
|
|
1273
|
+
body.error
|
|
1274
|
+
);
|
|
1275
|
+
}
|
|
1276
|
+
return res.json();
|
|
1277
|
+
});
|
|
1278
|
+
}
|
|
1279
|
+
};
|
|
1280
|
+
|
|
864
1281
|
// src/core/query/get-query-client.ts
|
|
865
1282
|
var import_react_query = require("@tanstack/react-query");
|
|
866
1283
|
function makeQueryClient() {
|
|
867
1284
|
return new import_react_query.QueryClient({
|
|
868
1285
|
defaultOptions: {
|
|
869
1286
|
queries: {
|
|
1287
|
+
// SSR/RSC: server-fetched data doesn't auto-refetch; use refetch()/invalidate() to refresh
|
|
870
1288
|
staleTime: Number.POSITIVE_INFINITY,
|
|
871
1289
|
refetchOnWindowFocus: false
|
|
872
1290
|
},
|
|
@@ -901,11 +1319,24 @@ function collectionKeys(collection) {
|
|
|
901
1319
|
infinite: (options) => [collection, "infinite", options]
|
|
902
1320
|
};
|
|
903
1321
|
}
|
|
1322
|
+
var customerKeys = {
|
|
1323
|
+
all: ["customer"],
|
|
1324
|
+
me: () => ["customer", "me"]
|
|
1325
|
+
};
|
|
904
1326
|
var DEFAULT_PAGE_SIZE = 20;
|
|
905
1327
|
var QueryHooks = class {
|
|
906
|
-
constructor(queryClient, collectionClient) {
|
|
1328
|
+
constructor(queryClient, collectionClient, customerAuth) {
|
|
907
1329
|
this.queryClient = queryClient;
|
|
908
1330
|
this.collectionClient = collectionClient;
|
|
1331
|
+
this.customerAuth = customerAuth;
|
|
1332
|
+
}
|
|
1333
|
+
ensureCustomerAuth() {
|
|
1334
|
+
if (!this.customerAuth) {
|
|
1335
|
+
throw createConfigError(
|
|
1336
|
+
"Customer hooks require BrowserClient. Use createBrowserClient() instead of createServerClient()."
|
|
1337
|
+
);
|
|
1338
|
+
}
|
|
1339
|
+
return this.customerAuth;
|
|
909
1340
|
}
|
|
910
1341
|
// ===== useQuery =====
|
|
911
1342
|
useQuery(params, options) {
|
|
@@ -1097,6 +1528,124 @@ var QueryHooks = class {
|
|
|
1097
1528
|
);
|
|
1098
1529
|
}
|
|
1099
1530
|
}
|
|
1531
|
+
// ===== Customer Query Hooks =====
|
|
1532
|
+
useCustomerMe(options) {
|
|
1533
|
+
var _a, _b;
|
|
1534
|
+
return (0, import_react_query2.useQuery)(__spreadProps(__spreadValues({
|
|
1535
|
+
queryKey: customerKeys.me(),
|
|
1536
|
+
queryFn: () => __async(this, null, function* () {
|
|
1537
|
+
return yield this.ensureCustomerAuth().me();
|
|
1538
|
+
})
|
|
1539
|
+
}, options), {
|
|
1540
|
+
enabled: ((_a = options == null ? void 0 : options.enabled) != null ? _a : true) && !!((_b = this.customerAuth) == null ? void 0 : _b.isAuthenticated())
|
|
1541
|
+
}));
|
|
1542
|
+
}
|
|
1543
|
+
useCustomerLogin(options) {
|
|
1544
|
+
return (0, import_react_query2.useMutation)({
|
|
1545
|
+
mutationFn: (data) => __async(this, null, function* () {
|
|
1546
|
+
return yield this.ensureCustomerAuth().login(data);
|
|
1547
|
+
}),
|
|
1548
|
+
onSuccess: (data) => {
|
|
1549
|
+
var _a;
|
|
1550
|
+
this.queryClient.invalidateQueries({ queryKey: customerKeys.me() });
|
|
1551
|
+
(_a = options == null ? void 0 : options.onSuccess) == null ? void 0 : _a.call(options, data);
|
|
1552
|
+
},
|
|
1553
|
+
onError: options == null ? void 0 : options.onError,
|
|
1554
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1555
|
+
});
|
|
1556
|
+
}
|
|
1557
|
+
useCustomerRegister(options) {
|
|
1558
|
+
return (0, import_react_query2.useMutation)({
|
|
1559
|
+
mutationFn: (data) => __async(this, null, function* () {
|
|
1560
|
+
return yield this.ensureCustomerAuth().register(data);
|
|
1561
|
+
}),
|
|
1562
|
+
onSuccess: options == null ? void 0 : options.onSuccess,
|
|
1563
|
+
onError: options == null ? void 0 : options.onError,
|
|
1564
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1565
|
+
});
|
|
1566
|
+
}
|
|
1567
|
+
useCustomerLogout(options) {
|
|
1568
|
+
return (0, import_react_query2.useMutation)({
|
|
1569
|
+
mutationFn: () => __async(this, null, function* () {
|
|
1570
|
+
this.ensureCustomerAuth().logout();
|
|
1571
|
+
}),
|
|
1572
|
+
onSuccess: () => {
|
|
1573
|
+
var _a;
|
|
1574
|
+
this.queryClient.removeQueries({ queryKey: customerKeys.all });
|
|
1575
|
+
(_a = options == null ? void 0 : options.onSuccess) == null ? void 0 : _a.call(options);
|
|
1576
|
+
},
|
|
1577
|
+
onError: options == null ? void 0 : options.onError,
|
|
1578
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1579
|
+
});
|
|
1580
|
+
}
|
|
1581
|
+
useCustomerForgotPassword(options) {
|
|
1582
|
+
return (0, import_react_query2.useMutation)({
|
|
1583
|
+
mutationFn: (email) => __async(this, null, function* () {
|
|
1584
|
+
yield this.ensureCustomerAuth().forgotPassword(email);
|
|
1585
|
+
}),
|
|
1586
|
+
onSuccess: options == null ? void 0 : options.onSuccess,
|
|
1587
|
+
onError: options == null ? void 0 : options.onError,
|
|
1588
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1589
|
+
});
|
|
1590
|
+
}
|
|
1591
|
+
useCustomerResetPassword(options) {
|
|
1592
|
+
return (0, import_react_query2.useMutation)({
|
|
1593
|
+
mutationFn: (data) => __async(this, null, function* () {
|
|
1594
|
+
yield this.ensureCustomerAuth().resetPassword(data.token, data.password);
|
|
1595
|
+
}),
|
|
1596
|
+
onSuccess: options == null ? void 0 : options.onSuccess,
|
|
1597
|
+
onError: options == null ? void 0 : options.onError,
|
|
1598
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1599
|
+
});
|
|
1600
|
+
}
|
|
1601
|
+
useCustomerVerifyEmail(options) {
|
|
1602
|
+
return (0, import_react_query2.useMutation)({
|
|
1603
|
+
mutationFn: (token) => __async(this, null, function* () {
|
|
1604
|
+
yield this.ensureCustomerAuth().verifyEmail(token);
|
|
1605
|
+
}),
|
|
1606
|
+
onSuccess: () => {
|
|
1607
|
+
var _a;
|
|
1608
|
+
this.queryClient.invalidateQueries({ queryKey: customerKeys.me() });
|
|
1609
|
+
(_a = options == null ? void 0 : options.onSuccess) == null ? void 0 : _a.call(options);
|
|
1610
|
+
},
|
|
1611
|
+
onError: options == null ? void 0 : options.onError,
|
|
1612
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1613
|
+
});
|
|
1614
|
+
}
|
|
1615
|
+
useCustomerRefreshToken(options) {
|
|
1616
|
+
return (0, import_react_query2.useMutation)({
|
|
1617
|
+
mutationFn: () => __async(this, null, function* () {
|
|
1618
|
+
return yield this.ensureCustomerAuth().refreshToken();
|
|
1619
|
+
}),
|
|
1620
|
+
onSuccess: (data) => {
|
|
1621
|
+
var _a;
|
|
1622
|
+
this.queryClient.invalidateQueries({ queryKey: customerKeys.me() });
|
|
1623
|
+
(_a = options == null ? void 0 : options.onSuccess) == null ? void 0 : _a.call(options, data);
|
|
1624
|
+
},
|
|
1625
|
+
onError: options == null ? void 0 : options.onError,
|
|
1626
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1627
|
+
});
|
|
1628
|
+
}
|
|
1629
|
+
useCustomerChangePassword(options) {
|
|
1630
|
+
return (0, import_react_query2.useMutation)({
|
|
1631
|
+
mutationFn: (data) => __async(this, null, function* () {
|
|
1632
|
+
yield this.ensureCustomerAuth().changePassword(data.currentPassword, data.newPassword);
|
|
1633
|
+
}),
|
|
1634
|
+
onSuccess: options == null ? void 0 : options.onSuccess,
|
|
1635
|
+
onError: options == null ? void 0 : options.onError,
|
|
1636
|
+
onSettled: options == null ? void 0 : options.onSettled
|
|
1637
|
+
});
|
|
1638
|
+
}
|
|
1639
|
+
// ===== Customer Cache Utilities =====
|
|
1640
|
+
invalidateCustomerQueries() {
|
|
1641
|
+
return this.queryClient.invalidateQueries({ queryKey: customerKeys.all });
|
|
1642
|
+
}
|
|
1643
|
+
getCustomerData() {
|
|
1644
|
+
return this.queryClient.getQueryData(customerKeys.me());
|
|
1645
|
+
}
|
|
1646
|
+
setCustomerData(data) {
|
|
1647
|
+
this.queryClient.setQueryData(customerKeys.me(), data);
|
|
1648
|
+
}
|
|
1100
1649
|
};
|
|
1101
1650
|
|
|
1102
1651
|
// src/core/client/client.ts
|
|
@@ -1114,8 +1663,19 @@ var BrowserClient = class {
|
|
|
1114
1663
|
};
|
|
1115
1664
|
this.state = { metadata };
|
|
1116
1665
|
this.queryClient = getQueryClient();
|
|
1117
|
-
this.
|
|
1118
|
-
this.
|
|
1666
|
+
this.customer = new CustomerAuth(this.config.clientKey, this.baseUrl, options.customer);
|
|
1667
|
+
this.cart = new CartApi({
|
|
1668
|
+
clientKey: this.config.clientKey,
|
|
1669
|
+
customerToken: () => this.customer.getToken(),
|
|
1670
|
+
baseUrl: this.baseUrl
|
|
1671
|
+
});
|
|
1672
|
+
this.collections = new CollectionClient(
|
|
1673
|
+
this.config.clientKey,
|
|
1674
|
+
void 0,
|
|
1675
|
+
this.baseUrl,
|
|
1676
|
+
() => this.customer.getToken()
|
|
1677
|
+
);
|
|
1678
|
+
this.query = new QueryHooks(this.queryClient, this.collections, this.customer);
|
|
1119
1679
|
}
|
|
1120
1680
|
from(collection) {
|
|
1121
1681
|
return this.collections.from(collection);
|
|
@@ -1128,68 +1688,14 @@ function createBrowserClient(options) {
|
|
|
1128
1688
|
return new BrowserClient(options);
|
|
1129
1689
|
}
|
|
1130
1690
|
|
|
1131
|
-
// src/core/api/order-api.ts
|
|
1132
|
-
var OrderApi = class {
|
|
1133
|
-
constructor(options) {
|
|
1134
|
-
if (!options.clientKey) {
|
|
1135
|
-
throw createConfigError("clientKey is required for OrderApi.");
|
|
1136
|
-
}
|
|
1137
|
-
if (!options.secretKey) {
|
|
1138
|
-
throw createConfigError("secretKey is required for OrderApi.");
|
|
1139
|
-
}
|
|
1140
|
-
this.clientKey = options.clientKey;
|
|
1141
|
-
this.secretKey = options.secretKey;
|
|
1142
|
-
this.baseUrl = options.baseUrl;
|
|
1143
|
-
}
|
|
1144
|
-
request(endpoint, body) {
|
|
1145
|
-
return __async(this, null, function* () {
|
|
1146
|
-
const response = yield _fetch(endpoint, {
|
|
1147
|
-
method: "POST",
|
|
1148
|
-
clientKey: this.clientKey,
|
|
1149
|
-
secretKey: this.secretKey,
|
|
1150
|
-
baseUrl: this.baseUrl,
|
|
1151
|
-
body: JSON.stringify(body)
|
|
1152
|
-
});
|
|
1153
|
-
let data;
|
|
1154
|
-
try {
|
|
1155
|
-
data = yield response.json();
|
|
1156
|
-
} catch (e) {
|
|
1157
|
-
throw createApiError(
|
|
1158
|
-
`Invalid JSON response from ${endpoint}`,
|
|
1159
|
-
response.status,
|
|
1160
|
-
void 0,
|
|
1161
|
-
"Server returned an invalid response.",
|
|
1162
|
-
"Check if the API endpoint is available."
|
|
1163
|
-
);
|
|
1164
|
-
}
|
|
1165
|
-
if (data.error) {
|
|
1166
|
-
const errorMessage = typeof data.error === "string" ? data.error : "Unknown API error";
|
|
1167
|
-
throw createApiError(
|
|
1168
|
-
errorMessage,
|
|
1169
|
-
response.status,
|
|
1170
|
-
data,
|
|
1171
|
-
errorMessage,
|
|
1172
|
-
"An error occurred while processing the request."
|
|
1173
|
-
);
|
|
1174
|
-
}
|
|
1175
|
-
return data;
|
|
1176
|
-
});
|
|
1177
|
-
}
|
|
1178
|
-
createOrder(params) {
|
|
1179
|
-
return this.request("/api/orders/create", params);
|
|
1180
|
-
}
|
|
1181
|
-
updateOrder(params) {
|
|
1182
|
-
return this.request("/api/orders/update", params);
|
|
1183
|
-
}
|
|
1184
|
-
updateTransaction(params) {
|
|
1185
|
-
return this.request("/api/transactions/update", params);
|
|
1186
|
-
}
|
|
1187
|
-
};
|
|
1188
|
-
|
|
1189
1691
|
// src/core/client/client.server.ts
|
|
1190
1692
|
var ServerClient = class {
|
|
1191
1693
|
constructor(options) {
|
|
1192
|
-
|
|
1694
|
+
if (typeof window !== "undefined") {
|
|
1695
|
+
throw createConfigError(
|
|
1696
|
+
"ServerClient must not be used in a browser environment. This risks exposing your secretKey in client bundles. Use createBrowserClient() for browser code instead."
|
|
1697
|
+
);
|
|
1698
|
+
}
|
|
1193
1699
|
if (!options.clientKey) {
|
|
1194
1700
|
throw createConfigError("clientKey is required.");
|
|
1195
1701
|
}
|
|
@@ -1200,7 +1706,7 @@ var ServerClient = class {
|
|
|
1200
1706
|
this.baseUrl = resolveApiUrl(options);
|
|
1201
1707
|
const metadata = {
|
|
1202
1708
|
timestamp: Date.now(),
|
|
1203
|
-
userAgent:
|
|
1709
|
+
userAgent: "Node.js"
|
|
1204
1710
|
};
|
|
1205
1711
|
this.state = { metadata };
|
|
1206
1712
|
this.api = new OrderApi({
|
|
@@ -1208,6 +1714,16 @@ var ServerClient = class {
|
|
|
1208
1714
|
secretKey: this.config.secretKey,
|
|
1209
1715
|
baseUrl: this.baseUrl
|
|
1210
1716
|
});
|
|
1717
|
+
this.cart = new CartApi({
|
|
1718
|
+
clientKey: this.config.clientKey,
|
|
1719
|
+
secretKey: this.config.secretKey,
|
|
1720
|
+
baseUrl: this.baseUrl
|
|
1721
|
+
});
|
|
1722
|
+
this.product = new ProductApi({
|
|
1723
|
+
clientKey: this.config.clientKey,
|
|
1724
|
+
secretKey: this.config.secretKey,
|
|
1725
|
+
baseUrl: this.baseUrl
|
|
1726
|
+
});
|
|
1211
1727
|
this.collections = new CollectionClient(
|
|
1212
1728
|
this.config.clientKey,
|
|
1213
1729
|
this.config.secretKey,
|
|
@@ -1261,6 +1777,11 @@ function handleWebhook(request, handler, options) {
|
|
|
1261
1777
|
return __async(this, null, function* () {
|
|
1262
1778
|
try {
|
|
1263
1779
|
const rawBody = yield request.text();
|
|
1780
|
+
if (!(options == null ? void 0 : options.secret)) {
|
|
1781
|
+
console.warn(
|
|
1782
|
+
"[@01.software/sdk] Webhook signature verification is skipped because no secret was provided. Pass { secret } to handleWebhook() to enable signature verification."
|
|
1783
|
+
);
|
|
1784
|
+
}
|
|
1264
1785
|
if (options == null ? void 0 : options.secret) {
|
|
1265
1786
|
const signature = request.headers.get("x-webhook-signature") || "";
|
|
1266
1787
|
const valid = yield verifySignature(rawBody, options.secret, signature);
|
|
@@ -1286,10 +1807,7 @@ function handleWebhook(request, handler, options) {
|
|
|
1286
1807
|
} catch (error) {
|
|
1287
1808
|
console.error("Webhook processing error:", error);
|
|
1288
1809
|
return new Response(
|
|
1289
|
-
JSON.stringify({
|
|
1290
|
-
error: "Internal server error",
|
|
1291
|
-
message: error instanceof Error ? error.message : "Unknown error"
|
|
1292
|
-
}),
|
|
1810
|
+
JSON.stringify({ error: "Internal server error" }),
|
|
1293
1811
|
{ status: 500, headers: { "Content-Type": "application/json" } }
|
|
1294
1812
|
);
|
|
1295
1813
|
}
|
|
@@ -1306,10 +1824,13 @@ function createTypedWebhookHandler(collection, handler) {
|
|
|
1306
1824
|
|
|
1307
1825
|
// src/utils/order/generateOrderNumber.ts
|
|
1308
1826
|
var generateOrderNumber = () => {
|
|
1827
|
+
var _a;
|
|
1309
1828
|
const year = (/* @__PURE__ */ new Date()).getFullYear().toString().slice(-2);
|
|
1310
1829
|
const month = ((/* @__PURE__ */ new Date()).getMonth() + 1).toString().padStart(2, "0");
|
|
1311
1830
|
const day = (/* @__PURE__ */ new Date()).getDate().toString().padStart(2, "0");
|
|
1312
|
-
const
|
|
1831
|
+
const array = new Uint32Array(1);
|
|
1832
|
+
globalThis.crypto.getRandomValues(array);
|
|
1833
|
+
const random = (((_a = array[0]) != null ? _a : 0) % 1e6).toString().padStart(6, "0");
|
|
1313
1834
|
return `${year}${month}${day}${random}`;
|
|
1314
1835
|
};
|
|
1315
1836
|
|