@unchainedshop/plugins 4.8.19 → 4.8.21

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.
Files changed (53) hide show
  1. package/lib/payment/datatrans-v2/adapter.js +12 -9
  2. package/lib/presets/countries/eu.d.ts +2 -0
  3. package/lib/presets/countries/eu.js +2 -0
  4. package/lib/presets/countries/uk.d.ts +2 -0
  5. package/lib/presets/countries/uk.js +2 -0
  6. package/lib/presets/countries/us.d.ts +2 -0
  7. package/lib/presets/countries/us.js +2 -0
  8. package/lib/pricing/delivery-eu-tax.d.ts +2 -0
  9. package/lib/pricing/delivery-eu-tax.js +55 -0
  10. package/lib/pricing/delivery-swiss-tax.js +7 -26
  11. package/lib/pricing/delivery-uk-tax.d.ts +2 -0
  12. package/lib/pricing/delivery-uk-tax.js +43 -0
  13. package/lib/pricing/delivery-us-sales-tax.d.ts +2 -0
  14. package/lib/pricing/delivery-us-sales-tax.js +58 -0
  15. package/lib/pricing/product-eu-tax.d.ts +2 -0
  16. package/lib/pricing/product-eu-tax.js +56 -0
  17. package/lib/pricing/product-swiss-tax.js +7 -26
  18. package/lib/pricing/product-uk-tax.d.ts +2 -0
  19. package/lib/pricing/product-uk-tax.js +57 -0
  20. package/lib/pricing/product-us-sales-tax.d.ts +2 -0
  21. package/lib/pricing/product-us-sales-tax.js +52 -0
  22. package/lib/pricing/tax/applyTaxRateToTaxableRows.d.ts +23 -0
  23. package/lib/pricing/tax/applyTaxRateToTaxableRows.js +30 -0
  24. package/lib/pricing/tax/ch-tax-rates.json +24 -0
  25. package/lib/pricing/tax/ch.js +6 -30
  26. package/lib/pricing/tax/eraRates.d.ts +10 -0
  27. package/lib/pricing/tax/eraRates.js +15 -0
  28. package/lib/pricing/tax/eu-tax-rates.json +797 -0
  29. package/lib/pricing/tax/eu.d.ts +12 -0
  30. package/lib/pricing/tax/eu.js +38 -0
  31. package/lib/pricing/tax/uk-tax-rates.json +18 -0
  32. package/lib/pricing/tax/uk.d.ts +10 -0
  33. package/lib/pricing/tax/uk.js +23 -0
  34. package/lib/pricing/tax/us-tax-rates.json +334 -0
  35. package/lib/pricing/tax/us.d.ts +11 -0
  36. package/lib/pricing/tax/us.js +20 -0
  37. package/lib/pricing/utils/isDeliveryAddressInCountry.d.ts +1 -1
  38. package/lib/pricing/utils/isDeliveryAddressInCountry.js +3 -8
  39. package/lib/pricing/utils/resolveDeliveryLocation.d.ts +10 -0
  40. package/lib/pricing/utils/resolveDeliveryLocation.js +9 -0
  41. package/lib/quotations/manual/adapter.js +6 -1
  42. package/lib/worker/gc-guests/adapter.d.ts +9 -0
  43. package/lib/worker/gc-guests/adapter.js +56 -0
  44. package/lib/worker/gc-guests/index.d.ts +4 -0
  45. package/lib/worker/gc-guests/index.js +13 -0
  46. package/lib/worker/invalidate-carts/adapter.d.ts +9 -0
  47. package/lib/worker/invalidate-carts/adapter.js +52 -0
  48. package/lib/worker/invalidate-carts/index.d.ts +4 -0
  49. package/lib/worker/invalidate-carts/index.js +13 -0
  50. package/lib/worker/zombie-killer/adapter.d.ts +2 -0
  51. package/lib/worker/zombie-killer/adapter.js +26 -3
  52. package/lib/worker/zombie-killer/index.js +4 -1
  53. package/package.json +2 -2
