@scayle/storefront-core 7.35.0 → 7.37.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/CHANGELOG.md CHANGED
@@ -1,5 +1,18 @@
1
1
  # @scayle/storefront-core
2
2
 
3
+ ## 7.37.0
4
+
5
+ ### Minor Changes
6
+
7
+ - Update dependency `jose` to the latest `5.2.0` version
8
+
9
+ ## 7.36.0
10
+
11
+ ### Minor Changes
12
+
13
+ - Support `Response` returns in RPC methods
14
+ - Handle 401 from CO and delete session
15
+
3
16
  ## 7.35.0
4
17
 
5
18
  ### Minor Changes
@@ -7,17 +7,16 @@ exports.CustomerAPIClient = void 0;
7
7
  var _fetch = require("../utils/fetch.cjs");
8
8
  var _httpStatus = require("../constants/httpStatus.cjs");
9
9
  class CustomerAPIClient {
10
- headers;
11
10
  baseURL;
12
- constructor(options) {
13
- const {
14
- accessToken,
15
- accessHeader,
16
- baseUrl
17
- } = options;
18
- this.baseURL = baseUrl;
19
- this.headers = {
20
- Authorization: `Bearer ${accessToken}`,
11
+ context;
12
+ constructor(context) {
13
+ this.baseURL = context.checkout.url;
14
+ this.context = context;
15
+ }
16
+ get headers() {
17
+ const accessHeader = this.context.checkout.accessHeader;
18
+ return {
19
+ Authorization: `Bearer ${this.context.accessToken}`,
21
20
  Accept: "application/json",
22
21
  "Content-Type": "application/json",
23
22
  ...(accessHeader ? {
@@ -27,6 +26,10 @@ class CustomerAPIClient {
27
26
  }
28
27
  async handleResponse(response) {
29
28
  if (!response.ok) {
29
+ if (response.status === _httpStatus.HttpStatusCode.UNAUTHORIZED && this.context.accessToken) {
30
+ this.context.log.debug("Invalid Checkout Token. Deleting session");
31
+ await this.context.destroySession();
32
+ }
30
33
  throw new _fetch.FetchError(response);
31
34
  }
32
35
  return await response.json();
@@ -1,19 +1,4 @@
1
- import type { ShopUserAddress, Order, ShopUser, Gender } from '../types';
2
- interface CustomerAPIOptions {
3
- /**
4
- * The OAuth Access Token
5
- */
6
- accessToken: string;
7
- /**
8
- * The OAuth Refresh Token
9
- */
10
- refreshToken: string;
11
- accessHeader: string;
12
- /**
13
- * The Checkout Host
14
- */
15
- baseUrl: string;
16
- }
1
+ import type { ShopUserAddress, Order, ShopUser, Gender, RpcContext } from '../types';
17
2
  interface PaginatedResponse<EntityType> {
18
3
  entities: EntityType[];
19
4
  pagination: {
@@ -50,9 +35,10 @@ interface PasswordUpdate {
50
35
  * @see https://scayle.dev/api/oauth/latest
51
36
  */
52
37
  export declare class CustomerAPIClient {
53
- headers: HeadersInit;
54
38
  baseURL: string;
55
- constructor(options: CustomerAPIOptions);
39
+ context: RpcContext;
40
+ constructor(context: RpcContext);
41
+ get headers(): HeadersInit;
56
42
  handleResponse<BodyType>(response: Response): Promise<BodyType>;
57
43
  /**
58
44
  * Get the addresses for the current customer
@@ -1,13 +1,16 @@
1
1
  import { FetchError } from "../utils/fetch.mjs";
2
2
  import { HttpStatusCode } from "../constants/httpStatus.mjs";
3
3
  export class CustomerAPIClient {
4
- headers;
5
4
  baseURL;
6
- constructor(options) {
7
- const { accessToken, accessHeader, baseUrl } = options;
8
- this.baseURL = baseUrl;
9
- this.headers = {
10
- Authorization: `Bearer ${accessToken}`,
5
+ context;
6
+ constructor(context) {
7
+ this.baseURL = context.checkout.url;
8
+ this.context = context;
9
+ }
10
+ get headers() {
11
+ const accessHeader = this.context.checkout.accessHeader;
12
+ return {
13
+ Authorization: `Bearer ${this.context.accessToken}`,
11
14
  Accept: "application/json",
12
15
  "Content-Type": "application/json",
13
16
  ...accessHeader ? { "X-Access-Header": accessHeader } : {}
@@ -15,6 +18,10 @@ export class CustomerAPIClient {
15
18
  }
16
19
  async handleResponse(response) {
17
20
  if (!response.ok) {
21
+ if (response.status === HttpStatusCode.UNAUTHORIZED && this.context.accessToken) {
22
+ this.context.log.debug("Invalid Checkout Token. Deleting session");
23
+ await this.context.destroySession();
24
+ }
18
25
  throw new FetchError(response);
19
26
  }
20
27
  return await response.json();
@@ -21,12 +21,7 @@ const getOrderById = exports.getOrderById = async function getOrderById2({
21
21
  if (!isOrderInUserOrderlist) {
22
22
  throw new Error("Order not belonging to current user");
23
23
  }
24
- const client = new _customer.CustomerAPIClient({
25
- accessToken: context.accessToken,
26
- refreshToken: context.refreshToken,
27
- accessHeader: context.checkout.accessHeader,
28
- baseUrl: context.checkout.url
29
- });
24
+ const client = new _customer.CustomerAPIClient(context);
30
25
  try {
31
26
  return await client.getOrder(context.shopId, orderId);
32
27
  } catch (error) {
@@ -15,12 +15,7 @@ export const getOrderById = async function getOrderById2({ orderId }, context) {
15
15
  if (!isOrderInUserOrderlist) {
16
16
  throw new Error("Order not belonging to current user");
17
17
  }
18
- const client = new CustomerAPIClient({
19
- accessToken: context.accessToken,
20
- refreshToken: context.refreshToken,
21
- accessHeader: context.checkout.accessHeader,
22
- baseUrl: context.checkout.url
23
- });
18
+ const client = new CustomerAPIClient(context);
24
19
  try {
25
20
  return await client.getOrder(context.shopId, orderId);
26
21
  } catch (error) {
@@ -28,12 +28,7 @@ const updateShopUser = exports.updateShopUser = async function updateShopUser2(p
28
28
  ...context.user,
29
29
  ...updatedUser
30
30
  };
31
- const client = new _customer.CustomerAPIClient({
32
- accessToken: context.accessToken,
33
- refreshToken: context.refreshToken,
34
- accessHeader: context.checkout.accessHeader,
35
- baseUrl: context.checkout.url
36
- });
31
+ const client = new _customer.CustomerAPIClient(context);
37
32
  try {
38
33
  await Promise.all([client.updateContactInfo(shopId, {
39
34
  email: user.email,
@@ -75,12 +70,7 @@ const updatePassword = exports.updatePassword = async function updatePassword2({
75
70
  user: shopUser
76
71
  };
77
72
  }
78
- const client = new _customer.CustomerAPIClient({
79
- accessToken: context.accessToken,
80
- refreshToken: context.refreshToken,
81
- accessHeader: context.checkout.accessHeader,
82
- baseUrl: context.checkout.url
83
- });
73
+ const client = new _customer.CustomerAPIClient(context);
84
74
  const user = await client.updatePassword(context.shopId, {
85
75
  password: oldPassword,
86
76
  newPassword
@@ -22,12 +22,7 @@ export const updateShopUser = async function updateShopUser2(payload, context) {
22
22
  ...context.user,
23
23
  ...updatedUser
24
24
  };
25
- const client = new CustomerAPIClient({
26
- accessToken: context.accessToken,
27
- refreshToken: context.refreshToken,
28
- accessHeader: context.checkout.accessHeader,
29
- baseUrl: context.checkout.url
30
- });
25
+ const client = new CustomerAPIClient(context);
31
26
  try {
32
27
  await Promise.all([
33
28
  client.updateContactInfo(shopId, {
@@ -64,12 +59,7 @@ export const updatePassword = async function updatePassword2({ oldPassword, newP
64
59
  );
65
60
  return { user: shopUser };
66
61
  }
67
- const client = new CustomerAPIClient({
68
- accessToken: context.accessToken,
69
- refreshToken: context.refreshToken,
70
- accessHeader: context.checkout.accessHeader,
71
- baseUrl: context.checkout.url
72
- });
62
+ const client = new CustomerAPIClient(context);
73
63
  const user = await client.updatePassword(context.shopId, {
74
64
  password: oldPassword,
75
65
  newPassword
@@ -7,11 +7,6 @@ exports.getShopUserAddresses = void 0;
7
7
  var _customer = require("../../../api/customer.cjs");
8
8
  const getShopUserAddresses = exports.getShopUserAddresses = async function getShopUserAddresses2(context) {
9
9
  const shopId = context.shopId;
10
- const client = new _customer.CustomerAPIClient({
11
- accessToken: context.accessToken,
12
- refreshToken: context.refreshToken,
13
- accessHeader: context.checkout.accessHeader,
14
- baseUrl: context.checkout.url
15
- });
10
+ const client = new _customer.CustomerAPIClient(context);
16
11
  return (await client.getAddresses(shopId)).entities;
17
12
  };
@@ -1,12 +1,7 @@
1
1
  import { CustomerAPIClient } from "../../../api/customer.mjs";
2
2
  const getShopUserAddresses = async function getShopUserAddresses2(context) {
3
3
  const shopId = context.shopId;
4
- const client = new CustomerAPIClient({
5
- accessToken: context.accessToken,
6
- refreshToken: context.refreshToken,
7
- accessHeader: context.checkout.accessHeader,
8
- baseUrl: context.checkout.url
9
- });
4
+ const client = new CustomerAPIClient(context);
10
5
  return (await client.getAddresses(shopId)).entities;
11
6
  };
12
7
  export { getShopUserAddresses };
@@ -17,12 +17,7 @@ const fetchUser = exports.fetchUser = async function fetchUser2(payload, context
17
17
  const {
18
18
  shopId
19
19
  } = context;
20
- const client = new _customer.CustomerAPIClient({
21
- accessToken: context.accessToken,
22
- refreshToken: context.refreshToken,
23
- accessHeader: context.checkout.accessHeader,
24
- baseUrl: context.checkout.url
25
- });
20
+ const client = new _customer.CustomerAPIClient(context);
26
21
  const user = await client.getMe(shopId);
27
22
  return {
28
23
  ...user,
@@ -40,12 +35,7 @@ const refreshUser = exports.refreshUser = async function refreshUser2(context) {
40
35
  accessToken,
41
36
  shopId
42
37
  } = context;
43
- const client = new _customer.CustomerAPIClient({
44
- accessToken: context.accessToken,
45
- refreshToken: context.refreshToken,
46
- accessHeader: context.checkout.accessHeader,
47
- baseUrl: context.checkout.url
48
- });
38
+ const client = new _customer.CustomerAPIClient(context);
49
39
  const user = await client.getMe(shopId);
50
40
  if (user?.id) {
51
41
  context.updateUser({
@@ -7,12 +7,7 @@ const getUser = function getUser2(context) {
7
7
  const fetchUser = async function fetchUser2(payload, context) {
8
8
  const { accessToken } = payload;
9
9
  const { shopId } = context;
10
- const client = new CustomerAPIClient({
11
- accessToken: context.accessToken,
12
- refreshToken: context.refreshToken,
13
- accessHeader: context.checkout.accessHeader,
14
- baseUrl: context.checkout.url
15
- });
10
+ const client = new CustomerAPIClient(context);
16
11
  const user = await client.getMe(shopId);
17
12
  return {
18
13
  ...user,
@@ -25,12 +20,7 @@ const fetchUser = async function fetchUser2(payload, context) {
25
20
  };
26
21
  const refreshUser = async function refreshUser2(context) {
27
22
  const { accessToken, shopId } = context;
28
- const client = new CustomerAPIClient({
29
- accessToken: context.accessToken,
30
- refreshToken: context.refreshToken,
31
- accessHeader: context.checkout.accessHeader,
32
- baseUrl: context.checkout.url
33
- });
23
+ const client = new CustomerAPIClient(context);
34
24
  const user = await client.getMe(shopId);
35
25
  if (user?.id) {
36
26
  context.updateUser({
@@ -4,7 +4,6 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.removeItemFromWishlist = exports.getWishlist = exports.clearWishlist = exports.addItemToWishlist = void 0;
7
- var _errors = require("../../errors/index.cjs");
8
7
  var _constants = require("../../constants/index.cjs");
9
8
  function getWithParams(params, context) {
10
9
  return params.with ?? context.withParams?.basket ?? _constants.MIN_WITH_PARAMS_WISHLIST;
@@ -41,7 +40,11 @@ const addItemToWishlist = exports.addItemToWishlist = async function addItemToWi
41
40
  message
42
41
  } = result.wishlist;
43
42
  context.log.error("Adding to wishlist failed", result.wishlist);
44
- throw new _errors.BAPIError("BAPI ERROR", code, message, "bapiClient.wishlist.addItem");
43
+ return new Response(JSON.stringify({
44
+ message
45
+ }), {
46
+ status: code
47
+ });
45
48
  }
46
49
  };
47
50
  const getWishlist = exports.getWishlist = async function getWishlist2(options, context) {
@@ -1,10 +1,10 @@
1
1
  import type { WishlistResponseData } from '@aboutyou/backbone/endpoints/wishlist/getWishlist';
2
- import { RpcHandler, WishlistWithOptions } from '../../types';
3
- export declare const addItemToWishlist: RpcHandler<{
2
+ import { RpcHandler, ParamRpcHandler, WishlistWithOptions } from '../../types';
3
+ export declare const addItemToWishlist: ParamRpcHandler<{
4
4
  variantId?: number;
5
5
  productId?: number;
6
6
  with?: WishlistWithOptions;
7
- }, WishlistResponseData>;
7
+ }, WishlistResponseData | Response>;
8
8
  export declare const getWishlist: RpcHandler<WishlistWithOptions | undefined, WishlistResponseData>;
9
9
  export declare const removeItemFromWishlist: RpcHandler<{
10
10
  itemKey: string;
@@ -1,4 +1,3 @@
1
- import { BAPIError } from "../../errors/index.mjs";
2
1
  import { MIN_WITH_PARAMS_WISHLIST } from "../../constants/index.mjs";
3
2
  function getWithParams(params, context) {
4
3
  return params.with ?? context.withParams?.basket ?? MIN_WITH_PARAMS_WISHLIST;
@@ -25,12 +24,7 @@ export const addItemToWishlist = async function addItemToWishlist2(options, cont
25
24
  } else {
26
25
  const { code, message } = result.wishlist;
27
26
  context.log.error("Adding to wishlist failed", result.wishlist);
28
- throw new BAPIError(
29
- "BAPI ERROR",
30
- code,
31
- message,
32
- "bapiClient.wishlist.addItem"
33
- );
27
+ return new Response(JSON.stringify({ message }), { status: code });
34
28
  }
35
29
  };
36
30
  export const getWishlist = async function getWishlist2(options, context) {
@@ -1,4 +1,4 @@
1
1
  import { RpcContext } from './context';
2
- export type ParamRpcHandler<Params extends Record<string, any>, Response> = (params: Params, context: RpcContext) => Promise<Response> | Response;
3
- export type NoParamRpcHandler<Response> = (context: RpcContext) => Promise<Response> | Response;
2
+ export type ParamRpcHandler<Params extends Record<string, any>, ResponseType> = (params: Params, context: RpcContext) => Promise<ResponseType> | ResponseType;
3
+ export type NoParamRpcHandler<ResponseType> = (context: RpcContext) => Promise<ResponseType> | ResponseType;
4
4
  export type RpcHandler<A, B = void> = B extends void ? NoParamRpcHandler<A> : ParamRpcHandler<A, B>;
@@ -0,0 +1 @@
1
+ "use strict";
@@ -0,0 +1 @@
1
+ export type * from '@aboutyou/backbone/endpoints/variants/variantsByIds';
File without changes
@@ -0,0 +1,13 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.unwrap = unwrap;
7
+ async function unwrap(response) {
8
+ if (response instanceof Response) {
9
+ console.log("unwrapping for ", response.url);
10
+ return await response.json();
11
+ }
12
+ return response;
13
+ }
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Unwrap a possible response into its body
3
+ * @param x
4
+ * @returns
5
+ */
6
+ export declare function unwrap<T>(response: Response | T): Promise<T>;
@@ -0,0 +1,7 @@
1
+ export async function unwrap(response) {
2
+ if (response instanceof Response) {
3
+ console.log("unwrapping for ", response.url);
4
+ return await response.json();
5
+ }
6
+ return response;
7
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@scayle/storefront-core",
3
- "version": "7.35.0",
3
+ "version": "7.37.0",
4
4
  "description": "Collection of essential utilities to work with the Storefront API",
5
5
  "author": "SCAYLE Commerce Engine",
6
6
  "license": "MIT",
@@ -61,7 +61,7 @@
61
61
  "dependencies": {
62
62
  "@aboutyou/backbone": "16.0.2",
63
63
  "crypto-js": "4.2.0",
64
- "jose": "^4.14.4",
64
+ "jose": "^5.2.0",
65
65
  "radash": "^11.0.0",
66
66
  "slugify": "^1.6.0",
67
67
  "ufo": "^1.1.1",
@@ -72,9 +72,9 @@
72
72
  "@scayle/eslint-config-storefront": "3.2.6",
73
73
  "@scayle/prettier-config-storefront": "2.0.2",
74
74
  "@types/crypto-js": "4.2.1",
75
- "@types/node": "20.10.7",
75
+ "@types/node": "20.11.4",
76
76
  "@types/webpack-env": "1.18.4",
77
- "@vitest/coverage-v8": "1.1.3",
77
+ "@vitest/coverage-v8": "1.2.0",
78
78
  "eslint": "8.56.0",
79
79
  "eslint-formatter-gitlab": "5.1.0",
80
80
  "prettier": "3.0.0",
@@ -84,7 +84,7 @@
84
84
  "typescript": "5.3.3",
85
85
  "unbuild": "2.0.0",
86
86
  "unstorage": "1.10.1",
87
- "vitest": "1.1.3"
87
+ "vitest": "1.2.0"
88
88
  },
89
89
  "optionalDependencies": {
90
90
  "redis": "4"