@scayle/storefront-product-detail 1.9.0 → 1.9.1
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 +66 -62
- package/dist/module.json +1 -1
- package/dist/module.mjs +1 -1
- package/dist/runtime/composables/useAllShopProductsForId.js +1 -6
- package/dist/runtime/composables/useRecentlyViewedProducts.js +1 -3
- package/dist/runtime/rpc/methods/products.js +35 -32
- package/dist/runtime/rpc/methods/recommendations.js +28 -28
- package/package.json +15 -15
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
# @scayle/storefront-product-detail
|
|
2
2
|
|
|
3
|
+
## 1.9.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- **\[Security\]** Use the patched Nuxt for build — `nuxt@3.21.8` (3.x) / `nuxt@4.4.8` (4.x), with matching `@nuxt/kit` and `@nuxt/schema` — which includes the fix for [CVE-2026-53721](https://nvd.nist.gov/vuln/detail/CVE-2026-53721) ([GHSA-mm7m-92g8-7m47](https://github.com/nuxt/nuxt/security/advisories/GHSA-mm7m-92g8-7m47)), a route-rule middleware bypass.
|
|
8
|
+
|
|
9
|
+
Compatibility with previously-supported Nuxt versions is unchanged and remains specified via each package's `peerDependencies` and the Nuxt compatibility flag. `@scayle/storefront-core` is released in lockstep with `@scayle/storefront-nuxt`.
|
|
10
|
+
|
|
3
11
|
## 1.9.0
|
|
4
12
|
|
|
5
13
|
### Minor Changes
|
|
@@ -19,19 +27,19 @@
|
|
|
19
27
|
params: {
|
|
20
28
|
productId: 123,
|
|
21
29
|
limit: 10,
|
|
22
|
-
with: { attributes:
|
|
30
|
+
with: { attributes: 'all', images: { attributes: 'all' } },
|
|
23
31
|
where: {
|
|
24
32
|
attributes: [
|
|
25
33
|
{
|
|
26
|
-
type:
|
|
27
|
-
key:
|
|
34
|
+
type: 'attributes',
|
|
35
|
+
key: 'brand',
|
|
28
36
|
values: [456],
|
|
29
37
|
},
|
|
30
38
|
],
|
|
31
39
|
},
|
|
32
40
|
ignoreSameMasterKey: true,
|
|
33
41
|
},
|
|
34
|
-
})
|
|
42
|
+
})
|
|
35
43
|
```
|
|
36
44
|
|
|
37
45
|
## 1.7.0
|
|
@@ -40,7 +48,6 @@
|
|
|
40
48
|
|
|
41
49
|
- Introduced support for Nuxt 4 while maintaining full backward compatibility with Nuxt 3.
|
|
42
50
|
This enables consumers to migrate to Nuxt 4 ahead of the Nuxt 3 end of support on 31 Jan 2026.
|
|
43
|
-
|
|
44
51
|
- **Version Requirements:**
|
|
45
52
|
- Nuxt 3: `v3.13.0+`
|
|
46
53
|
- Nuxt 4: `v4.2.0+`
|
|
@@ -78,64 +85,64 @@
|
|
|
78
85
|
**`sellableTimeframeStartsInFuture`:**
|
|
79
86
|
|
|
80
87
|
```ts
|
|
81
|
-
import { sellableTimeframeStartsInFuture } from
|
|
88
|
+
import { sellableTimeframeStartsInFuture } from '@scayle/storefront-product-detail'
|
|
82
89
|
|
|
83
90
|
// Example timeframe
|
|
84
91
|
const timeframe = {
|
|
85
|
-
sellableFrom:
|
|
86
|
-
sellableTo:
|
|
87
|
-
}
|
|
92
|
+
sellableFrom: '2099-01-01T00:00:00Z',
|
|
93
|
+
sellableTo: '2100-01-01T00:00:00Z',
|
|
94
|
+
}
|
|
88
95
|
|
|
89
|
-
const inFuture = sellableTimeframeStartsInFuture(timeframe)
|
|
90
|
-
console.log(inFuture)
|
|
96
|
+
const inFuture = sellableTimeframeStartsInFuture(timeframe)
|
|
97
|
+
console.log(inFuture) // true if current date is before 2099-01-01
|
|
91
98
|
```
|
|
92
99
|
|
|
93
100
|
**`sellableTimeframeEndsInPast`:**
|
|
94
101
|
|
|
95
102
|
```ts
|
|
96
|
-
import { sellableTimeframeEndsInPast } from
|
|
103
|
+
import { sellableTimeframeEndsInPast } from '@scayle/storefront-product-detail'
|
|
97
104
|
|
|
98
105
|
const timeframe = {
|
|
99
|
-
sellableFrom:
|
|
100
|
-
sellableTo:
|
|
101
|
-
}
|
|
106
|
+
sellableFrom: '2018-01-01T00:00:00Z',
|
|
107
|
+
sellableTo: '2020-01-01T00:00:00Z',
|
|
108
|
+
}
|
|
102
109
|
|
|
103
|
-
const ended = sellableTimeframeEndsInPast(timeframe)
|
|
104
|
-
console.log(ended)
|
|
110
|
+
const ended = sellableTimeframeEndsInPast(timeframe)
|
|
111
|
+
console.log(ended) // true if current date is after 2020-01-01
|
|
105
112
|
```
|
|
106
113
|
|
|
107
114
|
**`isInSellableTimeframe`:**
|
|
108
115
|
|
|
109
116
|
```ts
|
|
110
|
-
import { isInSellableTimeframe } from
|
|
117
|
+
import { isInSellableTimeframe } from '@scayle/storefront-product-detail'
|
|
111
118
|
|
|
112
119
|
const timeframe = {
|
|
113
|
-
sellableFrom:
|
|
114
|
-
sellableTo:
|
|
115
|
-
}
|
|
120
|
+
sellableFrom: '2023-01-01T00:00:00Z',
|
|
121
|
+
sellableTo: '2025-01-01T00:00:00Z',
|
|
122
|
+
}
|
|
116
123
|
|
|
117
|
-
const active = isInSellableTimeframe(timeframe)
|
|
118
|
-
console.log(active)
|
|
124
|
+
const active = isInSellableTimeframe(timeframe)
|
|
125
|
+
console.log(active) // true if current date is between 2023-01-01 and 2025-01-01
|
|
119
126
|
```
|
|
120
127
|
|
|
121
128
|
**`useSellableTimeFrame`:**
|
|
122
129
|
|
|
123
130
|
```ts
|
|
124
|
-
import { useSellableTimeFrame } from
|
|
131
|
+
import { useSellableTimeFrame } from '@scayle/storefront-product-detail'
|
|
125
132
|
|
|
126
133
|
const timeframe = {
|
|
127
|
-
sellableFrom:
|
|
128
|
-
sellableTo:
|
|
129
|
-
}
|
|
134
|
+
sellableFrom: '2023-01-01T00:00:00Z',
|
|
135
|
+
sellableTo: '2025-01-01T00:00:00Z',
|
|
136
|
+
}
|
|
130
137
|
const {
|
|
131
138
|
isInSellableTimeframe,
|
|
132
139
|
sellableTimeframeStartsInFuture,
|
|
133
140
|
sellableTimeframeEndsInPast,
|
|
134
|
-
} = useSellableTimeFrame(timeframe)
|
|
141
|
+
} = useSellableTimeFrame(timeframe)
|
|
135
142
|
|
|
136
|
-
console.log(isInSellableTimeframe)
|
|
137
|
-
console.log(sellableTimeframeStartsInFuture)
|
|
138
|
-
console.log(sellableTimeframeEndsInPast)
|
|
143
|
+
console.log(isInSellableTimeframe) // true if the timeframe is active
|
|
144
|
+
console.log(sellableTimeframeStartsInFuture) // true if the time frame starts in the future
|
|
145
|
+
console.log(sellableTimeframeEndsInPast) // true if the timeframe ended in the past
|
|
139
146
|
```
|
|
140
147
|
|
|
141
148
|
## 1.5.6
|
|
@@ -145,26 +152,25 @@
|
|
|
145
152
|
- Enhanced data fetching composables to support reactive keys, aligning with [Nuxt 3.17 data fetching improvements](https://nuxt.com/blog/v3-17#data-fetching-improvements).
|
|
146
153
|
|
|
147
154
|
You can now pass a `ref`, `computed`, or getter function as the `key` parameter to `useRpc` and derived composables (like `useProducts`, `useBrand` etc.). When the reactive key changes, the data will automatically re-fetch.
|
|
148
|
-
|
|
149
155
|
- **Before:** Keys were static strings.
|
|
150
156
|
- **After:** Keys can be reactive, enabling dynamic caching and automatic updates.
|
|
151
157
|
|
|
152
158
|
```ts
|
|
153
159
|
// Before
|
|
154
|
-
const { data } = await useRpc(
|
|
160
|
+
const { data } = await useRpc('getProduct', 'my-static-product-key', {
|
|
155
161
|
productId: 123,
|
|
156
|
-
})
|
|
162
|
+
})
|
|
157
163
|
|
|
158
164
|
// After
|
|
159
|
-
const productId = ref(123)
|
|
165
|
+
const productId = ref(123)
|
|
160
166
|
|
|
161
167
|
// The key is now reactive. If `productId` changes, the key updates
|
|
162
168
|
// to 'product-456' (for example) and triggers a new fetch.
|
|
163
169
|
const { data } = await useRpc(
|
|
164
|
-
|
|
170
|
+
'getProduct',
|
|
165
171
|
() => `product-${productId.value}`,
|
|
166
|
-
{ productId }
|
|
167
|
-
)
|
|
172
|
+
{ productId },
|
|
173
|
+
)
|
|
168
174
|
```
|
|
169
175
|
|
|
170
176
|
## 1.5.5
|
|
@@ -201,15 +207,15 @@
|
|
|
201
207
|
|
|
202
208
|
```ts
|
|
203
209
|
export default defineNuxtConfig({
|
|
204
|
-
modules: [
|
|
210
|
+
modules: ['@scayle/storefront-product-detail'],
|
|
205
211
|
runtimeConfig: {
|
|
206
212
|
public: {
|
|
207
|
-
|
|
213
|
+
'product-detail': {
|
|
208
214
|
maxRecentlyViewedProducts: 15,
|
|
209
215
|
},
|
|
210
216
|
},
|
|
211
217
|
},
|
|
212
|
-
})
|
|
218
|
+
})
|
|
213
219
|
```
|
|
214
220
|
|
|
215
221
|
## 1.5.0
|
|
@@ -221,15 +227,15 @@
|
|
|
221
227
|
Example usage:
|
|
222
228
|
|
|
223
229
|
```ts
|
|
224
|
-
import { useRecentlyViewedProducts } from
|
|
230
|
+
import { useRecentlyViewedProducts } from '#storefront-product-detail/composables'
|
|
225
231
|
|
|
226
232
|
const { products, addProduct, loadMissingProducts } =
|
|
227
|
-
useRecentlyViewedProducts()
|
|
233
|
+
useRecentlyViewedProducts()
|
|
228
234
|
|
|
229
235
|
onBeforeMount(async () => {
|
|
230
|
-
addProductId(1234)
|
|
231
|
-
await loadMissingProducts()
|
|
232
|
-
})
|
|
236
|
+
addProductId(1234)
|
|
237
|
+
await loadMissingProducts()
|
|
238
|
+
})
|
|
233
239
|
```
|
|
234
240
|
|
|
235
241
|
## 1.4.2
|
|
@@ -261,44 +267,44 @@
|
|
|
261
267
|
|
|
262
268
|
```ts
|
|
263
269
|
useProductSeoData({
|
|
264
|
-
name:
|
|
265
|
-
brand:
|
|
266
|
-
productDescription:
|
|
270
|
+
name: 'Name',
|
|
271
|
+
brand: 'Brand',
|
|
272
|
+
productDescription: 'Description',
|
|
267
273
|
variants: variants.value.map((variant) => {
|
|
268
274
|
return generateProductSchema({
|
|
269
|
-
productName:
|
|
275
|
+
productName: 'Name',
|
|
270
276
|
variant,
|
|
271
277
|
url: `${$config.public.baseUrl}${route.fullPath}`,
|
|
272
278
|
size,
|
|
273
|
-
})
|
|
279
|
+
})
|
|
274
280
|
}),
|
|
275
281
|
images: images.value,
|
|
276
282
|
productId: product.value?.id || 0,
|
|
277
283
|
color: formatColors(colors.value),
|
|
278
284
|
variesBy:
|
|
279
|
-
variants.value.length > 1 ? [
|
|
280
|
-
})
|
|
285
|
+
variants.value.length > 1 ? ['https://schema.org/size'] : undefined,
|
|
286
|
+
})
|
|
281
287
|
|
|
282
288
|
// Will become
|
|
283
289
|
|
|
284
290
|
useProductSeoData({
|
|
285
|
-
name:
|
|
286
|
-
brand:
|
|
287
|
-
productDescription:
|
|
291
|
+
name: 'Name',
|
|
292
|
+
brand: 'Brand',
|
|
293
|
+
productDescription: 'Description',
|
|
288
294
|
variants: variants.value.map((variant) => {
|
|
289
295
|
return generateProductSchema({
|
|
290
|
-
productName:
|
|
296
|
+
productName: 'Name',
|
|
291
297
|
variant,
|
|
292
298
|
url: `${$config.public.baseUrl}${route.fullPath}`,
|
|
293
299
|
size,
|
|
294
300
|
images: images.value[0],
|
|
295
|
-
})
|
|
301
|
+
})
|
|
296
302
|
}),
|
|
297
303
|
productId: product.value?.id || 0,
|
|
298
304
|
color: formatColors(colors.value),
|
|
299
305
|
variesBy:
|
|
300
|
-
variants.value.length > 1 ? [
|
|
301
|
-
})
|
|
306
|
+
variants.value.length > 1 ? ['https://schema.org/size'] : undefined,
|
|
307
|
+
})
|
|
302
308
|
```
|
|
303
309
|
|
|
304
310
|
## 1.2.0
|
|
@@ -355,7 +361,6 @@
|
|
|
355
361
|
|
|
356
362
|
- This release introduces the `@scayle/storefront-product-detail` package, decoupling composables and utilities of the Product Detail Page (PDP) functionality from the SCAYLE Storefront Boilerplate for enhanced modularity and integration.
|
|
357
363
|
This separation empowers developers with greater control over PDP updates and simplifies its integration into existing Storefront-based projects.
|
|
358
|
-
|
|
359
364
|
- [Discover more about the Product Detail Page for SCAYLE Storefront in our SCAYLE Resource Center.](https://scayle.dev/en/core-documentation/storefront-guide/storefront-application/features/product-detail-page)
|
|
360
365
|
|
|
361
366
|
- This release requires `@scayle/storefront-nuxt@8.x` or higher. Support for `@scayle/storefront-nuxt@7.x` has been discontinued. Please update your dependencies accordingly. The `peerDependency` range has been updated to `^8.0.0`.
|
|
@@ -363,7 +368,6 @@
|
|
|
363
368
|
### Minor Changes
|
|
364
369
|
|
|
365
370
|
- Compared to the original implementation within the SCAYLE Storefront Boilerplate, the `@scayle/storefront-product-detail` package has received some improvements and refactoring:
|
|
366
|
-
|
|
367
371
|
- Introduced the `getCombineWithProductIds` function within the product utility, enabling efficient retrieval of product combinations within product listings.
|
|
368
372
|
- Added the `getFilteredAttributeGroups` function to the attribute utility, simplifying the retrieval and formatting of filtered product attributes for display in listings.
|
|
369
373
|
- Introduced the `useProductSeoData` composable, automating the generation of SEO-critical metadata for product pages. This includes dynamically generated canonical links, robots meta tags, product titles, and structured data (`JSON-LD`) for product details and breadcrumbs, enhancing search engine visibility.
|
package/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { defineNuxtModule, createResolver, addImportsDir } from '@nuxt/kit';
|
|
2
2
|
|
|
3
3
|
const PACKAGE_NAME = "@scayle/storefront-product-detail";
|
|
4
|
-
const PACKAGE_VERSION = "1.9.
|
|
4
|
+
const PACKAGE_VERSION = "1.9.1";
|
|
5
5
|
const module$1 = defineNuxtModule({
|
|
6
6
|
meta: {
|
|
7
7
|
name: PACKAGE_NAME,
|
|
@@ -65,9 +65,7 @@ export function useRecentlyViewedProducts(options) {
|
|
|
65
65
|
products.value.push(...result);
|
|
66
66
|
}
|
|
67
67
|
const sortOrderMap = new Map(
|
|
68
|
-
recentlyViewedProductsIds.value.map(
|
|
69
|
-
(id, index) => [id, index]
|
|
70
|
-
)
|
|
68
|
+
recentlyViewedProductsIds.value.map((id, index) => [id, index])
|
|
71
69
|
);
|
|
72
70
|
products.value = products.value.sort((a, b) => {
|
|
73
71
|
const aIndex = sortOrderMap.get(a.id);
|
|
@@ -1,33 +1,36 @@
|
|
|
1
1
|
import { defineRpcHandler } from "@scayle/storefront-nuxt";
|
|
2
|
-
export const getAllShopProductsForId = defineRpcHandler(
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
2
|
+
export const getAllShopProductsForId = defineRpcHandler(
|
|
3
|
+
async (options, context) => {
|
|
4
|
+
const { runtimeConfiguration, sapiClient, log, cached } = context;
|
|
5
|
+
const fetchAllProducts = async () => {
|
|
6
|
+
const products = [];
|
|
7
|
+
const shops = Object.values(
|
|
8
|
+
runtimeConfiguration.storefront.shops
|
|
9
|
+
);
|
|
10
|
+
await Promise.all(
|
|
11
|
+
shops.map(async (shop) => {
|
|
12
|
+
try {
|
|
13
|
+
const product = await sapiClient.clone({ shopId: shop.shopId }).products.getById(options.id, {
|
|
14
|
+
with: options.with
|
|
15
|
+
});
|
|
16
|
+
products.push({
|
|
17
|
+
locale: shop.locale,
|
|
18
|
+
path: Array.isArray(shop.path) ? shop.path[0] : shop.path,
|
|
19
|
+
product
|
|
20
|
+
});
|
|
21
|
+
} catch (error) {
|
|
22
|
+
log.error(error instanceof Error ? error : String(error));
|
|
23
|
+
}
|
|
24
|
+
})
|
|
25
|
+
);
|
|
26
|
+
return products;
|
|
27
|
+
};
|
|
28
|
+
const result = await cached(fetchAllProducts, {
|
|
29
|
+
cacheKeyPrefix: `getAllShopProductsForId-${options.id}`,
|
|
30
|
+
ttl: 12 * 60 * 60
|
|
31
|
+
// 12 hours
|
|
32
|
+
})();
|
|
33
|
+
return result;
|
|
34
|
+
},
|
|
35
|
+
{ method: "GET" }
|
|
36
|
+
);
|
|
@@ -5,34 +5,34 @@ import {
|
|
|
5
5
|
MIN_WITH_PARAMS_PRODUCT,
|
|
6
6
|
defineRpcHandler
|
|
7
7
|
} from "@scayle/storefront-nuxt";
|
|
8
|
-
export const getSimilarProducts = defineRpcHandler(
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
8
|
+
export const getSimilarProducts = defineRpcHandler(
|
|
9
|
+
async (options, context) => {
|
|
10
|
+
const { sapiClient, cached, withParams } = context;
|
|
11
|
+
const campaignKey = await context.callRpc?.("getCampaignKey");
|
|
12
|
+
const { productId, with: withParameter, ...rest } = options;
|
|
13
|
+
const fetch = async (productId2, params) => {
|
|
14
|
+
try {
|
|
15
|
+
return sapiClient.recommendations.getSimilarProducts(productId2, params);
|
|
16
|
+
} catch (e) {
|
|
17
|
+
if (e instanceof FetchError) {
|
|
18
|
+
const response = e.response;
|
|
19
|
+
return new ErrorResponse(
|
|
20
|
+
response.status,
|
|
21
|
+
response.statusText,
|
|
22
|
+
"Failed to fetch similar products"
|
|
23
|
+
);
|
|
24
|
+
}
|
|
25
|
+
throw e;
|
|
23
26
|
}
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
};
|
|
27
|
-
return await cached(
|
|
28
|
-
fetch,
|
|
29
|
-
{
|
|
27
|
+
};
|
|
28
|
+
return await cached(fetch, {
|
|
30
29
|
cacheKeyPrefix: "getSimilarProducts-products",
|
|
31
30
|
ttl: 5 * MINUTE
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
}
|
|
38
|
-
|
|
31
|
+
})(productId, {
|
|
32
|
+
with: withParameter ?? withParams?.product ?? MIN_WITH_PARAMS_PRODUCT,
|
|
33
|
+
campaignKey,
|
|
34
|
+
...rest
|
|
35
|
+
});
|
|
36
|
+
},
|
|
37
|
+
{ method: "GET" }
|
|
38
|
+
);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@scayle/storefront-product-detail",
|
|
3
|
-
"version": "1.9.
|
|
3
|
+
"version": "1.9.1",
|
|
4
4
|
"description": "Collection of essential composables and utilities to work with product detail",
|
|
5
5
|
"author": "SCAYLE Commerce Engine",
|
|
6
6
|
"license": "MIT",
|
|
@@ -40,27 +40,27 @@
|
|
|
40
40
|
},
|
|
41
41
|
"devDependencies": {
|
|
42
42
|
"@arethetypeswrong/cli": "0.18.2",
|
|
43
|
-
"@nuxt/kit": "^3.
|
|
43
|
+
"@nuxt/kit": "^3.21.7",
|
|
44
44
|
"@nuxt/module-builder": "1.0.2",
|
|
45
|
-
"@nuxt/schema": "^3.
|
|
45
|
+
"@nuxt/schema": "^3.21.7",
|
|
46
46
|
"@nuxt/test-utils": "4.0.0",
|
|
47
47
|
"@scayle/eslint-config-storefront": "^4.8.0",
|
|
48
|
-
"@types/node": "
|
|
49
|
-
"@vitest/coverage-v8": "4.1.
|
|
50
|
-
"@vueuse/core": "14.
|
|
48
|
+
"@types/node": "24.12.2",
|
|
49
|
+
"@vitest/coverage-v8": "4.1.9",
|
|
50
|
+
"@vueuse/core": "14.3.0",
|
|
51
51
|
"eslint-formatter-gitlab": "7.1.0",
|
|
52
|
-
"eslint": "10.
|
|
53
|
-
"happy-dom": "20.
|
|
54
|
-
"nuxt": "^3.
|
|
55
|
-
"publint": "0.3.
|
|
52
|
+
"eslint": "10.5.0",
|
|
53
|
+
"happy-dom": "20.10.6",
|
|
54
|
+
"nuxt": "^3.21.7",
|
|
55
|
+
"publint": "0.3.21",
|
|
56
56
|
"schema-dts": "1.1.5",
|
|
57
|
-
"typescript": "
|
|
57
|
+
"typescript": "6.0.3",
|
|
58
58
|
"unbuild": "3.6.1",
|
|
59
|
-
"vitest": "4.1.
|
|
59
|
+
"vitest": "4.1.9",
|
|
60
60
|
"vue-router": "4.6.4",
|
|
61
|
-
"vue-tsc": "3.
|
|
62
|
-
"vue": "3.5.
|
|
63
|
-
"@scayle/storefront-nuxt": "8.
|
|
61
|
+
"vue-tsc": "3.3.5",
|
|
62
|
+
"vue": "3.5.38",
|
|
63
|
+
"@scayle/storefront-nuxt": "8.62.1",
|
|
64
64
|
"@scayle/vitest-config-storefront": "1.0.0"
|
|
65
65
|
},
|
|
66
66
|
"scripts": {
|