@@ -0,0 +1,12 @@
1
+ import type { DeliveryProvider } from '@unchainedshop/core-delivery';
2
+ import type { Product } from '@unchainedshop/core-products';
3
+ export declare const EU_TAX_CATEGORY_TAG_PREFIX = "eu-tax-category:";
4
+ export declare const EU_MEMBER_COUNTRY_CODES: string[];
5
+ export declare const isEuMemberCountry: (countryCode?: string | null) => boolean;
6
+ export declare const resolveEuTaxRate: ({ countryCode, category, referenceDate, }: {
7
+ countryCode?: string | null;
8
+ category?: string | null;
9
+ referenceDate?: Date;
10
+ }) => number | null;
11
+ export declare const resolveEuTaxCategoryFromProduct: (product: Product) => string | null;
12
+ export declare const resolveEuTaxCategoryFromDeliveryProvider: (provider: DeliveryProvider) => string | null;
@@ -0,0 +1,38 @@
1
+ import euTaxRates from './eu-tax-rates.json' with { type: 'json' };
2
+ import { compileEraRates, rateForDate } from "./eraRates.js";
3
+ export const EU_TAX_CATEGORY_TAG_PREFIX = 'eu-tax-category:';
4
+ const PROVIDER_CONFIGURATION_KEY = 'eu-tax-category';
5
+ const countryRates = Object.fromEntries(Object.entries(euTaxRates.countries).map(([countryCode, categories]) => [
6
+ countryCode,
7
+ Object.fromEntries(Object.entries(categories).map(([category, eras]) => [
8
+ category,
9
+ rateForDate(compileEraRates(eras, euTaxRates.timezone)),
10
+ ])),
11
+ ]));
12
+ const normalizeCountryCode = (countryCode) => {
13
+ const normalized = countryCode?.toUpperCase().trim() || null;
14
+ return normalized === 'EL' ? 'GR' : normalized;
15
+ };
16
+ export const EU_MEMBER_COUNTRY_CODES = Object.keys(countryRates);
17
+ export const isEuMemberCountry = (countryCode) => {
18
+ const normalized = normalizeCountryCode(countryCode);
19
+ return Boolean(normalized && countryRates[normalized]);
20
+ };
21
+ export const resolveEuTaxRate = ({ countryCode, category, referenceDate, }) => {
22
+ const normalized = normalizeCountryCode(countryCode);
23
+ const categories = normalized ? countryRates[normalized] : null;
24
+ if (!categories)
25
+ return null;
26
+ const resolveRate = (category && categories[category]) || categories.standard;
27
+ return resolveRate(referenceDate);
28
+ };
29
+ export const resolveEuTaxCategoryFromProduct = (product) => {
30
+ const categoryTag = product?.tags?.find((tag) => tag?.trim().toLowerCase().startsWith(EU_TAX_CATEGORY_TAG_PREFIX));
31
+ if (!categoryTag)
32
+ return null;
33
+ return categoryTag.trim().toLowerCase().slice(EU_TAX_CATEGORY_TAG_PREFIX.length) || null;
34
+ };
35
+ export const resolveEuTaxCategoryFromDeliveryProvider = (provider) => {
36
+ const value = provider?.configuration?.find(({ key }) => key === PROVIDER_CONFIGURATION_KEY)?.value;
37
+ return value?.trim().toLowerCase() || null;
38
+ };
@@ -0,0 +1,18 @@
1
+ {
2
+ "source": "https://www.gov.uk/vat-rates",
3
+ "verifiedAt": "2026-08-20",
4
+ "timezone": "+00:00",
5
+ "categories": {
6
+ "standard": [
7
+ { "validFrom": "1991-04-01", "rate": 0.175 },
8
+ { "validFrom": "2008-12-01", "rate": 0.15 },
9
+ { "validFrom": "2010-01-01", "rate": 0.175 },
10
+ { "validFrom": "2011-01-04", "rate": 0.2 }
11
+ ],
12
+ "reduced": [
13
+ { "validFrom": "1994-04-01", "rate": 0.08 },
14
+ { "validFrom": "1997-09-01", "rate": 0.05 }
15
+ ],
16
+ "zero": [{ "validFrom": "1973-04-01", "rate": 0 }]
17
+ }
18
+ }
@@ -0,0 +1,10 @@
1
+ import type { DeliveryProvider } from '@unchainedshop/core-delivery';
2
+ import type { Product } from '@unchainedshop/core-products';
3
+ export declare const UK_VAT_COUNTRY_CODES: string[];
4
+ export interface UkTaxCategoryResolver {
5
+ value: string;
6
+ rate: (referenceDate?: Date) => number;
7
+ }
8
+ export declare const UkTaxCategories: Record<string, UkTaxCategoryResolver>;
9
+ export declare const resolveUkTaxCategoryFromDeliveryProvider: (provider: DeliveryProvider) => UkTaxCategoryResolver | null;
10
+ export declare const resolveUkTaxCategoryFromProduct: (product: Product) => UkTaxCategoryResolver | null;
@@ -0,0 +1,23 @@
1
+ import ukTaxRates from './uk-tax-rates.json' with { type: 'json' };
2
+ import { compileEraRates, rateForDate } from "./eraRates.js";
3
+ export const UK_VAT_COUNTRY_CODES = ['GB', 'IM'];
4
+ export const UkTaxCategories = Object.fromEntries(Object.entries(ukTaxRates.categories).map(([value, eras]) => [
5
+ value.toUpperCase(),
6
+ { value, rate: rateForDate(compileEraRates(eras, ukTaxRates.timezone)) },
7
+ ]));
8
+ export const resolveUkTaxCategoryFromDeliveryProvider = (provider) => {
9
+ const taxCategoryFromProvider = provider?.configuration
10
+ ?.find(({ key }) => {
11
+ if (key === 'uk-tax-category')
12
+ return true;
13
+ return null;
14
+ })
15
+ ?.value?.toUpperCase();
16
+ const taxCategory = taxCategoryFromProvider ? UkTaxCategories[taxCategoryFromProvider] : null;
17
+ return taxCategory;
18
+ };
19
+ export const resolveUkTaxCategoryFromProduct = (product) => {
20
+ const productSpecialTaxTag = product?.tags?.find((tag) => tag?.trim().toLowerCase().startsWith('uk-tax-category:'));
21
+ const taxCategory = Object.values(UkTaxCategories).find((t) => `uk-tax-category:${t.value}` === productSpecialTaxTag?.trim().toLowerCase());
22
+ return taxCategory || null;
23
+ };
@@ -0,0 +1,334 @@
1
+ {
2
+ "source": "https://taxfoundation.org/data/all/state/2026-sales-tax-rates-midyear/",
3
+ "verifiedAt": "2026-08-20",
4
+ "timezone": "-06:00",
5
+ "states": {
6
+ "AK": [
7
+ {
8
+ "validFrom": "2026-07-01",
9
+ "rate": 0.0
10
+ }
11
+ ],
12
+ "AL": [
13
+ {
14
+ "validFrom": "2026-07-01",
15
+ "rate": 0.04
16
+ }
17
+ ],
18
+ "AR": [
19
+ {
20
+ "validFrom": "2026-07-01",
21
+ "rate": 0.065
22
+ }
23
+ ],
24
+ "AZ": [
25
+ {
26
+ "validFrom": "2026-07-01",
27
+ "rate": 0.056
28
+ }
29
+ ],
30
+ "CA": [
31
+ {
32
+ "validFrom": "2026-07-01",
33
+ "rate": 0.0725,
34
+ "note": "6.0% state + 1.25% mandatory statewide local"
35
+ }
36
+ ],
37
+ "CO": [
38
+ {
39
+ "validFrom": "2026-07-01",
40
+ "rate": 0.029
41
+ }
42
+ ],
43
+ "CT": [
44
+ {
45
+ "validFrom": "2026-07-01",
46
+ "rate": 0.0635
47
+ }
48
+ ],
49
+ "DC": [
50
+ {
51
+ "validFrom": "2026-07-01",
52
+ "rate": 0.06
53
+ },
54
+ {
55
+ "validFrom": "2026-10-01",
56
+ "rate": 0.07,
57
+ "note": "enacted increase per DC OTR notice"
58
+ }
59
+ ],
60
+ "DE": [
61
+ {
62
+ "validFrom": "2026-07-01",
63
+ "rate": 0.0
64
+ }
65
+ ],
66
+ "FL": [
67
+ {
68
+ "validFrom": "2026-07-01",
69
+ "rate": 0.06
70
+ }
71
+ ],
72
+ "GA": [
73
+ {
74
+ "validFrom": "2026-07-01",
75
+ "rate": 0.04
76
+ }
77
+ ],
78
+ "HI": [
79
+ {
80
+ "validFrom": "2026-07-01",
81
+ "rate": 0.04,
82
+ "note": "general excise tax (GET)"
83
+ }
84
+ ],
85
+ "IA": [
86
+ {
87
+ "validFrom": "2026-07-01",
88
+ "rate": 0.06
89
+ }
90
+ ],
91
+ "ID": [
92
+ {
93
+ "validFrom": "2026-07-01",
94
+ "rate": 0.06
95
+ }
96
+ ],
97
+ "IL": [
98
+ {
99
+ "validFrom": "2026-07-01",
100
+ "rate": 0.0625
101
+ }
102
+ ],
103
+ "IN": [
104
+ {
105
+ "validFrom": "2026-07-01",
106
+ "rate": 0.07
107
+ }
108
+ ],
109
+ "KS": [
110
+ {
111
+ "validFrom": "2026-07-01",
112
+ "rate": 0.065
113
+ }
114
+ ],
115
+ "KY": [
116
+ {
117
+ "validFrom": "2026-07-01",
118
+ "rate": 0.06
119
+ }
120
+ ],
121
+ "LA": [
122
+ {
123
+ "validFrom": "2018-07-01",
124
+ "rate": 0.0445
125
+ },
126
+ {
127
+ "validFrom": "2025-01-01",
128
+ "rate": 0.05,
129
+ "note": "Act 11 (2024); scheduled to drop to 4.75% from 2030"
130
+ }
131
+ ],
132
+ "MA": [
133
+ {
134
+ "validFrom": "2026-07-01",
135
+ "rate": 0.0625
136
+ }
137
+ ],
138
+ "MD": [
139
+ {
140
+ "validFrom": "2026-07-01",
141
+ "rate": 0.06
142
+ }
143
+ ],
144
+ "ME": [
145
+ {
146
+ "validFrom": "2026-07-01",
147
+ "rate": 0.055
148
+ }
149
+ ],
150
+ "MI": [
151
+ {
152
+ "validFrom": "2026-07-01",
153
+ "rate": 0.06
154
+ }
155
+ ],
156
+ "MN": [
157
+ {
158
+ "validFrom": "2026-07-01",
159
+ "rate": 0.06875
160
+ }
161
+ ],
162
+ "MO": [
163
+ {
164
+ "validFrom": "2026-07-01",
165
+ "rate": 0.04225
166
+ }
167
+ ],
168
+ "MS": [
169
+ {
170
+ "validFrom": "2026-07-01",
171
+ "rate": 0.07
172
+ }
173
+ ],
174
+ "MT": [
175
+ {
176
+ "validFrom": "2026-07-01",
177
+ "rate": 0.0
178
+ }
179
+ ],
180
+ "NC": [
181
+ {
182
+ "validFrom": "2026-07-01",
183
+ "rate": 0.0475
184
+ }
185
+ ],
186
+ "ND": [
187
+ {
188
+ "validFrom": "2026-07-01",
189
+ "rate": 0.05
190
+ }
191
+ ],
192
+ "NE": [
193
+ {
194
+ "validFrom": "2026-07-01",
195
+ "rate": 0.055
196
+ }
197
+ ],
198
+ "NH": [
199
+ {
200
+ "validFrom": "2026-07-01",
201
+ "rate": 0.0
202
+ }
203
+ ],
204
+ "NJ": [
205
+ {
206
+ "validFrom": "2026-07-01",
207
+ "rate": 0.06625
208
+ }
209
+ ],
210
+ "NM": [
211
+ {
212
+ "validFrom": "2022-07-01",
213
+ "rate": 0.05
214
+ },
215
+ {
216
+ "validFrom": "2023-07-01",
217
+ "rate": 0.04875,
218
+ "note": "gross receipts tax (HB 163, 2022)"
219
+ }
220
+ ],
221
+ "NV": [
222
+ {
223
+ "validFrom": "2026-07-01",
224
+ "rate": 0.0685,
225
+ "note": "includes mandatory statewide-levied components"
226
+ }
227
+ ],
228
+ "NY": [
229
+ {
230
+ "validFrom": "2026-07-01",
231
+ "rate": 0.04
232
+ }
233
+ ],
234
+ "OH": [
235
+ {
236
+ "validFrom": "2026-07-01",
237
+ "rate": 0.0575
238
+ }
239
+ ],
240
+ "OK": [
241
+ {
242
+ "validFrom": "2026-07-01",
243
+ "rate": 0.045
244
+ }
245
+ ],
246
+ "OR": [
247
+ {
248
+ "validFrom": "2026-07-01",
249
+ "rate": 0.0
250
+ }
251
+ ],
252
+ "PA": [
253
+ {
254
+ "validFrom": "2026-07-01",
255
+ "rate": 0.06
256
+ }
257
+ ],
258
+ "RI": [
259
+ {
260
+ "validFrom": "2026-07-01",
261
+ "rate": 0.07
262
+ }
263
+ ],
264
+ "SC": [
265
+ {
266
+ "validFrom": "2026-07-01",
267
+ "rate": 0.06
268
+ }
269
+ ],
270
+ "SD": [
271
+ {
272
+ "validFrom": "2023-07-01",
273
+ "rate": 0.042,
274
+ "note": "HB 1137 temporary cut; reverts to 4.5% on 2027-07-01 unless extended"
275
+ }
276
+ ],
277
+ "TN": [
278
+ {
279
+ "validFrom": "2026-07-01",
280
+ "rate": 0.07
281
+ }
282
+ ],
283
+ "TX": [
284
+ {
285
+ "validFrom": "2026-07-01",
286
+ "rate": 0.0625
287
+ }
288
+ ],
289
+ "UT": [
290
+ {
291
+ "validFrom": "2026-07-01",
292
+ "rate": 0.061,
293
+ "note": "includes 1.25% mandatory statewide local add-on"
294
+ }
295
+ ],
296
+ "VA": [
297
+ {
298
+ "validFrom": "2026-07-01",
299
+ "rate": 0.053,
300
+ "note": "4.3% state + 1% mandatory statewide local"
301
+ }
302
+ ],
303
+ "VT": [
304
+ {
305
+ "validFrom": "2026-07-01",
306
+ "rate": 0.06
307
+ }
308
+ ],
309
+ "WA": [
310
+ {
311
+ "validFrom": "2026-07-01",
312
+ "rate": 0.065
313
+ }
314
+ ],
315
+ "WI": [
316
+ {
317
+ "validFrom": "2026-07-01",
318
+ "rate": 0.05
319
+ }
320
+ ],
321
+ "WV": [
322
+ {
323
+ "validFrom": "2026-07-01",
324
+ "rate": 0.06
325
+ }
326
+ ],
327
+ "WY": [
328
+ {
329
+ "validFrom": "2026-07-01",
330
+ "rate": 0.04
331
+ }
332
+ ]
333
+ }
334
+ }
@@ -0,0 +1,11 @@
1
+ import type { DeliveryProvider } from '@unchainedshop/core-delivery';
2
+ import type { Product } from '@unchainedshop/core-products';
3
+ export declare const US_COUNTRY_CODE = "US";
4
+ export declare const US_SALES_TAX_EXEMPT_VALUE = "exempt";
5
+ export declare const US_STATE_CODES: string[];
6
+ export declare const resolveUsSalesTaxRate: ({ regionCode, referenceDate, }: {
7
+ regionCode?: string | null;
8
+ referenceDate?: Date;
9
+ }) => number | null;
10
+ export declare const isProductExemptFromUsSalesTax: (product: Product) => boolean;
11
+ export declare const isDeliveryExemptFromUsSalesTax: (provider: DeliveryProvider) => boolean;
@@ -0,0 +1,20 @@
1
+ import usTaxRates from './us-tax-rates.json' with { type: 'json' };
2
+ import { compileEraRates, rateForDate } from "./eraRates.js";
3
+ export const US_COUNTRY_CODE = 'US';
4
+ export const US_SALES_TAX_EXEMPT_VALUE = 'exempt';
5
+ const stateRates = Object.fromEntries(Object.entries(usTaxRates.states).map(([stateCode, eras]) => [
6
+ stateCode,
7
+ rateForDate(compileEraRates(eras, usTaxRates.timezone)),
8
+ ]));
9
+ export const US_STATE_CODES = Object.keys(stateRates);
10
+ export const resolveUsSalesTaxRate = ({ regionCode, referenceDate, }) => {
11
+ const resolveRate = regionCode ? stateRates[regionCode.toUpperCase().trim()] : null;
12
+ if (!resolveRate)
13
+ return null;
14
+ return resolveRate(referenceDate);
15
+ };
16
+ export const isProductExemptFromUsSalesTax = (product) => Boolean(product?.tags?.some((tag) => tag?.trim().toLowerCase() === `us-tax-category:${US_SALES_TAX_EXEMPT_VALUE}`));
17
+ export const isDeliveryExemptFromUsSalesTax = (provider) => provider?.configuration
18
+ ?.find(({ key }) => key === 'us-tax-category')
19
+ ?.value?.trim()
20
+ .toLowerCase() === US_SALES_TAX_EXEMPT_VALUE;
@@ -1,5 +1,5 @@
1
1
  import type { Order, OrderDelivery } from '@unchainedshop/core-orders';
