@faststore/core 2.1.0 → 2.1.3
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/.next/BUILD_ID +1 -1
- package/.next/build-manifest.json +43 -43
- package/.next/cache/.tsbuildinfo +1 -1
- package/.next/cache/config.json +7 -0
- package/.next/cache/eslint/.cache_1gneedd +1 -0
- package/.next/cache/next-server.js.nft.json +1 -1
- package/.next/cache/webpack/client-production/0.pack +0 -0
- package/.next/cache/webpack/client-production/index.pack +0 -0
- package/.next/cache/webpack/server-production/0.pack +0 -0
- package/.next/cache/webpack/server-production/index.pack +0 -0
- package/.next/next-server.js.nft.json +1 -1
- package/.next/prerender-manifest.json +1 -1
- package/.next/react-loadable-manifest.json +5 -5
- package/.next/required-server-files.json +1 -1
- package/.next/routes-manifest.json +1 -1
- package/.next/server/chunks/184.js +61 -0
- package/.next/server/chunks/205.js +1 -1
- package/.next/server/chunks/{280.js → 269.js} +233 -41
- package/.next/server/chunks/289.js +22 -9
- package/.next/server/chunks/350.js +1 -1
- package/.next/server/chunks/378.js +6 -6
- package/.next/server/chunks/74.js +54 -3
- package/.next/server/chunks/907.js +334 -180
- package/.next/server/middleware-build-manifest.js +1 -1
- package/.next/server/middleware-react-loadable-manifest.js +1 -1
- package/.next/server/pages/404.js +0 -7
- package/.next/server/pages/404.js.nft.json +1 -1
- package/.next/server/pages/500.js +0 -7
- package/.next/server/pages/500.js.nft.json +1 -1
- package/.next/server/pages/[...slug].js +1 -9
- package/.next/server/pages/[...slug].js.nft.json +1 -1
- package/.next/server/pages/[slug]/p.js +948 -907
- package/.next/server/pages/[slug]/p.js.nft.json +1 -1
- package/.next/server/pages/_app.js.nft.json +1 -1
- package/.next/server/pages/_document.js.nft.json +1 -1
- package/.next/server/pages/_error.js.nft.json +1 -1
- package/.next/server/pages/account.js +0 -7
- package/.next/server/pages/account.js.nft.json +1 -1
- package/.next/server/pages/api/graphql.js +1 -1
- package/.next/server/pages/checkout.js +0 -7
- package/.next/server/pages/checkout.js.nft.json +1 -1
- package/.next/server/pages/en-US/404.html +2 -2
- package/.next/server/pages/en-US/500.html +2 -2
- package/.next/server/pages/en-US/account.html +2 -2
- package/.next/server/pages/en-US/checkout.html +2 -2
- package/.next/server/pages/en-US/login.html +2 -2
- package/.next/server/pages/en-US/s.html +2 -2
- package/.next/server/pages/en-US.html +2 -2
- package/.next/server/pages/index.js +1 -9
- package/.next/server/pages/index.js.nft.json +1 -1
- package/.next/server/pages/login.js +0 -7
- package/.next/server/pages/login.js.nft.json +1 -1
- package/.next/server/pages/s.js +1 -8
- package/.next/server/pages/s.js.nft.json +1 -1
- package/.next/server/pages-manifest.json +4 -4
- package/.next/static/chunks/64.7ea3677ac3a10e00.js +1 -0
- package/.next/static/chunks/{682-dc059ce3e47eb9e1.js → 682-5cfea9ed52851ed1.js} +1 -1
- package/.next/static/chunks/738-a5ff304828f20cbf.js +1 -0
- package/.next/static/chunks/791-727eda8f766aa791.js +1 -0
- package/.next/static/chunks/pages/{404-e7a1846b72ad3430.js → 404-c3b320b915df45bb.js} +1 -1
- package/.next/static/chunks/pages/{500-0f4d738fa1caac78.js → 500-d37a3a2e931f6995.js} +1 -1
- package/.next/static/chunks/pages/[...slug]-d4e0a671c6248369.js +1 -0
- package/.next/static/chunks/pages/[slug]/p-2ad8b84fd5d98814.js +1 -0
- package/.next/static/chunks/pages/{account-bbe1795b8566f75a.js → account-86a1b6e7db03bab6.js} +1 -1
- package/.next/static/chunks/pages/{checkout-4321004c6cdaf5c7.js → checkout-c77dbc66c0b35ec3.js} +1 -1
- package/.next/static/chunks/pages/{index-949a5393471484d5.js → index-2912eeade1da43bf.js} +1 -1
- package/.next/static/chunks/pages/{login-b09e2dd0941c8882.js → login-bbf85bc59afce37c.js} +1 -1
- package/.next/static/chunks/pages/{s-e603b0c6e5eef0a7.js → s-dd486933e8ba7fbf.js} +1 -1
- package/.next/static/chunks/webpack-c5cf5350bcb7f6f4.js +1 -0
- package/.next/static/css/{8988ac07eb0af0ca.css → 0f8ce5203de8ae6f.css} +1 -1
- package/.next/static/hHM-WaPbC6D9MU3Qh2tZ1/_buildManifest.js +1 -0
- package/.next/trace +72 -72
- package/.turbo/turbo-build.log +14 -8
- package/.turbo/turbo-lint.log +2 -0
- package/package.json +8 -8
- package/src/components/product/ProductGrid/ProductGrid.tsx +22 -6
- package/src/components/search/Filter/Filter.tsx +12 -3
- package/src/components/sections/ProductDetails/Overrides.tsx +38 -2
- package/src/components/sections/ProductDetails/ProductDetails.tsx +45 -16
- package/src/components/sections/ProductDetails/section.module.scss +1 -0
- package/src/components/sections/ProductGallery/Overrides.tsx +52 -0
- package/src/components/ui/ImageGallery/ImageGallery.tsx +25 -14
- package/src/components/ui/ProductDetails/ProductDetailsSettings.tsx +32 -18
- package/src/components/ui/ProductGallery/ProductGallery.tsx +77 -37
- package/src/components/ui/ProductShelf/ProductShelf.tsx +1 -1
- package/src/components/ui/ShippingSimulation/ShippingSimulation.tsx +1 -2
- package/src/customizations/components/overrides/ProductDetails.tsx +15 -1
- package/src/customizations/components/overrides/ProductGallery.tsx +24 -0
- package/src/typings/overrides.d.ts +23 -0
- package/.next/cache/eslint/.cache_abdhua +0 -1
- package/.next/server/chunks/368.js +0 -253
- package/.next/static/chunks/21-5b0c50a44b0ed6ce.js +0 -1
- package/.next/static/chunks/460-08f41a79ff49f7be.js +0 -1
- package/.next/static/chunks/64.ebbe1d2b40f980c7.js +0 -1
- package/.next/static/chunks/pages/[...slug]-119a323292c7e3af.js +0 -1
- package/.next/static/chunks/pages/[slug]/p-3c424924080d88cb.js +0 -1
- package/.next/static/chunks/webpack-9ba6546d294eb768.js +0 -1
- package/.next/static/eLm2Cd_zypP0KQaj5UlQ2/_buildManifest.js +0 -1
- /package/.next/static/{eLm2Cd_zypP0KQaj5UlQ2 → hHM-WaPbC6D9MU3Qh2tZ1}/_ssgManifest.js +0 -0
package/.turbo/turbo-build.log
CHANGED
|
@@ -1,10 +1,16 @@
|
|
|
1
1
|
$ yarn partytown && next build
|
|
2
2
|
$ partytown copylib ./public/~partytown
|
|
3
|
-
Partytown lib copied to: /
|
|
3
|
+
Partytown lib copied to: /home/runner/work/faststore/faststore/packages/core/public/~partytown
|
|
4
|
+
warn - No build cache found. Please configure build caching for faster rebuilds. Read more: https://nextjs.org/docs/messages/no-cache
|
|
5
|
+
Attention: Next.js now collects completely anonymous telemetry regarding usage.
|
|
6
|
+
This information is used to shape Next.js' roadmap and prioritize features.
|
|
7
|
+
You can learn more, including how to opt-out if you'd not like to participate in this anonymous program, by visiting the following URL:
|
|
8
|
+
https://nextjs.org/telemetry
|
|
9
|
+
|
|
4
10
|
info - Linting and checking validity of types...
|
|
5
11
|
info - Creating an optimized production build...
|
|
6
12
|
info - Disabled SWC as replacement for Babel because of custom Babel configuration ".babelrc" https://nextjs.org/docs/messages/swc-disabled
|
|
7
|
-
info - Using external babel configuration from /
|
|
13
|
+
info - Using external babel configuration from /home/runner/work/faststore/faststore/packages/core/.babelrc
|
|
8
14
|
info - Compiled successfully
|
|
9
15
|
info - Collecting page data...
|
|
10
16
|
info - Generating static pages (0/7)
|
|
@@ -18,23 +24,23 @@ Route (pages) Size First Load JS
|
|
|
18
24
|
┌ ● / 3.47 kB 126 kB
|
|
19
25
|
├ └ css/c7fc1f563fa33060.css 7.18 kB
|
|
20
26
|
├ /_app 0 B 77.8 kB
|
|
21
|
-
├ ● /[...slug]
|
|
27
|
+
├ ● /[...slug] 8.79 kB 134 kB
|
|
22
28
|
├ └ css/6e41f1b6078c14c1.css 7.9 kB
|
|
23
|
-
├ ● /[slug]/p
|
|
24
|
-
├ └ css/
|
|
29
|
+
├ ● /[slug]/p 11.1 kB 134 kB
|
|
30
|
+
├ └ css/0f8ce5203de8ae6f.css 11.2 kB
|
|
25
31
|
├ ○ /404 1.09 kB 113 kB
|
|
26
32
|
├ ● /500 1.11 kB 113 kB
|
|
27
33
|
├ ● /account 668 B 113 kB
|
|
28
34
|
├ λ /api/graphql 0 B 77.8 kB
|
|
29
35
|
├ λ /api/preview 0 B 77.8 kB
|
|
30
|
-
├ ● /checkout
|
|
36
|
+
├ ● /checkout 657 B 113 kB
|
|
31
37
|
├ ● /login 1.01 kB 113 kB
|
|
32
|
-
└ ● /s 1.11 kB
|
|
38
|
+
└ ● /s 1.11 kB 126 kB
|
|
33
39
|
+ First Load JS shared by all 80.6 kB
|
|
34
40
|
├ chunks/framework-dfd14d7ce6600b03.js 45.3 kB
|
|
35
41
|
├ chunks/main-fd466221927468fd.js 23.9 kB
|
|
36
42
|
├ chunks/pages/_app-79d333aa6001a806.js 6.38 kB
|
|
37
|
-
├ chunks/webpack-
|
|
43
|
+
├ chunks/webpack-c5cf5350bcb7f6f4.js 2.21 kB
|
|
38
44
|
└ css/104f0f3ce3be32c6.css 2.79 kB
|
|
39
45
|
|
|
40
46
|
λ (Server) server-side renders at runtime (uses getInitialProps or getServerSideProps)
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@faststore/core",
|
|
3
|
-
"version": "2.1.
|
|
3
|
+
"version": "2.1.3",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"browserslist": "supports es6-module and not dead",
|
|
6
6
|
"scripts": {
|
|
@@ -29,11 +29,11 @@
|
|
|
29
29
|
"@envelop/graphql-jit": "^1.1.1",
|
|
30
30
|
"@envelop/parser-cache": "^2.2.0",
|
|
31
31
|
"@envelop/validation-cache": "^2.2.0",
|
|
32
|
-
"@faststore/api": "^2.1.
|
|
33
|
-
"@faststore/components": "^2.1.
|
|
34
|
-
"@faststore/graphql-utils": "^2.
|
|
35
|
-
"@faststore/sdk": "^2.1.
|
|
36
|
-
"@faststore/ui": "^2.1.
|
|
32
|
+
"@faststore/api": "^2.1.1",
|
|
33
|
+
"@faststore/components": "^2.1.1",
|
|
34
|
+
"@faststore/graphql-utils": "^2.1.1",
|
|
35
|
+
"@faststore/sdk": "^2.1.1",
|
|
36
|
+
"@faststore/ui": "^2.1.1",
|
|
37
37
|
"@types/react": "^18.0.14",
|
|
38
38
|
"@vtex/client-cms": "^0.2.12",
|
|
39
39
|
"autoprefixer": "^10.4.0",
|
|
@@ -59,7 +59,7 @@
|
|
|
59
59
|
},
|
|
60
60
|
"devDependencies": {
|
|
61
61
|
"@cypress/code-coverage": "^3.9.10",
|
|
62
|
-
"@faststore/eslint-config": "
|
|
62
|
+
"@faststore/eslint-config": "^2.1.1",
|
|
63
63
|
"@faststore/lighthouse": "^1.12.32",
|
|
64
64
|
"@graphql-codegen/cli": "^2.6.2",
|
|
65
65
|
"@graphql-codegen/typescript": "^2.5.1",
|
|
@@ -108,5 +108,5 @@
|
|
|
108
108
|
"msw": {
|
|
109
109
|
"workerDirectory": "public"
|
|
110
110
|
},
|
|
111
|
-
"gitHead": "
|
|
111
|
+
"gitHead": "4c32807ee7a90ca5ee882dc9f97ee726132c9ec4"
|
|
112
112
|
}
|
|
@@ -5,7 +5,14 @@ import {
|
|
|
5
5
|
import type { ProductSummary_ProductFragment } from '@generated/graphql'
|
|
6
6
|
import ProductGridSkeleton from 'src/components/skeletons/ProductGridSkeleton'
|
|
7
7
|
|
|
8
|
-
import
|
|
8
|
+
import { ProductCardProps } from '../ProductCard'
|
|
9
|
+
|
|
10
|
+
import {
|
|
11
|
+
Components,
|
|
12
|
+
Props,
|
|
13
|
+
} from 'src/components/sections/ProductGallery/Overrides'
|
|
14
|
+
|
|
15
|
+
const { __experimentalProductCard: ProductCard } = Components
|
|
9
16
|
|
|
10
17
|
interface Props {
|
|
11
18
|
/**
|
|
@@ -23,7 +30,15 @@ interface Props {
|
|
|
23
30
|
productCard?: Pick<ProductCardProps, 'showDiscountBadge' | 'bordered'>
|
|
24
31
|
}
|
|
25
32
|
|
|
26
|
-
function ProductGrid({
|
|
33
|
+
function ProductGrid({
|
|
34
|
+
products,
|
|
35
|
+
page,
|
|
36
|
+
pageSize,
|
|
37
|
+
productCard: {
|
|
38
|
+
showDiscountBadge = Props['ProductCard'].showDiscountBadge,
|
|
39
|
+
bordered = Props['ProductCard'].bordered,
|
|
40
|
+
} = {},
|
|
41
|
+
}: Props) {
|
|
27
42
|
const aspectRatio = 1
|
|
28
43
|
|
|
29
44
|
return (
|
|
@@ -35,16 +50,17 @@ function ProductGrid({ products, page, pageSize, productCard }: Props) {
|
|
|
35
50
|
{products.map(({ node: product }, idx) => (
|
|
36
51
|
<UIProductGridItem key={`${product.id}`}>
|
|
37
52
|
<ProductCard
|
|
38
|
-
product={product}
|
|
39
|
-
index={pageSize * page + idx + 1}
|
|
40
|
-
bordered={productCard?.bordered}
|
|
41
|
-
showDiscountBadge={productCard?.showDiscountBadge}
|
|
42
53
|
aspectRatio={aspectRatio}
|
|
43
54
|
imgProps={{
|
|
44
55
|
width: 150,
|
|
45
56
|
height: 150,
|
|
46
57
|
sizes: '30vw',
|
|
47
58
|
}}
|
|
59
|
+
{...Props['__experimentalProductCard']}
|
|
60
|
+
bordered={showDiscountBadge}
|
|
61
|
+
showDiscountBadge={bordered}
|
|
62
|
+
product={product}
|
|
63
|
+
index={pageSize * page + idx + 1}
|
|
48
64
|
/>
|
|
49
65
|
</UIProductGridItem>
|
|
50
66
|
))}
|
|
@@ -1,12 +1,19 @@
|
|
|
1
1
|
import { gql } from '@faststore/graphql-utils'
|
|
2
2
|
import { useUI } from '@faststore/ui'
|
|
3
3
|
import type { Filter_FacetsFragment } from '@generated/graphql'
|
|
4
|
-
import {
|
|
4
|
+
import { Suspense } from 'react'
|
|
5
5
|
import { ProductGalleryProps } from 'src/components/ui/ProductGallery/ProductGallery'
|
|
6
|
-
import FilterDesktop from './FilterDesktop'
|
|
7
6
|
import { useFilter } from './useFilter'
|
|
8
7
|
|
|
9
|
-
|
|
8
|
+
import {
|
|
9
|
+
Components,
|
|
10
|
+
Props,
|
|
11
|
+
} from 'src/components/sections/ProductGallery/Overrides'
|
|
12
|
+
|
|
13
|
+
const {
|
|
14
|
+
__experimentalFilterDesktop: FilterDesktop,
|
|
15
|
+
__experimentalFilterSlider: FilterSlider,
|
|
16
|
+
} = Components
|
|
10
17
|
|
|
11
18
|
interface Props {
|
|
12
19
|
/**
|
|
@@ -36,6 +43,7 @@ function Filter({
|
|
|
36
43
|
<>
|
|
37
44
|
<div className="hidden-mobile">
|
|
38
45
|
<FilterDesktop
|
|
46
|
+
{...Props['__experimentalFilterDesktop']}
|
|
39
47
|
{...filter}
|
|
40
48
|
testId={testId}
|
|
41
49
|
title={filterCmsData?.title}
|
|
@@ -45,6 +53,7 @@ function Filter({
|
|
|
45
53
|
{displayFilter && (
|
|
46
54
|
<Suspense fallback={null}>
|
|
47
55
|
<FilterSlider
|
|
56
|
+
{...Props['__experimentalFilterSlider']}
|
|
48
57
|
{...filter}
|
|
49
58
|
testId={testId}
|
|
50
59
|
title={filterCmsData?.title}
|
|
@@ -4,17 +4,53 @@ import {
|
|
|
4
4
|
BuyButton as UIBuyButton,
|
|
5
5
|
SkuSelector as UISkuSelector,
|
|
6
6
|
ShippingSimulation as UIShippingSimulation,
|
|
7
|
+
Icon as UIIcon,
|
|
8
|
+
Price as UIPrice,
|
|
9
|
+
QuantitySelector as UIQuantitySelector,
|
|
10
|
+
ImageZoom as UIImageZoom,
|
|
11
|
+
ImageGallery as UIImageGallery,
|
|
7
12
|
} from '@faststore/ui'
|
|
13
|
+
import ImageGallery from 'src/components/ui/ImageGallery'
|
|
14
|
+
import ShippingSimulation from 'src/components/ui/ShippingSimulation/ShippingSimulation'
|
|
15
|
+
import { Image } from 'src/components/ui/Image'
|
|
8
16
|
|
|
9
17
|
import ProductDetailsCustomizations from 'src/customizations/components/overrides/ProductDetails'
|
|
10
18
|
|
|
19
|
+
const productDetailsComponentsCustomization = {}
|
|
20
|
+
|
|
21
|
+
const productDetailsPropsCustomization = {} as any
|
|
22
|
+
|
|
23
|
+
Object.entries(ProductDetailsCustomizations.components).forEach(
|
|
24
|
+
([key, value]) => {
|
|
25
|
+
if (value.Component) {
|
|
26
|
+
productDetailsComponentsCustomization[key] = value.Component
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
)
|
|
30
|
+
|
|
31
|
+
Object.entries(ProductDetailsCustomizations.components).forEach(
|
|
32
|
+
([key, value]) => {
|
|
33
|
+
if (value.props) {
|
|
34
|
+
productDetailsPropsCustomization[key] = value.props
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
)
|
|
38
|
+
|
|
11
39
|
const Components = {
|
|
12
40
|
ProductTitle: UIProductTitle,
|
|
13
41
|
DiscountBadge: UIDiscountBadge,
|
|
14
42
|
BuyButton: UIBuyButton,
|
|
43
|
+
Icon: UIIcon,
|
|
44
|
+
Price: UIPrice,
|
|
45
|
+
QuantitySelector: UIQuantitySelector,
|
|
15
46
|
SkuSelector: UISkuSelector,
|
|
16
47
|
ShippingSimulation: UIShippingSimulation,
|
|
17
|
-
|
|
48
|
+
ImageGallery: UIImageGallery,
|
|
49
|
+
ImageZoom: UIImageZoom,
|
|
50
|
+
__experimentalImageGalleryImage: Image,
|
|
51
|
+
__experimentalImageGallery: ImageGallery,
|
|
52
|
+
__experimentalShippingSimulation: ShippingSimulation,
|
|
53
|
+
...productDetailsComponentsCustomization,
|
|
18
54
|
}
|
|
19
55
|
|
|
20
|
-
export { Components }
|
|
56
|
+
export { Components, productDetailsPropsCustomization as Props }
|
|
@@ -4,7 +4,6 @@ import { gql } from '@faststore/graphql-utils'
|
|
|
4
4
|
import { sendAnalyticsEvent } from '@faststore/sdk'
|
|
5
5
|
import type { CurrencyCode, ViewItemEvent } from '@faststore/sdk'
|
|
6
6
|
import type { ProductDetailsFragment_ProductFragment } from '@generated/graphql'
|
|
7
|
-
import { Link as UILink } from '@faststore/ui'
|
|
8
7
|
|
|
9
8
|
import { useSession } from 'src/sdk/session'
|
|
10
9
|
import { useProduct } from 'src/sdk/product/useProduct'
|
|
@@ -13,16 +12,22 @@ import type { AnalyticsItem } from 'src/sdk/analytics/types'
|
|
|
13
12
|
|
|
14
13
|
import Section from '../Section'
|
|
15
14
|
import OutOfStock from 'src/components/product/OutOfStock'
|
|
16
|
-
import ImageGallery from 'src/components/ui/ImageGallery'
|
|
17
|
-
import ShippingSimulation from 'src/components/ui/ShippingSimulation'
|
|
18
15
|
import ProductDescription from 'src/components/ui/ProductDescription'
|
|
19
16
|
import { ProductDetailsSettings } from 'src/components/ui/ProductDetails'
|
|
20
17
|
|
|
21
18
|
import styles from './section.module.scss'
|
|
22
19
|
|
|
23
|
-
import {
|
|
20
|
+
import {
|
|
21
|
+
Components,
|
|
22
|
+
Props,
|
|
23
|
+
} from 'src/components/sections/ProductDetails/Overrides'
|
|
24
24
|
|
|
25
|
-
const {
|
|
25
|
+
const {
|
|
26
|
+
ProductTitle,
|
|
27
|
+
DiscountBadge,
|
|
28
|
+
__experimentalImageGallery: ImageGallery,
|
|
29
|
+
__experimentalShippingSimulation: ShippingSimulation,
|
|
30
|
+
} = Components
|
|
26
31
|
|
|
27
32
|
interface ProductDetailsContextProps {
|
|
28
33
|
context: ProductDetailsFragment_ProductFragment
|
|
@@ -63,14 +68,28 @@ function ProductDetails({
|
|
|
63
68
|
context: staleProduct,
|
|
64
69
|
productTitle: {
|
|
65
70
|
refNumber: showRefNumber,
|
|
66
|
-
discountBadge: {
|
|
71
|
+
discountBadge: {
|
|
72
|
+
showDiscountBadge,
|
|
73
|
+
size: discountBadgeSize = Props['DiscountBadge'].size,
|
|
74
|
+
},
|
|
67
75
|
},
|
|
68
76
|
buyButton: { icon: buyButtonIcon, title: buyButtonTitle },
|
|
69
77
|
shippingSimulator: {
|
|
70
|
-
title: shippingSimulatorTitle
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
78
|
+
title: shippingSimulatorTitle = Props['__experimentalShippingSimulation']
|
|
79
|
+
.title,
|
|
80
|
+
inputLabel: shippingSimulatorInputLabel = Props[
|
|
81
|
+
'__experimentalShippingSimulation'
|
|
82
|
+
].inputLabel,
|
|
83
|
+
shippingOptionsTableTitle: shippingSimulatorOptionsTableTitle = Props[
|
|
84
|
+
'__experimentalShippingSimulation'
|
|
85
|
+
].optionsLabel,
|
|
86
|
+
link: {
|
|
87
|
+
to: shippingSimulatorLinkUrl = Props['__experimentalShippingSimulation']
|
|
88
|
+
.idkPostalCodeLinkProps?.href,
|
|
89
|
+
text: shippingSimulatorLinkText = Props[
|
|
90
|
+
'__experimentalShippingSimulation'
|
|
91
|
+
].idkPostalCodeLinkProps?.children,
|
|
92
|
+
},
|
|
74
93
|
},
|
|
75
94
|
productDescription: {
|
|
76
95
|
title: productDescriptionDetailsTitle,
|
|
@@ -149,13 +168,20 @@ function ProductDetails({
|
|
|
149
168
|
<section data-fs-product-details-body>
|
|
150
169
|
<header data-fs-product-details-title data-fs-product-details-section>
|
|
151
170
|
<ProductTitle
|
|
171
|
+
// TODO: We should review this prop. There's now way to override the title and use the dynamic name value.
|
|
172
|
+
// Maybe passing a ProductTitleHeader component as a prop would be better, as it would be overridable.
|
|
173
|
+
// Maybe now it's worth to make title always a h1 and receive only the name, as it would be easier for users to override.
|
|
152
174
|
title={<h1>{name}</h1>}
|
|
175
|
+
{...Props['ProductTitle']}
|
|
153
176
|
label={
|
|
154
177
|
showDiscountBadge && (
|
|
155
178
|
<DiscountBadge
|
|
179
|
+
{...Props['DiscountBadge']}
|
|
180
|
+
size={discountBadgeSize}
|
|
181
|
+
// Dynamic props shouldn't be overridable
|
|
182
|
+
// This decision can be reviewed later if needed
|
|
156
183
|
listPrice={listPrice}
|
|
157
184
|
spotPrice={lowPrice}
|
|
158
|
-
size={discountBadgeSize}
|
|
159
185
|
/>
|
|
160
186
|
)
|
|
161
187
|
}
|
|
@@ -164,6 +190,7 @@ function ProductDetails({
|
|
|
164
190
|
</header>
|
|
165
191
|
<ImageGallery
|
|
166
192
|
data-fs-product-details-gallery
|
|
193
|
+
{...Props['__experimentalImageGallery']}
|
|
167
194
|
images={productImages}
|
|
168
195
|
/>
|
|
169
196
|
<section data-fs-product-details-info>
|
|
@@ -189,18 +216,20 @@ function ProductDetails({
|
|
|
189
216
|
<ShippingSimulation
|
|
190
217
|
data-fs-product-details-section
|
|
191
218
|
data-fs-product-details-shipping
|
|
219
|
+
formatter={useFormattedPrice}
|
|
220
|
+
{...Props['__experimentalShippingSimulation']}
|
|
221
|
+
idkPostalCodeLinkProps={{
|
|
222
|
+
...Props['idkPostalCodeLinkProps'],
|
|
223
|
+
href: shippingSimulatorLinkUrl,
|
|
224
|
+
children: shippingSimulatorLinkText,
|
|
225
|
+
}}
|
|
192
226
|
productShippingInfo={{
|
|
193
227
|
id,
|
|
194
228
|
quantity,
|
|
195
229
|
seller: seller.identifier,
|
|
196
230
|
}}
|
|
197
|
-
formatter={useFormattedPrice}
|
|
198
231
|
title={shippingSimulatorTitle}
|
|
199
232
|
inputLabel={shippingSimulatorInputLabel}
|
|
200
|
-
idkPostalCodeLinkProps={{
|
|
201
|
-
href: shippingSimulatorLinkUrl,
|
|
202
|
-
children: shippingSimulatorLinkText,
|
|
203
|
-
}}
|
|
204
233
|
optionsLabel={shippingSimulatorOptionsTableTitle}
|
|
205
234
|
/>
|
|
206
235
|
)}
|
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
@import "@faststore/ui/src/components/molecules/Dropdown/styles.scss";
|
|
16
16
|
@import "@faststore/ui/src/components/molecules/InputField/styles.scss";
|
|
17
17
|
@import "@faststore/ui/src/components/molecules/LinkButton/styles.scss";
|
|
18
|
+
@import "@faststore/ui/src/components/molecules/Rating/styles.scss";
|
|
18
19
|
@import "@faststore/ui/src/components/molecules/ProductTitle/styles.scss";
|
|
19
20
|
@import "@faststore/ui/src/components/molecules/QuantitySelector/styles.scss";
|
|
20
21
|
@import "@faststore/ui/src/components/molecules/SkuSelector/styles.scss";
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { lazy } from 'react'
|
|
2
|
+
import {
|
|
3
|
+
Button as UIButton,
|
|
4
|
+
LinkButton as UILinkButton,
|
|
5
|
+
Skeleton as UISkeleton,
|
|
6
|
+
Icon as UIIcon,
|
|
7
|
+
} from '@faststore/ui'
|
|
8
|
+
import ProductCard from 'src/components/product/ProductCard'
|
|
9
|
+
import FilterDesktop from 'src/components/search/Filter/FilterDesktop'
|
|
10
|
+
|
|
11
|
+
const FilterSlider = lazy(
|
|
12
|
+
() => import('src/components/search/Filter/FilterSlider')
|
|
13
|
+
)
|
|
14
|
+
|
|
15
|
+
import ProductGalleryCustomizations from 'src/customizations/components/overrides/ProductGallery'
|
|
16
|
+
|
|
17
|
+
const productGalleryComponentsCustomization = {}
|
|
18
|
+
|
|
19
|
+
const productGalleryPropsCustomization = {} as any
|
|
20
|
+
|
|
21
|
+
Object.entries(ProductGalleryCustomizations.components).forEach(
|
|
22
|
+
([key, value]) => {
|
|
23
|
+
if (value.Component) {
|
|
24
|
+
productGalleryComponentsCustomization[key] = value.Component
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
)
|
|
28
|
+
|
|
29
|
+
Object.entries(ProductGalleryCustomizations.components).forEach(
|
|
30
|
+
([key, value]) => {
|
|
31
|
+
if (value.props) {
|
|
32
|
+
productGalleryPropsCustomization[key] = value.props
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
)
|
|
36
|
+
|
|
37
|
+
const Components = {
|
|
38
|
+
Button: UIButton,
|
|
39
|
+
FilterIcon: UIIcon,
|
|
40
|
+
PrevIcon: UIIcon,
|
|
41
|
+
ResultsCountSkeleton: UISkeleton,
|
|
42
|
+
SortSkeleton: UISkeleton,
|
|
43
|
+
FilterButtonSkeleton: UISkeleton,
|
|
44
|
+
LinkButtonPrev: UILinkButton,
|
|
45
|
+
LinkButtonNext: UILinkButton,
|
|
46
|
+
__experimentalFilterDesktop: FilterDesktop,
|
|
47
|
+
__experimentalFilterSlider: FilterSlider,
|
|
48
|
+
__experimentalProductCard: ProductCard,
|
|
49
|
+
...productGalleryComponentsCustomization,
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
export { Components, productGalleryPropsCustomization as Props }
|
|
@@ -1,16 +1,18 @@
|
|
|
1
|
-
import {
|
|
2
|
-
ImageElementData,
|
|
3
|
-
ImageZoom,
|
|
4
|
-
ImageGallery as UIImageGallery,
|
|
5
|
-
} from '@faststore/ui'
|
|
1
|
+
import { ImageElementData } from '@faststore/ui'
|
|
6
2
|
import { useEffect, useState } from 'react'
|
|
7
3
|
|
|
8
4
|
import { useRouter } from 'next/router'
|
|
9
|
-
import { Image } from 'src/components/ui/Image'
|
|
10
5
|
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
6
|
+
import {
|
|
7
|
+
Components,
|
|
8
|
+
Props,
|
|
9
|
+
} from 'src/components/sections/ProductDetails/Overrides'
|
|
10
|
+
|
|
11
|
+
const ImageComponent = ({ url, alternateName }) => {
|
|
12
|
+
const { __experimentalImageGalleryImage: Image } = Components
|
|
13
|
+
|
|
14
|
+
return <Image src={url} alt={alternateName} width={68} height={68} />
|
|
15
|
+
}
|
|
14
16
|
|
|
15
17
|
export interface ImageGalleryProps {
|
|
16
18
|
images: ImageElementData[]
|
|
@@ -23,25 +25,34 @@ const ImageGallery = ({ images, ...otherProps }: ImageGalleryProps) => {
|
|
|
23
25
|
|
|
24
26
|
useEffect(() => setSelectedImageIdx(0), [dynamicRoute])
|
|
25
27
|
|
|
28
|
+
// Deconstructing the object to avoid circular dependency errors
|
|
29
|
+
const {
|
|
30
|
+
ImageGallery: ImageGalleryWrapper,
|
|
31
|
+
ImageZoom,
|
|
32
|
+
__experimentalImageGalleryImage: Image,
|
|
33
|
+
} = Components
|
|
34
|
+
|
|
26
35
|
return (
|
|
27
|
-
<
|
|
36
|
+
<ImageGalleryWrapper
|
|
37
|
+
{...Props['ImageGallery']}
|
|
28
38
|
images={images}
|
|
29
39
|
ImageComponent={ImageComponent}
|
|
30
40
|
selectedImageIdx={selectedImageIdx}
|
|
31
41
|
setSelectedImageIdx={setSelectedImageIdx}
|
|
32
42
|
{...otherProps}
|
|
33
43
|
>
|
|
34
|
-
<ImageZoom>
|
|
44
|
+
<ImageZoom {...Props['ImageZoom']}>
|
|
35
45
|
<Image
|
|
36
|
-
src={currentImage.url}
|
|
37
|
-
alt={currentImage.alternateName}
|
|
38
46
|
sizes="(max-width: 360px) 50vw, (max-width: 768px) 90vw, 50vw"
|
|
39
47
|
width={691}
|
|
40
48
|
height={691 * (3 / 4)}
|
|
41
49
|
loading="eager"
|
|
50
|
+
{...Props['__experimentalImageGalleryImage']}
|
|
51
|
+
src={currentImage.url}
|
|
52
|
+
alt={currentImage.alternateName}
|
|
42
53
|
/>
|
|
43
54
|
</ImageZoom>
|
|
44
|
-
</
|
|
55
|
+
</ImageGalleryWrapper>
|
|
45
56
|
)
|
|
46
57
|
}
|
|
47
58
|
|
|
@@ -1,11 +1,5 @@
|
|
|
1
1
|
import type { Dispatch, SetStateAction } from 'react'
|
|
2
2
|
|
|
3
|
-
import {
|
|
4
|
-
Icon as UIIcon,
|
|
5
|
-
Price as UIPrice,
|
|
6
|
-
QuantitySelector as UIQuantitySelector,
|
|
7
|
-
} from '@faststore/ui'
|
|
8
|
-
|
|
9
3
|
import type { ProductDetailsFragment_ProductFragment } from '@generated/graphql'
|
|
10
4
|
|
|
11
5
|
import { useBuyButton } from 'src/sdk/cart/useBuyButton'
|
|
@@ -14,9 +8,12 @@ import { useFormattedPrice } from 'src/sdk/product/useFormattedPrice'
|
|
|
14
8
|
import Selectors from 'src/components/ui/SkuSelector'
|
|
15
9
|
import AddToCartLoadingSkeleton from './AddToCartLoadingSkeleton'
|
|
16
10
|
|
|
17
|
-
import {
|
|
11
|
+
import {
|
|
12
|
+
Components,
|
|
13
|
+
Props,
|
|
14
|
+
} from 'src/components/sections/ProductDetails/Overrides'
|
|
18
15
|
|
|
19
|
-
const { BuyButton } = Components
|
|
16
|
+
const { BuyButton, Icon, Price, QuantitySelector } = Components
|
|
20
17
|
|
|
21
18
|
interface ProductDetailsSettingsProps {
|
|
22
19
|
product: ProductDetailsFragment_ProductFragment
|
|
@@ -36,7 +33,10 @@ function ProductDetailsSettings({
|
|
|
36
33
|
isValidating,
|
|
37
34
|
quantity,
|
|
38
35
|
setQuantity,
|
|
39
|
-
buyButtonIcon: {
|
|
36
|
+
buyButtonIcon: {
|
|
37
|
+
icon: buyButtonIconName = Props['Icon'].name,
|
|
38
|
+
alt: buyButtonIconAlt = Props['Icon']['aria-label'],
|
|
39
|
+
},
|
|
40
40
|
}: ProductDetailsSettingsProps) {
|
|
41
41
|
const {
|
|
42
42
|
id,
|
|
@@ -77,25 +77,34 @@ function ProductDetailsSettings({
|
|
|
77
77
|
<>
|
|
78
78
|
<section data-fs-product-details-values>
|
|
79
79
|
<div data-fs-product-details-prices>
|
|
80
|
-
<
|
|
81
|
-
value={listPrice}
|
|
80
|
+
<Price
|
|
82
81
|
formatter={useFormattedPrice}
|
|
83
82
|
testId="list-price"
|
|
84
|
-
data-value={listPrice}
|
|
85
83
|
variant="listing"
|
|
86
84
|
SRText="Original price:"
|
|
85
|
+
{...Props['Price']}
|
|
86
|
+
value={listPrice}
|
|
87
|
+
data-value={listPrice}
|
|
87
88
|
/>
|
|
88
|
-
<
|
|
89
|
-
value={lowPrice}
|
|
89
|
+
<Price
|
|
90
90
|
formatter={useFormattedPrice}
|
|
91
91
|
testId="price"
|
|
92
|
-
data-value={lowPrice}
|
|
93
92
|
variant="spot"
|
|
94
93
|
className="text__lead"
|
|
95
94
|
SRText="Sale Price:"
|
|
95
|
+
{...Props['Price']}
|
|
96
|
+
value={lowPrice}
|
|
97
|
+
data-value={lowPrice}
|
|
96
98
|
/>
|
|
97
99
|
</div>
|
|
98
|
-
<
|
|
100
|
+
<QuantitySelector
|
|
101
|
+
min={1}
|
|
102
|
+
max={10}
|
|
103
|
+
{...Props['QuantitySelector']}
|
|
104
|
+
// Dynamic props shouldn't be overridable
|
|
105
|
+
// This decision can be reviewed later if needed
|
|
106
|
+
onChange={setQuantity}
|
|
107
|
+
/>
|
|
99
108
|
</section>
|
|
100
109
|
{skuVariants && (
|
|
101
110
|
<Selectors
|
|
@@ -114,10 +123,15 @@ function ProductDetailsSettings({
|
|
|
114
123
|
<AddToCartLoadingSkeleton />
|
|
115
124
|
) : (
|
|
116
125
|
<BuyButton
|
|
117
|
-
|
|
126
|
+
{...Props['BuyButton']}
|
|
118
127
|
icon={
|
|
119
|
-
<
|
|
128
|
+
<Icon
|
|
129
|
+
{...Props['Icon']}
|
|
130
|
+
aria-label={buyButtonIconAlt}
|
|
131
|
+
name={buyButtonIconName}
|
|
132
|
+
/>
|
|
120
133
|
}
|
|
134
|
+
disabled={buyDisabled}
|
|
121
135
|
{...buyProps}
|
|
122
136
|
>
|
|
123
137
|
{buyButtonTitle || 'Add to Cart'}
|