@rechargeapps/storefront-client 0.15.2 → 0.16.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.
@@ -3,6 +3,7 @@
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
5
  var bundlingData = require('@rechargeapps/bundling-data');
6
+ var nanoid = require('nanoid');
6
7
  var request = require('../utils/request.js');
7
8
  var options = require('../utils/options.js');
8
9
  var cdn = require('./cdn.js');
@@ -26,7 +27,7 @@ async function getBundleId(bundle) {
26
27
  const opts = options.getOptions();
27
28
  const isValid = await validateBundle(bundle);
28
29
  if (!isValid) {
29
- throw new Error("Bundle selection is invalid.");
30
+ throw new Error("Bundle is invalid.");
30
31
  }
31
32
  const timestampSeconds = await getTimestampSecondsFromServer();
32
33
  const bundleData = bundlingData.toLineItemProperty({
@@ -59,6 +60,33 @@ async function getBundleId(bundle) {
59
60
  throw new Error(`2: failed generating rb_id ${e}`);
60
61
  }
61
62
  }
63
+ function getDynamicBundleItems(bundle, shopifyProductHandle) {
64
+ const isValid = validateDynamicBundle(bundle);
65
+ if (isValid !== true) {
66
+ throw new Error(`Dynamic Bundle is invalid. ${isValid}`);
67
+ }
68
+ const bundleId = `${nanoid.nanoid(9)}:${bundle.externalProductId}`;
69
+ return bundle.selections.map((item) => {
70
+ const itemData = {
71
+ id: item.externalVariantId,
72
+ quantity: item.quantity,
73
+ properties: {
74
+ _rc_bundle: bundleId,
75
+ _rc_bundle_variant: bundle.externalVariantId,
76
+ _rc_bundle_parent: shopifyProductHandle,
77
+ _rc_bundle_collection_id: item.collectionId
78
+ }
79
+ };
80
+ if (item.sellingPlan) {
81
+ itemData.selling_plan = item.sellingPlan;
82
+ } else if (item.shippingIntervalFrequency) {
83
+ itemData.properties.shipping_interval_frequency = item.shippingIntervalFrequency;
84
+ itemData.properties.shipping_interval_unit_type = item.shippingIntervalUnitType;
85
+ itemData.id = `${item.discountedVariantId}`;
86
+ }
87
+ return itemData;
88
+ });
89
+ }
62
90
  async function validateBundle(bundle) {
63
91
  try {
64
92
  const bundleSettings = await cdn.getCDNBundleSettings(bundle.externalProductId);
@@ -68,7 +96,43 @@ async function validateBundle(bundle) {
68
96
  return false;
69
97
  }
70
98
  }
99
+ const intervalUnitGroups = {
100
+ day: ["day", "days", "Days"],
101
+ days: ["day", "days", "Days"],
102
+ Days: ["day", "days", "Days"],
103
+ week: ["week", "weeks", "Weeks"],
104
+ weeks: ["week", "weeks", "Weeks"],
105
+ Weeks: ["week", "weeks", "Weeks"],
106
+ month: ["month", "months", "Months"],
107
+ months: ["month", "months", "Months"],
108
+ Months: ["month", "months", "Months"]
109
+ };
110
+ function validateDynamicBundle(bundle) {
111
+ if (!bundle) {
112
+ return "No bundle defined.";
113
+ }
114
+ if (bundle.selections.length === 0) {
115
+ return "No selections defined.";
116
+ }
117
+ const { shippingIntervalFrequency, shippingIntervalUnitType } = bundle.selections.find((selection) => selection.shippingIntervalFrequency || selection.shippingIntervalUnitType) || {};
118
+ if (shippingIntervalFrequency || shippingIntervalUnitType) {
119
+ if (!shippingIntervalFrequency || !shippingIntervalUnitType) {
120
+ return "Shipping intervals do not match on selections.";
121
+ } else {
122
+ const shippingIntervalUnitGroup = intervalUnitGroups[shippingIntervalUnitType];
123
+ for (let x = 0; x < bundle.selections.length; x++) {
124
+ const { shippingIntervalFrequency: frequency, shippingIntervalUnitType: unitType } = bundle.selections[x];
125
+ if (frequency && frequency !== shippingIntervalFrequency || unitType && !shippingIntervalUnitGroup.includes(unitType)) {
126
+ return "Shipping intervals do not match on selections.";
127
+ }
128
+ }
129
+ }
130
+ }
131
+ return true;
132
+ }
71
133
 
72
134
  exports.getBundleId = getBundleId;
135
+ exports.getDynamicBundleItems = getDynamicBundleItems;
73
136
  exports.validateBundle = validateBundle;
137
+ exports.validateDynamicBundle = validateDynamicBundle;
74
138
  //# sourceMappingURL=bundle.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"bundle.js","sources":["../../../src/api/bundle.ts"],"sourcesContent":["import { toLineItemProperty } from '@rechargeapps/bundling-data';\nimport { Bundle } from '../types';\nimport { shopifyAppProxyRequest } from '../utils/request';\nimport { getOptions } from '../utils/options';\nimport { getCDNBundleSettings } from './cdn';\n\nconst STORE_FRONT_MANAGER_URL = '/bundling-storefront-manager';\n\nfunction getTimestampSecondsFromClient(): number {\n /**\n * Get the current unix epoch in seconds from the client-side.\n */\n return Math.ceil(Date.now() / 1000);\n}\n\nasync function getTimestampSecondsFromServer(): Promise<number> {\n /**\n * Get the unix epoch from the server instead of using it directly from the\n * client. This must reduce even more the number of invalid Bundles.\n */\n try {\n const { timestamp } = await shopifyAppProxyRequest<{ timestamp: number }>('get', `${STORE_FRONT_MANAGER_URL}/t`, {\n headers: { 'X-Recharge-App': 'storefront-client' },\n });\n return timestamp;\n } catch (ex) {\n console.error(`Fetch failed: ${ex}. Using client-side date.`);\n return getTimestampSecondsFromClient();\n }\n}\n\nexport async function getBundleId(bundle: Bundle): Promise<string> {\n const opts = getOptions();\n const isValid = await validateBundle(bundle);\n if (!isValid) {\n throw new Error('Bundle selection is invalid.');\n }\n const timestampSeconds = await getTimestampSecondsFromServer();\n const bundleData = toLineItemProperty({\n variantId: bundle.externalVariantId,\n version: timestampSeconds,\n items: bundle.selections.map(item => {\n return {\n collectionId: item.collectionId,\n productId: item.externalProductId,\n variantId: item.externalVariantId,\n quantity: item.quantity,\n sku: '',\n };\n }),\n });\n\n try {\n const payload = await shopifyAppProxyRequest<{ id: string; code: number; message: string }>(\n 'post',\n `${STORE_FRONT_MANAGER_URL}/api/v1/bundles`,\n {\n data: {\n bundle: bundleData,\n },\n headers: {\n Origin: `https://${opts.storeIdentifier}`,\n },\n }\n );\n\n if (!payload.id || payload.code !== 200) {\n throw new Error(`1: failed generating rb_id: ${JSON.stringify(payload)}`);\n }\n\n return payload.id;\n } catch (e) {\n // Handle NetworkError exceptions\n throw new Error(`2: failed generating rb_id ${e}`);\n }\n}\n\nexport async function validateBundle(bundle: Bundle): Promise<boolean> {\n try {\n const bundleSettings = await getCDNBundleSettings(bundle.externalProductId);\n // once we implement this function, we can make it raise an exception\n // we could also have a local store relative to this function so we don't have to pass bundleProduct\n return !!bundle && !!bundleSettings;\n } catch (e) {\n console.error('Error fetching bundle settings');\n return false;\n }\n}\n"],"names":["shopifyAppProxyRequest","getOptions","toLineItemProperty","getCDNBundleSettings"],"mappings":"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"}
1
+ {"version":3,"file":"bundle.js","sources":["../../../src/api/bundle.ts"],"sourcesContent":["import { toLineItemProperty } from '@rechargeapps/bundling-data';\nimport { nanoid } from 'nanoid';\nimport { Bundle, BundleItem } from '../types';\nimport { shopifyAppProxyRequest } from '../utils/request';\nimport { getOptions } from '../utils/options';\nimport { getCDNBundleSettings } from './cdn';\n\nconst STORE_FRONT_MANAGER_URL = '/bundling-storefront-manager';\n\nfunction getTimestampSecondsFromClient(): number {\n /**\n * Get the current unix epoch in seconds from the client-side.\n */\n return Math.ceil(Date.now() / 1000);\n}\n\nasync function getTimestampSecondsFromServer(): Promise<number> {\n /**\n * Get the unix epoch from the server instead of using it directly from the\n * client. This must reduce even more the number of invalid Bundles.\n */\n try {\n const { timestamp } = await shopifyAppProxyRequest<{ timestamp: number }>('get', `${STORE_FRONT_MANAGER_URL}/t`, {\n headers: { 'X-Recharge-App': 'storefront-client' },\n });\n return timestamp;\n } catch (ex) {\n console.error(`Fetch failed: ${ex}. Using client-side date.`);\n return getTimestampSecondsFromClient();\n }\n}\n\nexport async function getBundleId(bundle: Bundle): Promise<string> {\n const opts = getOptions();\n const isValid = await validateBundle(bundle);\n if (!isValid) {\n throw new Error('Bundle is invalid.');\n }\n const timestampSeconds = await getTimestampSecondsFromServer();\n const bundleData = toLineItemProperty({\n variantId: bundle.externalVariantId,\n version: timestampSeconds,\n items: bundle.selections.map(item => {\n return {\n collectionId: item.collectionId,\n productId: item.externalProductId,\n variantId: item.externalVariantId,\n quantity: item.quantity,\n sku: '',\n };\n }),\n });\n\n try {\n const payload = await shopifyAppProxyRequest<{ id: string; code: number; message: string }>(\n 'post',\n `${STORE_FRONT_MANAGER_URL}/api/v1/bundles`,\n {\n data: {\n bundle: bundleData,\n },\n headers: {\n Origin: `https://${opts.storeIdentifier}`,\n },\n }\n );\n\n if (!payload.id || payload.code !== 200) {\n throw new Error(`1: failed generating rb_id: ${JSON.stringify(payload)}`);\n }\n\n return payload.id;\n } catch (e) {\n // Handle NetworkError exceptions\n throw new Error(`2: failed generating rb_id ${e}`);\n }\n}\n\nexport function getDynamicBundleItems(bundle: Bundle, shopifyProductHandle: string) {\n const isValid = validateDynamicBundle(bundle);\n if (isValid !== true) {\n throw new Error(`Dynamic Bundle is invalid. ${isValid}`);\n }\n // generate unique id for dynamic bundle\n const bundleId = `${nanoid(9)}:${bundle.externalProductId}`;\n return bundle.selections.map(item => {\n const itemData: BundleItem = {\n id: item.externalVariantId,\n quantity: item.quantity,\n properties: {\n _rc_bundle: bundleId,\n _rc_bundle_variant: bundle.externalVariantId,\n _rc_bundle_parent: shopifyProductHandle,\n _rc_bundle_collection_id: item.collectionId,\n },\n };\n\n if (item.sellingPlan) {\n // this is used by SCI stores\n itemData.selling_plan = item.sellingPlan;\n } else if (item.shippingIntervalFrequency) {\n // this is used by RCS stores\n itemData.properties.shipping_interval_frequency = item.shippingIntervalFrequency;\n itemData.properties.shipping_interval_unit_type = item.shippingIntervalUnitType;\n itemData.id = `${item.discountedVariantId}`;\n }\n\n return itemData;\n });\n}\n\nexport async function validateBundle(bundle: Bundle): Promise<boolean> {\n try {\n const bundleSettings = await getCDNBundleSettings(bundle.externalProductId);\n // once we implement this function, we can make it raise an exception\n // we could also have a local store relative to this function so we don't have to pass bundleProduct\n return !!bundle && !!bundleSettings;\n } catch (e) {\n console.error('Error fetching bundle settings');\n return false;\n }\n}\n\nconst intervalUnitGroups = {\n day: ['day', 'days', 'Days'],\n days: ['day', 'days', 'Days'],\n Days: ['day', 'days', 'Days'],\n week: ['week', 'weeks', 'Weeks'],\n weeks: ['week', 'weeks', 'Weeks'],\n Weeks: ['week', 'weeks', 'Weeks'],\n month: ['month', 'months', 'Months'],\n months: ['month', 'months', 'Months'],\n Months: ['month', 'months', 'Months'],\n};\n\n/**\n * Validates a dynamic bundle\n *\n * @param bundle Dynamic Bundle being validated\n * @returns true or error message\n */\nexport function validateDynamicBundle(bundle: Bundle): true | string {\n if (!bundle) {\n return 'No bundle defined.';\n }\n if (bundle.selections.length === 0) {\n return 'No selections defined.';\n }\n // validation for RCS onetimes\n const { shippingIntervalFrequency, shippingIntervalUnitType } =\n bundle.selections.find(selection => selection.shippingIntervalFrequency || selection.shippingIntervalUnitType) ||\n {};\n if (shippingIntervalFrequency || shippingIntervalUnitType) {\n // if we have shipping intervals then we should have both defined\n if (!shippingIntervalFrequency || !shippingIntervalUnitType) {\n return 'Shipping intervals do not match on selections.';\n } else {\n // if we have shipping intervals then any that are defined should match\n const shippingIntervalUnitGroup = intervalUnitGroups[shippingIntervalUnitType];\n for (let x = 0; x < bundle.selections.length; x++) {\n const { shippingIntervalFrequency: frequency, shippingIntervalUnitType: unitType } = bundle.selections[x];\n if (\n (frequency && frequency !== shippingIntervalFrequency) ||\n (unitType && !shippingIntervalUnitGroup.includes(unitType))\n ) {\n return 'Shipping intervals do not match on selections.';\n }\n }\n }\n }\n return true;\n}\n"],"names":["shopifyAppProxyRequest","getOptions","toLineItemProperty","nanoid","getCDNBundleSettings"],"mappings":"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"}
package/dist/cjs/index.js CHANGED
@@ -43,7 +43,9 @@ exports.getCDNStoreSettings = cdn.getCDNStoreSettings;
43
43
  exports.getCDNWidgetSettings = cdn.getCDNWidgetSettings;
44
44
  exports.resetCDNCache = cdn.resetCDNCache;
45
45
  exports.getBundleId = bundle.getBundleId;
46
+ exports.getDynamicBundleItems = bundle.getDynamicBundleItems;
46
47
  exports.validateBundle = bundle.validateBundle;
48
+ exports.validateDynamicBundle = bundle.validateDynamicBundle;
47
49
  exports.activateMembership = membership.activateMembership;
48
50
  exports.cancelMembership = membership.cancelMembership;
49
51
  exports.getMembership = membership.getMembership;
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
1
+ {"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -1,4 +1,5 @@
1
1
  import { toLineItemProperty } from '@rechargeapps/bundling-data';
2
+ import { nanoid } from 'nanoid';
2
3
  import { shopifyAppProxyRequest } from '../utils/request.js';
3
4
  import { getOptions } from '../utils/options.js';
4
5
  import { getCDNBundleSettings } from './cdn.js';
@@ -22,7 +23,7 @@ async function getBundleId(bundle) {
22
23
  const opts = getOptions();
23
24
  const isValid = await validateBundle(bundle);
24
25
  if (!isValid) {
25
- throw new Error("Bundle selection is invalid.");
26
+ throw new Error("Bundle is invalid.");
26
27
  }
27
28
  const timestampSeconds = await getTimestampSecondsFromServer();
28
29
  const bundleData = toLineItemProperty({
@@ -55,6 +56,33 @@ async function getBundleId(bundle) {
55
56
  throw new Error(`2: failed generating rb_id ${e}`);
56
57
  }
57
58
  }
59
+ function getDynamicBundleItems(bundle, shopifyProductHandle) {
60
+ const isValid = validateDynamicBundle(bundle);
61
+ if (isValid !== true) {
62
+ throw new Error(`Dynamic Bundle is invalid. ${isValid}`);
63
+ }
64
+ const bundleId = `${nanoid(9)}:${bundle.externalProductId}`;
65
+ return bundle.selections.map((item) => {
66
+ const itemData = {
67
+ id: item.externalVariantId,
68
+ quantity: item.quantity,
69
+ properties: {
70
+ _rc_bundle: bundleId,
71
+ _rc_bundle_variant: bundle.externalVariantId,
72
+ _rc_bundle_parent: shopifyProductHandle,
73
+ _rc_bundle_collection_id: item.collectionId
74
+ }
75
+ };
76
+ if (item.sellingPlan) {
77
+ itemData.selling_plan = item.sellingPlan;
78
+ } else if (item.shippingIntervalFrequency) {
79
+ itemData.properties.shipping_interval_frequency = item.shippingIntervalFrequency;
80
+ itemData.properties.shipping_interval_unit_type = item.shippingIntervalUnitType;
81
+ itemData.id = `${item.discountedVariantId}`;
82
+ }
83
+ return itemData;
84
+ });
85
+ }
58
86
  async function validateBundle(bundle) {
59
87
  try {
60
88
  const bundleSettings = await getCDNBundleSettings(bundle.externalProductId);
@@ -64,6 +92,40 @@ async function validateBundle(bundle) {
64
92
  return false;
65
93
  }
66
94
  }
95
+ const intervalUnitGroups = {
96
+ day: ["day", "days", "Days"],
97
+ days: ["day", "days", "Days"],
98
+ Days: ["day", "days", "Days"],
99
+ week: ["week", "weeks", "Weeks"],
100
+ weeks: ["week", "weeks", "Weeks"],
101
+ Weeks: ["week", "weeks", "Weeks"],
102
+ month: ["month", "months", "Months"],
103
+ months: ["month", "months", "Months"],
104
+ Months: ["month", "months", "Months"]
105
+ };
106
+ function validateDynamicBundle(bundle) {
107
+ if (!bundle) {
108
+ return "No bundle defined.";
109
+ }
110
+ if (bundle.selections.length === 0) {
111
+ return "No selections defined.";
112
+ }
113
+ const { shippingIntervalFrequency, shippingIntervalUnitType } = bundle.selections.find((selection) => selection.shippingIntervalFrequency || selection.shippingIntervalUnitType) || {};
114
+ if (shippingIntervalFrequency || shippingIntervalUnitType) {
115
+ if (!shippingIntervalFrequency || !shippingIntervalUnitType) {
116
+ return "Shipping intervals do not match on selections.";
117
+ } else {
118
+ const shippingIntervalUnitGroup = intervalUnitGroups[shippingIntervalUnitType];
119
+ for (let x = 0; x < bundle.selections.length; x++) {
120
+ const { shippingIntervalFrequency: frequency, shippingIntervalUnitType: unitType } = bundle.selections[x];
121
+ if (frequency && frequency !== shippingIntervalFrequency || unitType && !shippingIntervalUnitGroup.includes(unitType)) {
122
+ return "Shipping intervals do not match on selections.";
123
+ }
124
+ }
125
+ }
126
+ }
127
+ return true;
128
+ }
67
129
 
68
- export { getBundleId, validateBundle };
130
+ export { getBundleId, getDynamicBundleItems, validateBundle, validateDynamicBundle };
69
131
  //# sourceMappingURL=bundle.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"bundle.js","sources":["../../../src/api/bundle.ts"],"sourcesContent":["import { toLineItemProperty } from '@rechargeapps/bundling-data';\nimport { Bundle } from '../types';\nimport { shopifyAppProxyRequest } from '../utils/request';\nimport { getOptions } from '../utils/options';\nimport { getCDNBundleSettings } from './cdn';\n\nconst STORE_FRONT_MANAGER_URL = '/bundling-storefront-manager';\n\nfunction getTimestampSecondsFromClient(): number {\n /**\n * Get the current unix epoch in seconds from the client-side.\n */\n return Math.ceil(Date.now() / 1000);\n}\n\nasync function getTimestampSecondsFromServer(): Promise<number> {\n /**\n * Get the unix epoch from the server instead of using it directly from the\n * client. This must reduce even more the number of invalid Bundles.\n */\n try {\n const { timestamp } = await shopifyAppProxyRequest<{ timestamp: number }>('get', `${STORE_FRONT_MANAGER_URL}/t`, {\n headers: { 'X-Recharge-App': 'storefront-client' },\n });\n return timestamp;\n } catch (ex) {\n console.error(`Fetch failed: ${ex}. Using client-side date.`);\n return getTimestampSecondsFromClient();\n }\n}\n\nexport async function getBundleId(bundle: Bundle): Promise<string> {\n const opts = getOptions();\n const isValid = await validateBundle(bundle);\n if (!isValid) {\n throw new Error('Bundle selection is invalid.');\n }\n const timestampSeconds = await getTimestampSecondsFromServer();\n const bundleData = toLineItemProperty({\n variantId: bundle.externalVariantId,\n version: timestampSeconds,\n items: bundle.selections.map(item => {\n return {\n collectionId: item.collectionId,\n productId: item.externalProductId,\n variantId: item.externalVariantId,\n quantity: item.quantity,\n sku: '',\n };\n }),\n });\n\n try {\n const payload = await shopifyAppProxyRequest<{ id: string; code: number; message: string }>(\n 'post',\n `${STORE_FRONT_MANAGER_URL}/api/v1/bundles`,\n {\n data: {\n bundle: bundleData,\n },\n headers: {\n Origin: `https://${opts.storeIdentifier}`,\n },\n }\n );\n\n if (!payload.id || payload.code !== 200) {\n throw new Error(`1: failed generating rb_id: ${JSON.stringify(payload)}`);\n }\n\n return payload.id;\n } catch (e) {\n // Handle NetworkError exceptions\n throw new Error(`2: failed generating rb_id ${e}`);\n }\n}\n\nexport async function validateBundle(bundle: Bundle): Promise<boolean> {\n try {\n const bundleSettings = await getCDNBundleSettings(bundle.externalProductId);\n // once we implement this function, we can make it raise an exception\n // we could also have a local store relative to this function so we don't have to pass bundleProduct\n return !!bundle && !!bundleSettings;\n } catch (e) {\n console.error('Error fetching bundle settings');\n return false;\n }\n}\n"],"names":[],"mappings":";;;;;AAIA,MAAM,uBAAuB,GAAG,8BAA8B,CAAC;AAC/D,SAAS,6BAA6B,GAAG;AACzC,EAAE,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,GAAG,CAAC,CAAC;AACrC,CAAC;AACD,eAAe,6BAA6B,GAAG;AAC/C,EAAE,IAAI;AACN,IAAI,MAAM,EAAE,SAAS,EAAE,GAAG,MAAM,sBAAsB,CAAC,KAAK,EAAE,CAAC,EAAE,uBAAuB,CAAC,EAAE,CAAC,EAAE;AAC9F,MAAM,OAAO,EAAE,EAAE,gBAAgB,EAAE,mBAAmB,EAAE;AACxD,KAAK,CAAC,CAAC;AACP,IAAI,OAAO,SAAS,CAAC;AACrB,GAAG,CAAC,OAAO,EAAE,EAAE;AACf,IAAI,OAAO,CAAC,KAAK,CAAC,CAAC,cAAc,EAAE,EAAE,CAAC,yBAAyB,CAAC,CAAC,CAAC;AAClE,IAAI,OAAO,6BAA6B,EAAE,CAAC;AAC3C,GAAG;AACH,CAAC;AACM,eAAe,WAAW,CAAC,MAAM,EAAE;AAC1C,EAAE,MAAM,IAAI,GAAG,UAAU,EAAE,CAAC;AAC5B,EAAE,MAAM,OAAO,GAAG,MAAM,cAAc,CAAC,MAAM,CAAC,CAAC;AAC/C,EAAE,IAAI,CAAC,OAAO,EAAE;AAChB,IAAI,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,CAAC;AACpD,GAAG;AACH,EAAE,MAAM,gBAAgB,GAAG,MAAM,6BAA6B,EAAE,CAAC;AACjE,EAAE,MAAM,UAAU,GAAG,kBAAkB,CAAC;AACxC,IAAI,SAAS,EAAE,MAAM,CAAC,iBAAiB;AACvC,IAAI,OAAO,EAAE,gBAAgB;AAC7B,IAAI,KAAK,EAAE,MAAM,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,IAAI,KAAK;AAC3C,MAAM,OAAO;AACb,QAAQ,YAAY,EAAE,IAAI,CAAC,YAAY;AACvC,QAAQ,SAAS,EAAE,IAAI,CAAC,iBAAiB;AACzC,QAAQ,SAAS,EAAE,IAAI,CAAC,iBAAiB;AACzC,QAAQ,QAAQ,EAAE,IAAI,CAAC,QAAQ;AAC/B,QAAQ,GAAG,EAAE,EAAE;AACf,OAAO,CAAC;AACR,KAAK,CAAC;AACN,GAAG,CAAC,CAAC;AACL,EAAE,IAAI;AACN,IAAI,MAAM,OAAO,GAAG,MAAM,sBAAsB,CAAC,MAAM,EAAE,CAAC,EAAE,uBAAuB,CAAC,eAAe,CAAC,EAAE;AACtG,MAAM,IAAI,EAAE;AACZ,QAAQ,MAAM,EAAE,UAAU;AAC1B,OAAO;AACP,MAAM,OAAO,EAAE;AACf,QAAQ,MAAM,EAAE,CAAC,QAAQ,EAAE,IAAI,CAAC,eAAe,CAAC,CAAC;AACjD,OAAO;AACP,KAAK,CAAC,CAAC;AACP,IAAI,IAAI,CAAC,OAAO,CAAC,EAAE,IAAI,OAAO,CAAC,IAAI,KAAK,GAAG,EAAE;AAC7C,MAAM,MAAM,IAAI,KAAK,CAAC,CAAC,4BAA4B,EAAE,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC;AAChF,KAAK;AACL,IAAI,OAAO,OAAO,CAAC,EAAE,CAAC;AACtB,GAAG,CAAC,OAAO,CAAC,EAAE;AACd,IAAI,MAAM,IAAI,KAAK,CAAC,CAAC,2BAA2B,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;AACvD,GAAG;AACH,CAAC;AACM,eAAe,cAAc,CAAC,MAAM,EAAE;AAC7C,EAAE,IAAI;AACN,IAAI,MAAM,cAAc,GAAG,MAAM,oBAAoB,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC;AAChF,IAAI,OAAO,CAAC,CAAC,MAAM,IAAI,CAAC,CAAC,cAAc,CAAC;AACxC,GAAG,CAAC,OAAO,CAAC,EAAE;AACd,IAAI,OAAO,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAC;AACpD,IAAI,OAAO,KAAK,CAAC;AACjB,GAAG;AACH;;;;"}
1
+ {"version":3,"file":"bundle.js","sources":["../../../src/api/bundle.ts"],"sourcesContent":["import { toLineItemProperty } from '@rechargeapps/bundling-data';\nimport { nanoid } from 'nanoid';\nimport { Bundle, BundleItem } from '../types';\nimport { shopifyAppProxyRequest } from '../utils/request';\nimport { getOptions } from '../utils/options';\nimport { getCDNBundleSettings } from './cdn';\n\nconst STORE_FRONT_MANAGER_URL = '/bundling-storefront-manager';\n\nfunction getTimestampSecondsFromClient(): number {\n /**\n * Get the current unix epoch in seconds from the client-side.\n */\n return Math.ceil(Date.now() / 1000);\n}\n\nasync function getTimestampSecondsFromServer(): Promise<number> {\n /**\n * Get the unix epoch from the server instead of using it directly from the\n * client. This must reduce even more the number of invalid Bundles.\n */\n try {\n const { timestamp } = await shopifyAppProxyRequest<{ timestamp: number }>('get', `${STORE_FRONT_MANAGER_URL}/t`, {\n headers: { 'X-Recharge-App': 'storefront-client' },\n });\n return timestamp;\n } catch (ex) {\n console.error(`Fetch failed: ${ex}. Using client-side date.`);\n return getTimestampSecondsFromClient();\n }\n}\n\nexport async function getBundleId(bundle: Bundle): Promise<string> {\n const opts = getOptions();\n const isValid = await validateBundle(bundle);\n if (!isValid) {\n throw new Error('Bundle is invalid.');\n }\n const timestampSeconds = await getTimestampSecondsFromServer();\n const bundleData = toLineItemProperty({\n variantId: bundle.externalVariantId,\n version: timestampSeconds,\n items: bundle.selections.map(item => {\n return {\n collectionId: item.collectionId,\n productId: item.externalProductId,\n variantId: item.externalVariantId,\n quantity: item.quantity,\n sku: '',\n };\n }),\n });\n\n try {\n const payload = await shopifyAppProxyRequest<{ id: string; code: number; message: string }>(\n 'post',\n `${STORE_FRONT_MANAGER_URL}/api/v1/bundles`,\n {\n data: {\n bundle: bundleData,\n },\n headers: {\n Origin: `https://${opts.storeIdentifier}`,\n },\n }\n );\n\n if (!payload.id || payload.code !== 200) {\n throw new Error(`1: failed generating rb_id: ${JSON.stringify(payload)}`);\n }\n\n return payload.id;\n } catch (e) {\n // Handle NetworkError exceptions\n throw new Error(`2: failed generating rb_id ${e}`);\n }\n}\n\nexport function getDynamicBundleItems(bundle: Bundle, shopifyProductHandle: string) {\n const isValid = validateDynamicBundle(bundle);\n if (isValid !== true) {\n throw new Error(`Dynamic Bundle is invalid. ${isValid}`);\n }\n // generate unique id for dynamic bundle\n const bundleId = `${nanoid(9)}:${bundle.externalProductId}`;\n return bundle.selections.map(item => {\n const itemData: BundleItem = {\n id: item.externalVariantId,\n quantity: item.quantity,\n properties: {\n _rc_bundle: bundleId,\n _rc_bundle_variant: bundle.externalVariantId,\n _rc_bundle_parent: shopifyProductHandle,\n _rc_bundle_collection_id: item.collectionId,\n },\n };\n\n if (item.sellingPlan) {\n // this is used by SCI stores\n itemData.selling_plan = item.sellingPlan;\n } else if (item.shippingIntervalFrequency) {\n // this is used by RCS stores\n itemData.properties.shipping_interval_frequency = item.shippingIntervalFrequency;\n itemData.properties.shipping_interval_unit_type = item.shippingIntervalUnitType;\n itemData.id = `${item.discountedVariantId}`;\n }\n\n return itemData;\n });\n}\n\nexport async function validateBundle(bundle: Bundle): Promise<boolean> {\n try {\n const bundleSettings = await getCDNBundleSettings(bundle.externalProductId);\n // once we implement this function, we can make it raise an exception\n // we could also have a local store relative to this function so we don't have to pass bundleProduct\n return !!bundle && !!bundleSettings;\n } catch (e) {\n console.error('Error fetching bundle settings');\n return false;\n }\n}\n\nconst intervalUnitGroups = {\n day: ['day', 'days', 'Days'],\n days: ['day', 'days', 'Days'],\n Days: ['day', 'days', 'Days'],\n week: ['week', 'weeks', 'Weeks'],\n weeks: ['week', 'weeks', 'Weeks'],\n Weeks: ['week', 'weeks', 'Weeks'],\n month: ['month', 'months', 'Months'],\n months: ['month', 'months', 'Months'],\n Months: ['month', 'months', 'Months'],\n};\n\n/**\n * Validates a dynamic bundle\n *\n * @param bundle Dynamic Bundle being validated\n * @returns true or error message\n */\nexport function validateDynamicBundle(bundle: Bundle): true | string {\n if (!bundle) {\n return 'No bundle defined.';\n }\n if (bundle.selections.length === 0) {\n return 'No selections defined.';\n }\n // validation for RCS onetimes\n const { shippingIntervalFrequency, shippingIntervalUnitType } =\n bundle.selections.find(selection => selection.shippingIntervalFrequency || selection.shippingIntervalUnitType) ||\n {};\n if (shippingIntervalFrequency || shippingIntervalUnitType) {\n // if we have shipping intervals then we should have both defined\n if (!shippingIntervalFrequency || !shippingIntervalUnitType) {\n return 'Shipping intervals do not match on selections.';\n } else {\n // if we have shipping intervals then any that are defined should match\n const shippingIntervalUnitGroup = intervalUnitGroups[shippingIntervalUnitType];\n for (let x = 0; x < bundle.selections.length; x++) {\n const { shippingIntervalFrequency: frequency, shippingIntervalUnitType: unitType } = bundle.selections[x];\n if (\n (frequency && frequency !== shippingIntervalFrequency) ||\n (unitType && !shippingIntervalUnitGroup.includes(unitType))\n ) {\n return 'Shipping intervals do not match on selections.';\n }\n }\n }\n }\n return true;\n}\n"],"names":[],"mappings":"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"}
package/dist/esm/index.js CHANGED
@@ -2,7 +2,7 @@ export { createAddress, deleteAddress, getAddress, listAddresses, mergeAddresses
2
2
  export { loginShopifyApi, loginShopifyAppProxy } from './api/auth.js';
3
3
  export { applyDiscount, getCharge, listCharges, processCharge, removeDiscount, skipCharge, unskipCharge } from './api/charge.js';
4
4
  export { getCDNBundleSettings, getCDNProduct, getCDNProductAndSettings, getCDNProducts, getCDNProductsAndSettings, getCDNStoreSettings, getCDNWidgetSettings, resetCDNCache } from './api/cdn.js';
5
- export { getBundleId, validateBundle } from './api/bundle.js';
5
+ export { getBundleId, getDynamicBundleItems, validateBundle, validateDynamicBundle } from './api/bundle.js';
6
6
  export { activateMembership, cancelMembership, getMembership, listMemberships } from './api/membership.js';
7
7
  export { createOnetime, deleteOnetime, getOnetime, listOnetimes, updateOnetime } from './api/onetime.js';
8
8
  export { getOrder, listOrders } from './api/order.js';
package/dist/index.d.ts CHANGED
@@ -119,6 +119,8 @@ interface AnalyticsData {
119
119
  utm_timestamp: string;
120
120
  }[];
121
121
  }
122
+ /** preferred values are 'day', 'week', 'month' other values are available for backwards compatibility */
123
+ declare type IntervalUnit = 'day' | 'week' | 'month' | 'days' | 'Days' | 'weeks' | 'Weeks' | 'months' | 'Months';
122
124
  declare type SubType<T, TRequired extends keyof T = keyof T, TOptional extends keyof T = keyof T> = Required<Pick<T, TRequired>> & Partial<Pick<T, TOptional>>;
123
125
 
124
126
  interface ShippingLine {
@@ -233,20 +235,33 @@ interface OrdersResponse {
233
235
  }
234
236
  declare type OrderSortBy = 'id-asc' | 'id-desc' | 'updated_at-asc' | 'updated_at-desc' | 'processed_at-asc' | 'processed_at-desc' | 'scheduled_at-asc' | 'scheduled_at-desc';
235
237
  interface OrderListParams extends ListParams<OrderSortBy> {
238
+ /** Filter orders by address. */
236
239
  address_id?: string;
240
+ /** Filter orders by charge. */
237
241
  charge_id?: string;
242
+ /** Show orders created after the given date. */
238
243
  created_at_min?: IsoDateString;
244
+ /** Show orders created before the given date. */
239
245
  created_at_max?: IsoDateString;
240
- customer_id?: string;
241
- external_customer_id?: string;
246
+ /** Filter orders by external_order_id. */
247
+ external_order_id?: string;
248
+ /** Filter orders by id. */
242
249
  ids?: string[];
250
+ /** Show orders scheduled before the given date. */
243
251
  scheduled_at_max?: IsoDateString;
252
+ /** Show orders scheduled after the given date. */
244
253
  scheduled_at_min?: IsoDateString;
254
+ /** Filter orders with/without external_order_id. */
245
255
  has_external_order?: string;
256
+ /** Filter orders by status. */
246
257
  status?: OrderStatus;
258
+ /** Filter orders by type. */
247
259
  type?: OrderType;
260
+ /** Filter orders by subscription or onetime. */
248
261
  purchase_item_id?: string;
262
+ /** Show orders updated before the given date. */
249
263
  updated_at_max?: IsoDateString;
264
+ /** Show orders updated after the given date. */
250
265
  updated_at_min?: IsoDateString;
251
266
  }
252
267
 
@@ -353,8 +368,6 @@ declare type ChargeSortBy = 'id-asc' | 'id-desc' | 'updated_at-asc' | 'updated_a
353
368
  interface ChargeListParams extends ListParams<ChargeSortBy> {
354
369
  /** Filter Charges by Address. */
355
370
  address_id?: string;
356
- /** Filter Charges by Customer. */
357
- customer_id?: string;
358
371
  /** List Charges that contain the given discount_id. */
359
372
  discount_id?: string;
360
373
  /** List Charges that contain the given discount_code. */
@@ -519,11 +532,16 @@ interface AddressListResponse {
519
532
  }
520
533
  declare type AddressSortBy = 'id-asc' | 'id-desc' | 'updated_at-asc' | 'updated_at-desc';
521
534
  interface AddressListParams extends ListParams<AddressSortBy> {
522
- customer_id?: string;
535
+ /** Returns addresses that have the provided discount_id. */
523
536
  discount_id?: string;
537
+ /** Returns addresses that have the provided discount_code. */
524
538
  discount_code?: string;
539
+ /** Returns addresses created after the given time. */
525
540
  created_at_min?: IsoDateString;
541
+ /** Returns addresses created before the given time. */
526
542
  created_at_max?: IsoDateString;
543
+ /** Returns active addresses. */
544
+ is_active?: boolean;
527
545
  }
528
546
 
529
547
  interface Session {
@@ -606,15 +624,32 @@ interface BundleSelection {
606
624
  externalProductId: string;
607
625
  externalVariantId: string;
608
626
  quantity: number;
627
+ sellingPlan?: number;
628
+ shippingIntervalFrequency?: number;
629
+ shippingIntervalUnitType?: IntervalUnit;
630
+ discountedVariantId?: number;
609
631
  }
610
632
  interface Bundle {
611
633
  externalVariantId: string;
612
634
  externalProductId: string;
613
635
  selections: BundleSelection[];
614
636
  }
637
+ interface BundleProperties {
638
+ _rc_bundle: string;
639
+ _rc_bundle_variant: string;
640
+ _rc_bundle_parent: string;
641
+ _rc_bundle_collection_id: string;
642
+ shipping_interval_frequency?: number;
643
+ shipping_interval_unit_type?: IntervalUnit;
644
+ }
645
+ interface BundleItem {
646
+ id: string;
647
+ properties: BundleProperties;
648
+ quantity: number;
649
+ selling_plan?: number;
650
+ }
615
651
 
616
652
  declare type FirstOption = 'onetime' | 'autodeliver';
617
- declare type IntervalUnit = 'day' | 'week' | 'month';
618
653
  declare type PriceAdjustmentsType = 'percentage';
619
654
  declare type StorefrontPurchaseOption = 'subscription_and_onetime' | 'subscription_only' | 'onetime_only' | 'inactive';
620
655
  interface BundleTranslations {
@@ -1029,12 +1064,15 @@ declare type UpdatePaymentMethodRequest = Partial<Pick<PaymentMethod, PaymentMet
1029
1064
  /** no sorting options for payment_methods, always by id-desc */
1030
1065
  declare type PaymentMethodSortBy = null;
1031
1066
  interface PaymentMethodListParams extends ListParams<PaymentMethodSortBy> {
1032
- customer_id?: string;
1067
+ /** Return the payment_methods linked to the given processor_name. */
1033
1068
  processor_name?: ProcessorName;
1069
+ /** Return the payment_methods linked to the given address_id. */
1034
1070
  address_id?: string;
1071
+ /** Return the payment_methods linked to the given processor_payment_method_token. */
1035
1072
  processor_payment_method_token?: string;
1036
1073
  }
1037
1074
 
1075
+ declare type SubscriptionStatus = 'active' | 'cancelled' | 'expired';
1038
1076
  interface Subscription {
1039
1077
  /** Unique numeric identifier for the subscription. */
1040
1078
  id: number;
@@ -1092,7 +1130,7 @@ interface Subscription {
1092
1130
  */
1093
1131
  order_interval_frequency: number;
1094
1132
  /** The frequency unit used to determine when a subscription’s order is created. */
1095
- order_interval_unit: 'day' | 'week' | 'month';
1133
+ order_interval_unit: IntervalUnit;
1096
1134
  /** The presentment currency of the subscription. */
1097
1135
  presentment_currency: string | null;
1098
1136
  /** The price of the item before discounts, taxes, or shipping have been applied. */
@@ -1111,7 +1149,7 @@ interface Subscription {
1111
1149
  * The status of the subscription.
1112
1150
  * expired - This status occurs when the maximum number of charges for a product has been reached.
1113
1151
  */
1114
- status: 'active' | 'cancelled' | 'expired';
1152
+ status: SubscriptionStatus;
1115
1153
  /** The date time at which the purchase_item record was last updated. */
1116
1154
  updated_at: IsoDateString;
1117
1155
  /** The name of the variant in a shop’s catalog. */
@@ -1124,9 +1162,24 @@ interface SubscriptionsResponse {
1124
1162
  }
1125
1163
  declare type SubscriptionSortBy = 'id-asc' | 'id-desc' | 'created_at-asc' | 'created_at-desc' | 'updated_at-asc' | 'updated_at-desc';
1126
1164
  interface SubscriptionListParams extends ListParams<SubscriptionSortBy> {
1127
- created_at_min?: IsoDateString;
1165
+ /** Return the subscriptions linked to the given address_id. */
1166
+ address_id?: string;
1167
+ /** Return the subscriptions linked to the given address_ids. */
1168
+ address_ids?: string[];
1169
+ /** Return the subscriptions created before the given date. */
1128
1170
  created_at_max?: IsoDateString;
1129
- customer_id?: string;
1171
+ /** Return the subscriptions created after the given date. */
1172
+ created_at_min?: IsoDateString;
1173
+ /** Return the subscriptions linked to the given external_variant_id */
1174
+ external_variant_id?: string;
1175
+ /** Comma-separated list of subscription_ids to filter */
1176
+ ids?: string[];
1177
+ /** Return the subscriptions with specified status. */
1178
+ status?: SubscriptionStatus;
1179
+ /** Return the subscriptions updated before the given date. */
1180
+ updated_at_max?: IsoDateString;
1181
+ /** Return the subscriptions updated after the given date. */
1182
+ updated_at_min?: IsoDateString;
1130
1183
  }
1131
1184
  declare type SubscriptionRequiredCreateProps = 'address_id' | 'charge_interval_frequency' | 'external_variant_id' | 'next_charge_scheduled_at' | 'order_interval_frequency' | 'order_interval_unit' | 'quantity';
1132
1185
  declare type SubscriptionOptionalCreateProps = 'expire_after_specific_number_of_charges' | 'order_day_of_month' | 'order_day_of_week' | 'external_product_id' | 'product_title' | 'properties' | 'status';
@@ -1239,16 +1292,21 @@ declare type MembershipIncludes = `${membershipIncludes}` | `${membershipInclude
1239
1292
  /** @internal */
1240
1293
  interface MembershipListParams extends ListParams<MembershipsSortBy> {
1241
1294
  include?: MembershipIncludes;
1242
- customer_id?: number;
1243
- customer_name?: string;
1244
- customer_email?: string;
1245
- membership_program_ids?: string;
1295
+ /** Return the memberships linked to the given membership_program_ids. */
1296
+ membership_program_ids?: string[];
1297
+ /** Return the memberships with specified status. */
1246
1298
  status?: MembershipStatus;
1299
+ /** Returns memberships created after the given time. */
1247
1300
  created_at_min?: IsoDateString;
1301
+ /** Returns memberships created before the given time. */
1248
1302
  created_at_max?: IsoDateString;
1303
+ /** Returns memberships expiring after the given time. */
1249
1304
  expires_at_min?: IsoDateString;
1305
+ /** Returns memberships expiring before the given time. */
1250
1306
  expires_at_max?: IsoDateString;
1307
+ /** If true the response will include the cancelled Memberships as well as the others. */
1251
1308
  include_cancelled?: boolean;
1309
+ /** If true the response will include the deleted Memberships as well as the others. */
1252
1310
  include_deleted?: boolean;
1253
1311
  }
1254
1312
  /** @internal */
@@ -1317,7 +1375,26 @@ interface OnetimesResponse {
1317
1375
  onetimes: Onetime[];
1318
1376
  }
1319
1377
  declare type OnetimesSortBy = 'id-asc' | 'id-desc' | 'created_at-asc' | 'created_at-desc' | 'updated_at-asc' | 'updated_at-desc';
1320
- declare type OnetimeListParams = ListParams<OnetimesSortBy>;
1378
+ interface OnetimeListParams extends ListParams<OnetimesSortBy> {
1379
+ /** Return the onetimes linked to the given address_id. */
1380
+ address_id?: string;
1381
+ /** Return the onetimes linked to the given address_ids. */
1382
+ address_ids?: string[];
1383
+ /** Return the onetimes created before the given date. */
1384
+ created_at_max?: IsoDateString;
1385
+ /** Return the onetimes created after the given date. */
1386
+ created_at_min?: IsoDateString;
1387
+ /** Return the onetimes linked to the given external_variant_id */
1388
+ external_variant_id?: string;
1389
+ /** Comma-separated list of onetime_ids to filter */
1390
+ ids?: string[];
1391
+ /** If true the response will include the cancelled Onetimes as well as the others. */
1392
+ include_cancelled?: boolean;
1393
+ /** Return the onetimes updated before the given date. */
1394
+ updated_at_max?: IsoDateString;
1395
+ /** Return the onetimes updated after the given date. */
1396
+ updated_at_min?: IsoDateString;
1397
+ }
1321
1398
 
1322
1399
  /** @internal */
1323
1400
  declare type StorefrontEnvironment = 'stage' | 'prod';
@@ -1393,9 +1470,13 @@ interface PlansResponse {
1393
1470
  }
1394
1471
  declare type PlanSortBy = 'id-asc' | 'id-desc' | 'updated_at-asc' | 'updated_at-desc';
1395
1472
  interface PlanListParams extends ListParams<PlanSortBy> {
1473
+ /** Return the Plans linked to the Product record in Recharge with the indicated external_product_id */
1396
1474
  external_product_id?: string;
1475
+ /** Return the plans updated before the given date. */
1397
1476
  updated_at_max?: IsoDateString;
1477
+ /** Return the plans updated after the given date. */
1398
1478
  updated_at_min?: IsoDateString;
1479
+ /** Return the plans that are of a specific type. */
1399
1480
  type?: PlanType;
1400
1481
  }
1401
1482
 
@@ -1409,7 +1490,15 @@ declare function getCDNBundleSettings(externalProductId: string | number): Promi
1409
1490
  declare function resetCDNCache(): Promise<void>;
1410
1491
 
1411
1492
  declare function getBundleId(bundle: Bundle): Promise<string>;
1493
+ declare function getDynamicBundleItems(bundle: Bundle, shopifyProductHandle: string): BundleItem[];
1412
1494
  declare function validateBundle(bundle: Bundle): Promise<boolean>;
1495
+ /**
1496
+ * Validates a dynamic bundle
1497
+ *
1498
+ * @param bundle Dynamic Bundle being validated
1499
+ * @returns true or error message
1500
+ */
1501
+ declare function validateDynamicBundle(bundle: Bundle): true | string;
1413
1502
 
1414
1503
  /** @internal Retrieves membership information for passed in id */
1415
1504
  declare function getMembership(session: Session, id: string | number): Promise<Membership>;
@@ -1483,4 +1572,4 @@ declare const api: {
1483
1572
  };
1484
1573
  declare function initRecharge(opt?: InitOptions): void;
1485
1574
 
1486
- export { ActivateMembershipRequest, Address, AddressListParams, AddressListResponse, AddressResponse, AddressSortBy, AnalyticsData, ApplyDiscountRequest, AssociatedAddress, Bundle, BundleSelection, BundleTranslations, CDNBaseWidgetSettings, CDNBundleLayoutSettings, CDNBundleSettings, CDNBundleStep, CDNBundleStepOption, CDNBundleVariant, CDNBundleVariantOptionSource, CDNBundleVariantSelectionDefault, CDNPrices, CDNProduct, CDNProductAndSettings, CDNProductKeyObject, CDNProductOption, CDNProductOptionValue, CDNProductRaw, CDNProductResource, CDNProductsAndSettings, CDNProductsAndSettingsResource, CDNSellingPlan, CDNSellingPlanAllocations, CDNSellingPlanGroup, CDNStoreSettings, CDNSubscriptionOption, CDNVariant, CDNVariantOptionValue, CDNWidgetSettings, CDNWidgetSettingsRaw, CDNWidgetSettingsResource, CRUDRequestOptions, CancelMembershipRequest, CancelSubscriptionRequest, ChannelSettings, Charge, ChargeListParams, ChargeListResponse, ChargeResponse, ChargeSortBy, ChargeStatus, ColorString, CreateAddressRequest, CreateOnetimeRequest, CreateSubscriptionRequest, Customer, CustomerDeliveryScheduleParams, CustomerDeliveryScheduleResponse, CustomerIncludes, CustomerOptionalUpdateProps, Delivery, Discount, ExternalId, ExternalTransactionId, FirstOption, GetCustomerOptions, GetRequestOptions, HTMLString, InitOptions, IntervalUnit, IsoDateString, LineItem, ListParams, LoginResponse, Membership, MembershipIncludes, MembershipListParams, MembershipListResponse, MembershipResponse, MembershipStatus, MembershipsSortBy, MergeAddressesRequest, Method, Onetime, OnetimeCreateProps, OnetimeListParams, OnetimeOptionalCreateProps, OnetimeOptionalUpdateProps, OnetimeRequiredCreateProps, OnetimesResponse, OnetimesSortBy, Order, OrderListParams, OrderSortBy, OrderStatus, OrderType, OrdersResponse, PaymentDetails, PaymentMethod, PaymentMethodListParams, PaymentMethodOptionalUpdateProps, PaymentMethodSortBy, PaymentMethodStatus, PaymentMethodsResponse, PaymentType, Plan, PlanListParams, PlanSortBy, PlanType, PlansResponse, PriceAdjustmentsType, ProcessorName, ProductImage, Property, Request, RequestHeaders, RequestOptions, RequestOptionsHeaders, Session, ShippingLine, SkipFutureChargeAddressRequest, SkipFutureChargeAddressResponse, StorefrontEnvironment, StorefrontOptions, StorefrontPurchaseOption, SubType, Subscription, SubscriptionListParams, SubscriptionOptionalCreateProps, SubscriptionOptionalUpdateProps, SubscriptionPreferences, SubscriptionRequiredCreateProps, SubscriptionSortBy, SubscriptionsResponse, TaxLine, Translations, UpdateAddressRequest, UpdateCustomerRequest, UpdateOnetimeRequest, UpdatePaymentMethodRequest, UpdateSubscriptionParams, UpdateSubscriptionRequest, WidgetIconColor, WidgetTemplateType, activateMembership, activateSubscription, api, applyDiscount, cancelMembership, cancelSubscription, createAddress, createOnetime, createSubscription, deleteAddress, deleteOnetime, getAddress, getBundleId, getCDNBundleSettings, getCDNProduct, getCDNProductAndSettings, getCDNProducts, getCDNProductsAndSettings, getCDNStoreSettings, getCDNWidgetSettings, getCharge, getCustomer, getDeliverySchedule, getMembership, getOnetime, getOrder, getPaymentMethod, getPlan, getSubscription, initRecharge, listAddresses, listCharges, listMemberships, listOnetimes, listOrders, listPaymentMethods, listPlans, listSubscriptions, loginShopifyApi, loginShopifyAppProxy, membershipIncludes, mergeAddresses, processCharge, removeDiscount, resetCDNCache, skipCharge, skipFutureCharge, skipSubscriptionCharge, unskipCharge, updateAddress, updateCustomer, updateOnetime, updatePaymentMethod, updateSubscription, updateSubscriptionAddress, updateSubscriptionChargeDate, validateBundle };
1575
+ export { ActivateMembershipRequest, Address, AddressListParams, AddressListResponse, AddressResponse, AddressSortBy, AnalyticsData, ApplyDiscountRequest, AssociatedAddress, Bundle, BundleItem, BundleProperties, BundleSelection, BundleTranslations, CDNBaseWidgetSettings, CDNBundleLayoutSettings, CDNBundleSettings, CDNBundleStep, CDNBundleStepOption, CDNBundleVariant, CDNBundleVariantOptionSource, CDNBundleVariantSelectionDefault, CDNPrices, CDNProduct, CDNProductAndSettings, CDNProductKeyObject, CDNProductOption, CDNProductOptionValue, CDNProductRaw, CDNProductResource, CDNProductsAndSettings, CDNProductsAndSettingsResource, CDNSellingPlan, CDNSellingPlanAllocations, CDNSellingPlanGroup, CDNStoreSettings, CDNSubscriptionOption, CDNVariant, CDNVariantOptionValue, CDNWidgetSettings, CDNWidgetSettingsRaw, CDNWidgetSettingsResource, CRUDRequestOptions, CancelMembershipRequest, CancelSubscriptionRequest, ChannelSettings, Charge, ChargeListParams, ChargeListResponse, ChargeResponse, ChargeSortBy, ChargeStatus, ColorString, CreateAddressRequest, CreateOnetimeRequest, CreateSubscriptionRequest, Customer, CustomerDeliveryScheduleParams, CustomerDeliveryScheduleResponse, CustomerIncludes, CustomerOptionalUpdateProps, Delivery, Discount, ExternalId, ExternalTransactionId, FirstOption, GetCustomerOptions, GetRequestOptions, HTMLString, InitOptions, IntervalUnit, IsoDateString, LineItem, ListParams, LoginResponse, Membership, MembershipIncludes, MembershipListParams, MembershipListResponse, MembershipResponse, MembershipStatus, MembershipsSortBy, MergeAddressesRequest, Method, Onetime, OnetimeCreateProps, OnetimeListParams, OnetimeOptionalCreateProps, OnetimeOptionalUpdateProps, OnetimeRequiredCreateProps, OnetimesResponse, OnetimesSortBy, Order, OrderListParams, OrderSortBy, OrderStatus, OrderType, OrdersResponse, PaymentDetails, PaymentMethod, PaymentMethodListParams, PaymentMethodOptionalUpdateProps, PaymentMethodSortBy, PaymentMethodStatus, PaymentMethodsResponse, PaymentType, Plan, PlanListParams, PlanSortBy, PlanType, PlansResponse, PriceAdjustmentsType, ProcessorName, ProductImage, Property, Request, RequestHeaders, RequestOptions, RequestOptionsHeaders, Session, ShippingLine, SkipFutureChargeAddressRequest, SkipFutureChargeAddressResponse, StorefrontEnvironment, StorefrontOptions, StorefrontPurchaseOption, SubType, Subscription, SubscriptionListParams, SubscriptionOptionalCreateProps, SubscriptionOptionalUpdateProps, SubscriptionPreferences, SubscriptionRequiredCreateProps, SubscriptionSortBy, SubscriptionStatus, SubscriptionsResponse, TaxLine, Translations, UpdateAddressRequest, UpdateCustomerRequest, UpdateOnetimeRequest, UpdatePaymentMethodRequest, UpdateSubscriptionParams, UpdateSubscriptionRequest, WidgetIconColor, WidgetTemplateType, activateMembership, activateSubscription, api, applyDiscount, cancelMembership, cancelSubscription, createAddress, createOnetime, createSubscription, deleteAddress, deleteOnetime, getAddress, getBundleId, getCDNBundleSettings, getCDNProduct, getCDNProductAndSettings, getCDNProducts, getCDNProductsAndSettings, getCDNStoreSettings, getCDNWidgetSettings, getCharge, getCustomer, getDeliverySchedule, getDynamicBundleItems, getMembership, getOnetime, getOrder, getPaymentMethod, getPlan, getSubscription, initRecharge, listAddresses, listCharges, listMemberships, listOnetimes, listOrders, listPaymentMethods, listPlans, listSubscriptions, loginShopifyApi, loginShopifyAppProxy, membershipIncludes, mergeAddresses, processCharge, removeDiscount, resetCDNCache, skipCharge, skipFutureCharge, skipSubscriptionCharge, unskipCharge, updateAddress, updateCustomer, updateOnetime, updatePaymentMethod, updateSubscription, updateSubscriptionAddress, updateSubscriptionChargeDate, validateBundle, validateDynamicBundle };