2
- export default function isDeliveryAddressInCountry({ orderDelivery, order, countryCode: forceCountryCode, }: {
2
+ export default function isDeliveryAddressInCountry(params: {
3
3
  orderDelivery?: OrderDelivery | null;
4
4
  order?: Order | null;
5
5
  countryCode?: string | null;
@@ -1,11 +1,6 @@
1
- export default function isDeliveryAddressInCountry({ orderDelivery, order, countryCode: forceCountryCode = null, }, allowedCountryCodes) {
2
- let countryCode = forceCountryCode?.toUpperCase().trim() || order?.countryCode;
3
- if (orderDelivery || order) {
4
- const address = orderDelivery?.context?.address || order?.billingAddress;
5
- if (address?.countryCode > '') {
6
- countryCode = address.countryCode?.toUpperCase().trim();
7
- }
8
- }
1
+ import resolveDeliveryLocation from "./resolveDeliveryLocation.js";
2
+ export default function isDeliveryAddressInCountry(params, allowedCountryCodes) {
3
+ const { countryCode } = resolveDeliveryLocation(params);
9
4
  if (!countryCode)
10
5
  return false;
11
6
  return allowedCountryCodes.includes(countryCode);
@@ -0,0 +1,10 @@
1
+ import type { Order, OrderDelivery } from '@unchainedshop/core-orders';
2
+ export interface DeliveryLocation {
3
+ countryCode: string | null;
4
+ regionCode: string | null;
5
+ }
6
+ export default function resolveDeliveryLocation({ orderDelivery, order, countryCode: forceCountryCode, }: {
7
+ orderDelivery?: OrderDelivery | null;
8
+ order?: Order | null;
9
+ countryCode?: string | null;
10
+ }): DeliveryLocation;
@@ -0,0 +1,9 @@
1
+ export default function resolveDeliveryLocation({ orderDelivery, order, countryCode: forceCountryCode = null, }) {
2
+ const address = orderDelivery?.context?.address || order?.billingAddress;
3
+ let countryCode = forceCountryCode?.toUpperCase().trim() || order?.countryCode || null;
4
+ if (address?.countryCode && address.countryCode > '') {
5
+ countryCode = address.countryCode.toUpperCase().trim();
6
+ }
7
+ const regionCode = address?.regionCode?.toUpperCase().trim() || null;
8
+ return { countryCode, regionCode };
9
+ }
@@ -10,8 +10,13 @@ export const ManualOffering = {
10
10
  return {
11
11
  ...QuotationAdapter.actions(params),
12
12
  quote: async () => {
13
+ const { quotation } = params;
14
+ const price = Number(quotation?.context?.price);
13
15
  return {
14
- expires: new Date(new Date().getTime() + 3600 * 1000),
16
+ expires: quotation?.context?.expires
17
+ ? new Date(quotation.context.expires)
18
+ : new Date(new Date().getTime() + 3600 * 1000),
19
+ price: Number.isFinite(price) && price > 0 ? Math.round(price) : undefined,
15
20
  };
16
21
  },
17
22
  };
@@ -0,0 +1,9 @@
1
+ import { type IWorkerAdapter } from '@unchainedshop/core';
2
+ export declare const GCGuestsWorker: IWorkerAdapter<{
3
+ guestUserMaxAgeInDays?: number;
4
+ }, {
5
+ scannedGuestCount: number;
6
+ deletedGuestCount: number;
7
+ }>;
8
+ export default GCGuestsWorker;
9
+ export declare const configureGCGuestsAutoscheduling: () => void;
@@ -0,0 +1,56 @@
1
+ import { WorkerAdapter, WorkerDirector, schedule } from '@unchainedshop/core';
2
+ import { userSettings } from '@unchainedshop/core-users';
3
+ import { createLogger } from '@unchainedshop/logger';
4
+ const logger = createLogger('unchained:worker:gc-guests');
5
+ const ONE_DAY_IN_MILLISECONDS = 86400000;
6
+ const everyDayAtHalfPastTwo = schedule.parse.cron('30 2 * * *');
7
+ export const GCGuestsWorker = {
8
+ ...WorkerAdapter,
9
+ key: 'shop.unchained.worker-plugin.gc-guests',
10
+ label: 'Garbage Collect Guests',
11
+ version: '1.0.0',
12
+ type: 'GC_GUESTS',
13
+ doWork: async ({ guestUserMaxAgeInDays } = {}, unchainedAPI) => {
14
+ const { modules, services } = unchainedAPI;
15
+ try {
16
+ const maxAgeInDays = guestUserMaxAgeInDays ?? userSettings.guestUserMaxAgeInDays;
17
+ const before = new Date(Date.now() - maxAgeInDays * ONE_DAY_IN_MILLISECONDS);
18
+ const userIdsToDelete = await modules.users.findGuestUserIds({ before });
19
+ let deletedGuestCount = 0;
20
+ await Array.fromAsync(userIdsToDelete, async (userId) => {
21
+ try {
22
+ await services.users.deleteUser({ userId });
23
+ deletedGuestCount += 1;
24
+ }
25
+ catch (err) {
26
+ logger.warn(`Failed to garbage-collect guest ${userId}: ${err.message}`);
27
+ }
28
+ });
29
+ return {
30
+ success: true,
31
+ result: {
32
+ scannedGuestCount: userIdsToDelete.length,
33
+ deletedGuestCount,
34
+ },
35
+ };
36
+ }
37
+ catch (err) {
38
+ return {
39
+ success: false,
40
+ error: {
41
+ name: err.name,
42
+ message: err.message,
43
+ stack: err.stack,
44
+ },
45
+ };
46
+ }
47
+ },
48
+ };
49
+ export default GCGuestsWorker;
50
+ export const configureGCGuestsAutoscheduling = () => {
51
+ WorkerDirector.configureAutoscheduling({
52
+ type: GCGuestsWorker.type,
53
+ schedule: everyDayAtHalfPastTwo,
54
+ retries: 0,
55
+ });
56
+ };
@@ -0,0 +1,4 @@
1
+ import { type IPlugin } from '@unchainedshop/core';
2
+ export declare const GCGuestsPlugin: IPlugin;
3
+ export default GCGuestsPlugin;
4
+ export * from './adapter.ts';
@@ -0,0 +1,13 @@
1
+ import {} from '@unchainedshop/core';
2
+ import { GCGuestsWorker, configureGCGuestsAutoscheduling } from "./adapter.js";
3
+ export const GCGuestsPlugin = {
4
+ key: 'shop.unchained.worker-plugin.gc-guests',
5
+ label: 'Garbage Collect Guests Worker Plugin',
6
+ version: '1.0.0',
7
+ adapters: [GCGuestsWorker],
8
+ onRegister: () => {
9
+ configureGCGuestsAutoscheduling();
10
+ },
11
+ };
12
+ export default GCGuestsPlugin;
13
+ export * from "./adapter.js";
@@ -0,0 +1,9 @@
1
+ import { type IWorkerAdapter } from '@unchainedshop/core';
2
+ export declare const InvalidateCartsWorker: IWorkerAdapter<{
3
+ maxAgeDays?: number;
4
+ }, {
5
+ scannedCartCount: number;
6
+ recalculatedCartCount: number;
7
+ }>;
8
+ export default InvalidateCartsWorker;
9
+ export declare const configureInvalidateCartsAutoscheduling: () => void;