mirror of
https://github.com/vercel/commerce.git
synced 2025-05-18 07:26:59 +00:00
Merge branch 'local-provider' into custom-checkout
This commit is contained in:
commit
d2688df15f
@ -38,6 +38,7 @@ const UserNav: FC<Props> = ({ className }) => {
|
|||||||
</Link>
|
</Link>
|
||||||
</li>
|
</li>
|
||||||
)}
|
)}
|
||||||
|
{process.env.COMMERCE_CUSTOMER_ENABLED && (
|
||||||
<li className={s.item}>
|
<li className={s.item}>
|
||||||
{customer ? (
|
{customer ? (
|
||||||
<DropdownMenu />
|
<DropdownMenu />
|
||||||
@ -51,6 +52,7 @@ const UserNav: FC<Props> = ({ className }) => {
|
|||||||
</button>
|
</button>
|
||||||
)}
|
)}
|
||||||
</li>
|
</li>
|
||||||
|
)}
|
||||||
</ul>
|
</ul>
|
||||||
</nav>
|
</nav>
|
||||||
)
|
)
|
||||||
|
@ -41,9 +41,9 @@ export default function Search({ categories, brands }: SearchPropsType) {
|
|||||||
const query = filterQuery({ sort })
|
const query = filterQuery({ sort })
|
||||||
|
|
||||||
const { pathname, category, brand } = useSearchMeta(asPath)
|
const { pathname, category, brand } = useSearchMeta(asPath)
|
||||||
const activeCategory = categories.find((cat) => cat.slug === category)
|
const activeCategory = categories.find((cat: any) => cat.slug === category)
|
||||||
const activeBrand = brands.find(
|
const activeBrand = brands.find(
|
||||||
(b) => getSlug(b.node.path) === `brands/${brand}`
|
(b: any) => getSlug(b.node.path) === `brands/${brand}`
|
||||||
)?.node
|
)?.node
|
||||||
|
|
||||||
const { data } = useSearch({
|
const { data } = useSearch({
|
||||||
@ -132,7 +132,7 @@ export default function Search({ categories, brands }: SearchPropsType) {
|
|||||||
</a>
|
</a>
|
||||||
</Link>
|
</Link>
|
||||||
</li>
|
</li>
|
||||||
{categories.map((cat) => (
|
{categories.map((cat: any) => (
|
||||||
<li
|
<li
|
||||||
key={cat.path}
|
key={cat.path}
|
||||||
className={cn(
|
className={cn(
|
||||||
@ -233,7 +233,7 @@ export default function Search({ categories, brands }: SearchPropsType) {
|
|||||||
</a>
|
</a>
|
||||||
</Link>
|
</Link>
|
||||||
</li>
|
</li>
|
||||||
{brands.flatMap(({ node }) => (
|
{brands.flatMap(({ node }: { node: any }) => (
|
||||||
<li
|
<li
|
||||||
key={node.path}
|
key={node.path}
|
||||||
className={cn(
|
className={cn(
|
||||||
@ -312,7 +312,6 @@ export default function Search({ categories, brands }: SearchPropsType) {
|
|||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{data ? (
|
{data ? (
|
||||||
<div className="grid grid-cols-1 gap-6 sm:grid-cols-2 lg:grid-cols-3">
|
<div className="grid grid-cols-1 gap-6 sm:grid-cols-2 lg:grid-cols-3">
|
||||||
{data.products.map((product: Product) => (
|
{data.products.map((product: Product) => (
|
||||||
@ -336,7 +335,8 @@ export default function Search({ categories, brands }: SearchPropsType) {
|
|||||||
</Skeleton>
|
</Skeleton>
|
||||||
))}
|
))}
|
||||||
</div>
|
</div>
|
||||||
)} </div>
|
)}{' '}
|
||||||
|
</div>
|
||||||
|
|
||||||
{/* Sort */}
|
{/* Sort */}
|
||||||
<div className="col-span-8 lg:col-span-2 order-2 lg:order-none">
|
<div className="col-span-8 lg:col-span-2 order-2 lg:order-none">
|
||||||
|
@ -72,9 +72,8 @@ export type APIProvider = {
|
|||||||
operations: APIOperations<any>
|
operations: APIOperations<any>
|
||||||
}
|
}
|
||||||
|
|
||||||
export type CommerceAPI<
|
export type CommerceAPI<P extends APIProvider = APIProvider> =
|
||||||
P extends APIProvider = APIProvider
|
CommerceAPICore<P> & AllOperations<P>
|
||||||
> = CommerceAPICore<P> & AllOperations<P>
|
|
||||||
|
|
||||||
export class CommerceAPICore<P extends APIProvider = APIProvider> {
|
export class CommerceAPICore<P extends APIProvider = APIProvider> {
|
||||||
constructor(readonly provider: P) {}
|
constructor(readonly provider: P) {}
|
||||||
@ -134,9 +133,9 @@ export function getEndpoint<
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export const createEndpoint = <API extends GetAPISchema<any, any>>(
|
export const createEndpoint =
|
||||||
endpoint: API['endpoint']
|
<API extends GetAPISchema<any, any>>(endpoint: API['endpoint']) =>
|
||||||
) => <P extends APIProvider>(
|
<P extends APIProvider>(
|
||||||
commerce: CommerceAPI<P>,
|
commerce: CommerceAPI<P>,
|
||||||
context?: Partial<API['endpoint']> & {
|
context?: Partial<API['endpoint']> & {
|
||||||
config?: P['config']
|
config?: P['config']
|
||||||
|
@ -7,7 +7,7 @@ const fs = require('fs')
|
|||||||
const merge = require('deepmerge')
|
const merge = require('deepmerge')
|
||||||
const prettier = require('prettier')
|
const prettier = require('prettier')
|
||||||
|
|
||||||
const PROVIDERS = ['bigcommerce', 'shopify', 'swell', 'vendure']
|
const PROVIDERS = ['bigcommerce', 'shopify', 'swell', 'vendure', 'local']
|
||||||
|
|
||||||
function getProviderName() {
|
function getProviderName() {
|
||||||
return (
|
return (
|
||||||
@ -18,7 +18,7 @@ function getProviderName() {
|
|||||||
? 'shopify'
|
? 'shopify'
|
||||||
: process.env.NEXT_PUBLIC_SWELL_STORE_ID
|
: process.env.NEXT_PUBLIC_SWELL_STORE_ID
|
||||||
? 'swell'
|
? 'swell'
|
||||||
: null)
|
: 'local')
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -165,15 +165,13 @@ export type AddItemHandler<T extends CartTypes = CartTypes> = AddItemHook<T> & {
|
|||||||
body: { cartId: string }
|
body: { cartId: string }
|
||||||
}
|
}
|
||||||
|
|
||||||
export type UpdateItemHandler<
|
export type UpdateItemHandler<T extends CartTypes = CartTypes> =
|
||||||
T extends CartTypes = CartTypes
|
UpdateItemHook<T> & {
|
||||||
> = UpdateItemHook<T> & {
|
|
||||||
data: T['cart']
|
data: T['cart']
|
||||||
body: { cartId: string }
|
body: { cartId: string }
|
||||||
}
|
}
|
||||||
|
|
||||||
export type RemoveItemHandler<
|
export type RemoveItemHandler<T extends CartTypes = CartTypes> =
|
||||||
T extends CartTypes = CartTypes
|
RemoveItemHook<T> & {
|
||||||
> = RemoveItemHook<T> & {
|
|
||||||
body: { cartId: string }
|
body: { cartId: string }
|
||||||
}
|
}
|
||||||
|
1
framework/local/.env.template
Normal file
1
framework/local/.env.template
Normal file
@ -0,0 +1 @@
|
|||||||
|
COMMERCE_PROVIDER=local
|
1
framework/local/README.md
Normal file
1
framework/local/README.md
Normal file
@ -0,0 +1 @@
|
|||||||
|
# Next.js Local Provider
|
1
framework/local/api/endpoints/cart/index.ts
Normal file
1
framework/local/api/endpoints/cart/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/catalog/index.ts
Normal file
1
framework/local/api/endpoints/catalog/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/catalog/products.ts
Normal file
1
framework/local/api/endpoints/catalog/products.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/checkout/index.ts
Normal file
1
framework/local/api/endpoints/checkout/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/customer/index.ts
Normal file
1
framework/local/api/endpoints/customer/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/login/index.ts
Normal file
1
framework/local/api/endpoints/login/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/logout/index.ts
Normal file
1
framework/local/api/endpoints/logout/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/signup/index.ts
Normal file
1
framework/local/api/endpoints/signup/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
1
framework/local/api/endpoints/wishlist/index.tsx
Normal file
1
framework/local/api/endpoints/wishlist/index.tsx
Normal file
@ -0,0 +1 @@
|
|||||||
|
export default function noopApi(...args: any[]): void {}
|
42
framework/local/api/index.ts
Normal file
42
framework/local/api/index.ts
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
import type { APIProvider, CommerceAPIConfig } from '@commerce/api'
|
||||||
|
import { CommerceAPI, getCommerceApi as commerceApi } from '@commerce/api'
|
||||||
|
import fetcher from './utils/fetch-local'
|
||||||
|
|
||||||
|
import getAllPages from './operations/get-all-pages'
|
||||||
|
import getPage from './operations/get-page'
|
||||||
|
import getSiteInfo from './operations/get-site-info'
|
||||||
|
import getCustomerWishlist from './operations/get-customer-wishlist'
|
||||||
|
import getAllProductPaths from './operations/get-all-product-paths'
|
||||||
|
import getAllProducts from './operations/get-all-products'
|
||||||
|
import getProduct from './operations/get-product'
|
||||||
|
|
||||||
|
export interface LocalConfig extends CommerceAPIConfig {}
|
||||||
|
const config: LocalConfig = {
|
||||||
|
commerceUrl: '',
|
||||||
|
apiToken: '',
|
||||||
|
cartCookie: '',
|
||||||
|
customerCookie: '',
|
||||||
|
cartCookieMaxAge: 2592000,
|
||||||
|
fetch: fetcher,
|
||||||
|
}
|
||||||
|
|
||||||
|
const operations = {
|
||||||
|
getAllPages,
|
||||||
|
getPage,
|
||||||
|
getSiteInfo,
|
||||||
|
getCustomerWishlist,
|
||||||
|
getAllProductPaths,
|
||||||
|
getAllProducts,
|
||||||
|
getProduct,
|
||||||
|
}
|
||||||
|
|
||||||
|
export const provider = { config, operations }
|
||||||
|
|
||||||
|
export type Provider = typeof provider
|
||||||
|
export type LocalAPI<P extends Provider = Provider> = CommerceAPI<P | any>
|
||||||
|
|
||||||
|
export function getCommerceApi<P extends Provider>(
|
||||||
|
customProvider: P = provider as any
|
||||||
|
): LocalAPI<P> {
|
||||||
|
return commerceApi(customProvider as any)
|
||||||
|
}
|
19
framework/local/api/operations/get-all-pages.ts
Normal file
19
framework/local/api/operations/get-all-pages.ts
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
export type Page = { url: string }
|
||||||
|
export type GetAllPagesResult = { pages: Page[] }
|
||||||
|
import type { LocalConfig } from '../index'
|
||||||
|
|
||||||
|
export default function getAllPagesOperation() {
|
||||||
|
function getAllPages({
|
||||||
|
config,
|
||||||
|
preview,
|
||||||
|
}: {
|
||||||
|
url?: string
|
||||||
|
config?: Partial<LocalConfig>
|
||||||
|
preview?: boolean
|
||||||
|
}): Promise<GetAllPagesResult> {
|
||||||
|
return Promise.resolve({
|
||||||
|
pages: [],
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return getAllPages
|
||||||
|
}
|
15
framework/local/api/operations/get-all-product-paths.ts
Normal file
15
framework/local/api/operations/get-all-product-paths.ts
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
import data from '../../data.json'
|
||||||
|
|
||||||
|
export type GetAllProductPathsResult = {
|
||||||
|
products: Array<{ path: string }>
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function getAllProductPathsOperation() {
|
||||||
|
function getAllProductPaths(): Promise<GetAllProductPathsResult> {
|
||||||
|
return Promise.resolve({
|
||||||
|
products: data.products.map(({ path }) => ({ path })),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
return getAllProductPaths
|
||||||
|
}
|
25
framework/local/api/operations/get-all-products.ts
Normal file
25
framework/local/api/operations/get-all-products.ts
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
import { Product } from '@commerce/types/product'
|
||||||
|
import { GetAllProductsOperation } from '@commerce/types/product'
|
||||||
|
import type { OperationContext } from '@commerce/api/operations'
|
||||||
|
import type { LocalConfig, Provider } from '../index'
|
||||||
|
import data from '../../data.json'
|
||||||
|
|
||||||
|
export default function getAllProductsOperation({
|
||||||
|
commerce,
|
||||||
|
}: OperationContext<any>) {
|
||||||
|
async function getAllProducts<T extends GetAllProductsOperation>({
|
||||||
|
query = '',
|
||||||
|
variables,
|
||||||
|
config,
|
||||||
|
}: {
|
||||||
|
query?: string
|
||||||
|
variables?: T['variables']
|
||||||
|
config?: Partial<LocalConfig>
|
||||||
|
preview?: boolean
|
||||||
|
} = {}): Promise<{ products: Product[] | any[] }> {
|
||||||
|
return Promise.resolve({
|
||||||
|
products: data.products,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return getAllProducts
|
||||||
|
}
|
6
framework/local/api/operations/get-customer-wishlist.ts
Normal file
6
framework/local/api/operations/get-customer-wishlist.ts
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
export default function getCustomerWishlistOperation() {
|
||||||
|
function getCustomerWishlist(): any {
|
||||||
|
return { wishlist: {} }
|
||||||
|
}
|
||||||
|
return getCustomerWishlist
|
||||||
|
}
|
12
framework/local/api/operations/get-page.ts
Normal file
12
framework/local/api/operations/get-page.ts
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
export type Page = any
|
||||||
|
export type GetPageResult = { page?: Page }
|
||||||
|
export type PageVariables = {
|
||||||
|
id: number
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function getPageOperation() {
|
||||||
|
function getPage(): Promise<GetPageResult> {
|
||||||
|
return Promise.resolve({})
|
||||||
|
}
|
||||||
|
return getPage
|
||||||
|
}
|
26
framework/local/api/operations/get-product.ts
Normal file
26
framework/local/api/operations/get-product.ts
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
import type { LocalConfig } from '../index'
|
||||||
|
import { Product } from '@commerce/types/product'
|
||||||
|
import { GetProductOperation } from '@commerce/types/product'
|
||||||
|
import data from '../../data.json'
|
||||||
|
import type { OperationContext } from '@commerce/api/operations'
|
||||||
|
|
||||||
|
export default function getProductOperation({
|
||||||
|
commerce,
|
||||||
|
}: OperationContext<any>) {
|
||||||
|
async function getProduct<T extends GetProductOperation>({
|
||||||
|
query = '',
|
||||||
|
variables,
|
||||||
|
config,
|
||||||
|
}: {
|
||||||
|
query?: string
|
||||||
|
variables?: T['variables']
|
||||||
|
config?: Partial<LocalConfig>
|
||||||
|
preview?: boolean
|
||||||
|
} = {}): Promise<Product | {} | any> {
|
||||||
|
return Promise.resolve({
|
||||||
|
product: data.products[0],
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
return getProduct
|
||||||
|
}
|
30
framework/local/api/operations/get-site-info.ts
Normal file
30
framework/local/api/operations/get-site-info.ts
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
import { OperationContext } from '@commerce/api/operations'
|
||||||
|
import { Category } from '@commerce/types/site'
|
||||||
|
import { LocalConfig } from '../index'
|
||||||
|
|
||||||
|
export type GetSiteInfoResult<
|
||||||
|
T extends { categories: any[]; brands: any[] } = {
|
||||||
|
categories: Category[]
|
||||||
|
brands: any[]
|
||||||
|
}
|
||||||
|
> = T
|
||||||
|
|
||||||
|
export default function getSiteInfoOperation({}: OperationContext<any>) {
|
||||||
|
function getSiteInfo({
|
||||||
|
query,
|
||||||
|
variables,
|
||||||
|
config: cfg,
|
||||||
|
}: {
|
||||||
|
query?: string
|
||||||
|
variables?: any
|
||||||
|
config?: Partial<LocalConfig>
|
||||||
|
preview?: boolean
|
||||||
|
} = {}): Promise<GetSiteInfoResult> {
|
||||||
|
return Promise.resolve({
|
||||||
|
categories: [],
|
||||||
|
brands: [],
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
return getSiteInfo
|
||||||
|
}
|
6
framework/local/api/operations/index.ts
Normal file
6
framework/local/api/operations/index.ts
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
export { default as getPage } from './get-page'
|
||||||
|
export { default as getSiteInfo } from './get-site-info'
|
||||||
|
export { default as getAllPages } from './get-all-pages'
|
||||||
|
export { default as getProduct } from './get-product'
|
||||||
|
export { default as getAllProducts } from './get-all-products'
|
||||||
|
export { default as getAllProductPaths } from './get-all-product-paths'
|
36
framework/local/api/utils/fetch-local.ts
Normal file
36
framework/local/api/utils/fetch-local.ts
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
import { FetcherError } from '@commerce/utils/errors'
|
||||||
|
import type { GraphQLFetcher } from '@commerce/api'
|
||||||
|
import { getCommerceApi } from '../index'
|
||||||
|
import fetch from './fetch'
|
||||||
|
|
||||||
|
const fetchGraphqlApi: GraphQLFetcher = async (
|
||||||
|
query: string,
|
||||||
|
{ variables, preview } = {},
|
||||||
|
fetchOptions
|
||||||
|
) => {
|
||||||
|
const config = getCommerceApi().getConfig()
|
||||||
|
const res = await fetch(config.commerceUrl, {
|
||||||
|
...fetchOptions,
|
||||||
|
method: 'POST',
|
||||||
|
headers: {
|
||||||
|
...fetchOptions?.headers,
|
||||||
|
'Content-Type': 'application/json',
|
||||||
|
},
|
||||||
|
body: JSON.stringify({
|
||||||
|
query,
|
||||||
|
variables,
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
|
||||||
|
const json = await res.json()
|
||||||
|
if (json.errors) {
|
||||||
|
throw new FetcherError({
|
||||||
|
errors: json.errors ?? [{ message: 'Failed to fetch for API' }],
|
||||||
|
status: res.status,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
return { data: json.data, res }
|
||||||
|
}
|
||||||
|
|
||||||
|
export default fetchGraphqlApi
|
3
framework/local/api/utils/fetch.ts
Normal file
3
framework/local/api/utils/fetch.ts
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
import zeitFetch from '@vercel/fetch'
|
||||||
|
|
||||||
|
export default zeitFetch()
|
3
framework/local/auth/index.ts
Normal file
3
framework/local/auth/index.ts
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
export { default as useLogin } from './use-login'
|
||||||
|
export { default as useLogout } from './use-logout'
|
||||||
|
export { default as useSignup } from './use-signup'
|
16
framework/local/auth/use-login.tsx
Normal file
16
framework/local/auth/use-login.tsx
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
import useLogin, { UseLogin } from '@commerce/auth/use-login'
|
||||||
|
|
||||||
|
export default useLogin as UseLogin<typeof handler>
|
||||||
|
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher() {
|
||||||
|
return null
|
||||||
|
},
|
||||||
|
useHook: () => () => {
|
||||||
|
return async function () {}
|
||||||
|
},
|
||||||
|
}
|
17
framework/local/auth/use-logout.tsx
Normal file
17
framework/local/auth/use-logout.tsx
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
import useLogout, { UseLogout } from '@commerce/auth/use-logout'
|
||||||
|
|
||||||
|
export default useLogout as UseLogout<typeof handler>
|
||||||
|
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher() {
|
||||||
|
return null
|
||||||
|
},
|
||||||
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() =>
|
||||||
|
async () => {},
|
||||||
|
}
|
19
framework/local/auth/use-signup.tsx
Normal file
19
framework/local/auth/use-signup.tsx
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
import { useCallback } from 'react'
|
||||||
|
import useCustomer from '../customer/use-customer'
|
||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
import useSignup, { UseSignup } from '@commerce/auth/use-signup'
|
||||||
|
|
||||||
|
export default useSignup as UseSignup<typeof handler>
|
||||||
|
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher() {
|
||||||
|
return null
|
||||||
|
},
|
||||||
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() =>
|
||||||
|
() => {},
|
||||||
|
}
|
4
framework/local/cart/index.ts
Normal file
4
framework/local/cart/index.ts
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
export { default as useCart } from './use-cart'
|
||||||
|
export { default as useAddItem } from './use-add-item'
|
||||||
|
export { default as useRemoveItem } from './use-remove-item'
|
||||||
|
export { default as useUpdateItem } from './use-update-item'
|
17
framework/local/cart/use-add-item.tsx
Normal file
17
framework/local/cart/use-add-item.tsx
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import useAddItem, { UseAddItem } from '@commerce/cart/use-add-item'
|
||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
|
||||||
|
export default useAddItem as UseAddItem<typeof handler>
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher({ input, options, fetch }) {},
|
||||||
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() => {
|
||||||
|
return async function addItem() {
|
||||||
|
return {}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
42
framework/local/cart/use-cart.tsx
Normal file
42
framework/local/cart/use-cart.tsx
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
import { useMemo } from 'react'
|
||||||
|
import { SWRHook } from '@commerce/utils/types'
|
||||||
|
import useCart, { UseCart } from '@commerce/cart/use-cart'
|
||||||
|
|
||||||
|
export default useCart as UseCart<typeof handler>
|
||||||
|
|
||||||
|
export const handler: SWRHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher() {
|
||||||
|
return {
|
||||||
|
id: '',
|
||||||
|
createdAt: '',
|
||||||
|
currency: { code: '' },
|
||||||
|
taxesIncluded: '',
|
||||||
|
lineItems: [],
|
||||||
|
lineItemsSubtotalPrice: '',
|
||||||
|
subtotalPrice: 0,
|
||||||
|
totalPrice: 0,
|
||||||
|
}
|
||||||
|
},
|
||||||
|
useHook:
|
||||||
|
({ useData }) =>
|
||||||
|
(input) => {
|
||||||
|
return useMemo(
|
||||||
|
() =>
|
||||||
|
Object.create(
|
||||||
|
{},
|
||||||
|
{
|
||||||
|
isEmpty: {
|
||||||
|
get() {
|
||||||
|
return true
|
||||||
|
},
|
||||||
|
enumerable: true,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
),
|
||||||
|
[]
|
||||||
|
)
|
||||||
|
},
|
||||||
|
}
|
18
framework/local/cart/use-remove-item.tsx
Normal file
18
framework/local/cart/use-remove-item.tsx
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
import useRemoveItem, { UseRemoveItem } from '@commerce/cart/use-remove-item'
|
||||||
|
|
||||||
|
export default useRemoveItem as UseRemoveItem<typeof handler>
|
||||||
|
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher({ input, options, fetch }) {},
|
||||||
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() => {
|
||||||
|
return async function removeItem(input) {
|
||||||
|
return {}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
18
framework/local/cart/use-update-item.tsx
Normal file
18
framework/local/cart/use-update-item.tsx
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
import { MutationHook } from '@commerce/utils/types'
|
||||||
|
import useUpdateItem, { UseUpdateItem } from '@commerce/cart/use-update-item'
|
||||||
|
|
||||||
|
export default useUpdateItem as UseUpdateItem<any>
|
||||||
|
|
||||||
|
export const handler: MutationHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher({ input, options, fetch }) {},
|
||||||
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() => {
|
||||||
|
return async function addItem() {
|
||||||
|
return {}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
6
framework/local/commerce.config.json
Normal file
6
framework/local/commerce.config.json
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
{
|
||||||
|
"provider": "local",
|
||||||
|
"features": {
|
||||||
|
"wishlist": false
|
||||||
|
}
|
||||||
|
}
|
1
framework/local/customer/index.ts
Normal file
1
framework/local/customer/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export { default as useCustomer } from './use-customer'
|
15
framework/local/customer/use-customer.tsx
Normal file
15
framework/local/customer/use-customer.tsx
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
import { SWRHook } from '@commerce/utils/types'
|
||||||
|
import useCustomer, { UseCustomer } from '@commerce/customer/use-customer'
|
||||||
|
|
||||||
|
export default useCustomer as UseCustomer<typeof handler>
|
||||||
|
export const handler: SWRHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher({ input, options, fetch }) {},
|
||||||
|
useHook: () => () => {
|
||||||
|
return async function addItem() {
|
||||||
|
return {}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
241
framework/local/data.json
Normal file
241
framework/local/data.json
Normal file
@ -0,0 +1,241 @@
|
|||||||
|
{
|
||||||
|
"products": [
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjA=",
|
||||||
|
"name": "New Short Sleeve T-Shirt",
|
||||||
|
"vendor": "Next.js",
|
||||||
|
"path": "/new-short-sleeve-t-shirt",
|
||||||
|
"slug": "new-short-sleeve-t-shirt",
|
||||||
|
"price": { "value": 25, "currencyCode": "USD" },
|
||||||
|
"descriptionHtml": "<p><span>Show off your love for Next.js and Vercel with this unique, </span><strong>limited edition</strong><span> t-shirt. This design is part of a limited run, numbered drop at the June 2021 Next.js Conf. It features a unique, handcrafted triangle design. Get it while supplies last – only 200 of these shirts will be made! </span><strong>All proceeds will be donated to charity.</strong></p>",
|
||||||
|
"images": [
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-0.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-1.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-2.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-3.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"variants": [
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjAss=",
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"__typename": "MultipleChoiceOption",
|
||||||
|
"id": "asd",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "XL"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"id": "option-color",
|
||||||
|
"displayName": "Color",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "color",
|
||||||
|
"hexColors": ["#222"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "option-size",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "S"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "M"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "L"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjA=",
|
||||||
|
"name": "New Short Sleeve T-Shirt",
|
||||||
|
"vendor": "Next.js",
|
||||||
|
"path": "/new-short-sleeve-t-shirt",
|
||||||
|
"slug": "new-short-sleeve-t-shirt",
|
||||||
|
"price": { "value": 25, "currencyCode": "USD" },
|
||||||
|
"descriptionHtml": "<p><span>Show off your love for Next.js and Vercel with this unique, </span><strong>limited edition</strong><span> t-shirt. This design is part of a limited run, numbered drop at the June 2021 Next.js Conf. It features a unique, handcrafted triangle design. Get it while supplies last – only 200 of these shirts will be made! </span><strong>All proceeds will be donated to charity.</strong></p>",
|
||||||
|
"images": [
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-0.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-1.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-2.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-3.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"variants": [
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjAss=",
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"__typename": "MultipleChoiceOption",
|
||||||
|
"id": "asd",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "XL"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"id": "option-color",
|
||||||
|
"displayName": "Color",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "color",
|
||||||
|
"hexColors": ["#222"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "option-size",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "S"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "M"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "L"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjA=",
|
||||||
|
"name": "New Short Sleeve T-Shirt",
|
||||||
|
"vendor": "Next.js",
|
||||||
|
"path": "/new-short-sleeve-t-shirt",
|
||||||
|
"slug": "new-short-sleeve-t-shirt",
|
||||||
|
"price": { "value": 25, "currencyCode": "USD" },
|
||||||
|
"descriptionHtml": "<p><span>Show off your love for Next.js and Vercel with this unique, </span><strong>limited edition</strong><span> t-shirt. This design is part of a limited run, numbered drop at the June 2021 Next.js Conf. It features a unique, handcrafted triangle design. Get it while supplies last – only 200 of these shirts will be made! </span><strong>All proceeds will be donated to charity.</strong></p>",
|
||||||
|
"images": [
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-0.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-1.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-2.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "/assets/drop-shirt-3.png",
|
||||||
|
"altText": "Shirt",
|
||||||
|
"width": 1000,
|
||||||
|
"height": 1000
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"variants": [
|
||||||
|
{
|
||||||
|
"id": "Z2lkOi8vc2hvcGlmeS9Qcm9kdWN0LzU0NDczMjUwMjQ0MjAss=",
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"__typename": "MultipleChoiceOption",
|
||||||
|
"id": "asd",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "XL"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"options": [
|
||||||
|
{
|
||||||
|
"id": "option-color",
|
||||||
|
"displayName": "Color",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "color",
|
||||||
|
"hexColors": ["#222"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "option-size",
|
||||||
|
"displayName": "Size",
|
||||||
|
"values": [
|
||||||
|
{
|
||||||
|
"label": "S"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "M"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "L"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
11
framework/local/fetcher.ts
Normal file
11
framework/local/fetcher.ts
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
import { Fetcher } from '@commerce/utils/types'
|
||||||
|
|
||||||
|
export const fetcher: Fetcher = async () => {
|
||||||
|
console.log('FETCHER')
|
||||||
|
const res = await fetch('./data.json')
|
||||||
|
if (res.ok) {
|
||||||
|
const { data } = await res.json()
|
||||||
|
return data
|
||||||
|
}
|
||||||
|
throw res
|
||||||
|
}
|
32
framework/local/index.tsx
Normal file
32
framework/local/index.tsx
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
import * as React from 'react'
|
||||||
|
import { ReactNode } from 'react'
|
||||||
|
import { localProvider } from './provider'
|
||||||
|
import {
|
||||||
|
CommerceConfig,
|
||||||
|
CommerceProvider as CoreCommerceProvider,
|
||||||
|
useCommerce as useCoreCommerce,
|
||||||
|
} from '@commerce'
|
||||||
|
|
||||||
|
export const localConfig: CommerceConfig = {
|
||||||
|
locale: 'en-us',
|
||||||
|
cartCookie: 'session',
|
||||||
|
}
|
||||||
|
|
||||||
|
export function CommerceProvider({
|
||||||
|
children,
|
||||||
|
...config
|
||||||
|
}: {
|
||||||
|
children?: ReactNode
|
||||||
|
locale: string
|
||||||
|
} & Partial<CommerceConfig>) {
|
||||||
|
return (
|
||||||
|
<CoreCommerceProvider
|
||||||
|
provider={localProvider}
|
||||||
|
config={{ ...localConfig, ...config }}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
</CoreCommerceProvider>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useCommerce = () => useCoreCommerce()
|
8
framework/local/next.config.js
Normal file
8
framework/local/next.config.js
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
const commerce = require('./commerce.config.json')
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
commerce,
|
||||||
|
images: {
|
||||||
|
domains: ['localhost'],
|
||||||
|
},
|
||||||
|
}
|
2
framework/local/product/index.ts
Normal file
2
framework/local/product/index.ts
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
export { default as usePrice } from './use-price'
|
||||||
|
export { default as useSearch } from './use-search'
|
2
framework/local/product/use-price.tsx
Normal file
2
framework/local/product/use-price.tsx
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
export * from '@commerce/product/use-price'
|
||||||
|
export { default } from '@commerce/product/use-price'
|
17
framework/local/product/use-search.tsx
Normal file
17
framework/local/product/use-search.tsx
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import { SWRHook } from '@commerce/utils/types'
|
||||||
|
import useSearch, { UseSearch } from '@commerce/product/use-search'
|
||||||
|
export default useSearch as UseSearch<typeof handler>
|
||||||
|
|
||||||
|
export const handler: SWRHook<any> = {
|
||||||
|
fetchOptions: {
|
||||||
|
query: '',
|
||||||
|
},
|
||||||
|
async fetcher({ input, options, fetch }) {},
|
||||||
|
useHook: () => () => {
|
||||||
|
return {
|
||||||
|
data: {
|
||||||
|
products: [],
|
||||||
|
},
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
21
framework/local/provider.ts
Normal file
21
framework/local/provider.ts
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
import { fetcher } from './fetcher'
|
||||||
|
import { handler as useCart } from './cart/use-cart'
|
||||||
|
import { handler as useAddItem } from './cart/use-add-item'
|
||||||
|
import { handler as useUpdateItem } from './cart/use-update-item'
|
||||||
|
import { handler as useRemoveItem } from './cart/use-remove-item'
|
||||||
|
import { handler as useCustomer } from './customer/use-customer'
|
||||||
|
import { handler as useSearch } from './product/use-search'
|
||||||
|
import { handler as useLogin } from './auth/use-login'
|
||||||
|
import { handler as useLogout } from './auth/use-logout'
|
||||||
|
import { handler as useSignup } from './auth/use-signup'
|
||||||
|
|
||||||
|
export type Provider = typeof localProvider
|
||||||
|
export const localProvider = {
|
||||||
|
locale: 'en-us',
|
||||||
|
cartCookie: 'session',
|
||||||
|
fetcher: fetcher,
|
||||||
|
cart: { useCart, useAddItem, useUpdateItem, useRemoveItem },
|
||||||
|
customer: { useCustomer },
|
||||||
|
products: { useSearch },
|
||||||
|
auth: { useLogin, useLogout, useSignup },
|
||||||
|
}
|
13
framework/local/wishlist/use-add-item.tsx
Normal file
13
framework/local/wishlist/use-add-item.tsx
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
import { useCallback } from 'react'
|
||||||
|
|
||||||
|
export function emptyHook() {
|
||||||
|
const useEmptyHook = async (options = {}) => {
|
||||||
|
return useCallback(async function () {
|
||||||
|
return Promise.resolve()
|
||||||
|
}, [])
|
||||||
|
}
|
||||||
|
|
||||||
|
return useEmptyHook
|
||||||
|
}
|
||||||
|
|
||||||
|
export default emptyHook
|
17
framework/local/wishlist/use-remove-item.tsx
Normal file
17
framework/local/wishlist/use-remove-item.tsx
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
import { useCallback } from 'react'
|
||||||
|
|
||||||
|
type Options = {
|
||||||
|
includeProducts?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
export function emptyHook(options?: Options) {
|
||||||
|
const useEmptyHook = async ({ id }: { id: string | number }) => {
|
||||||
|
return useCallback(async function () {
|
||||||
|
return Promise.resolve()
|
||||||
|
}, [])
|
||||||
|
}
|
||||||
|
|
||||||
|
return useEmptyHook
|
||||||
|
}
|
||||||
|
|
||||||
|
export default emptyHook
|
43
framework/local/wishlist/use-wishlist.tsx
Normal file
43
framework/local/wishlist/use-wishlist.tsx
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
import { HookFetcher } from '@commerce/utils/types'
|
||||||
|
import type { Product } from '@commerce/types/product'
|
||||||
|
|
||||||
|
const defaultOpts = {}
|
||||||
|
|
||||||
|
export type Wishlist = {
|
||||||
|
items: [
|
||||||
|
{
|
||||||
|
product_id: number
|
||||||
|
variant_id: number
|
||||||
|
id: number
|
||||||
|
product: Product
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface UseWishlistOptions {
|
||||||
|
includeProducts?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface UseWishlistInput extends UseWishlistOptions {
|
||||||
|
customerId?: number
|
||||||
|
}
|
||||||
|
|
||||||
|
export const fetcher: HookFetcher<Wishlist | null, UseWishlistInput> = () => {
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
export function extendHook(
|
||||||
|
customFetcher: typeof fetcher,
|
||||||
|
// swrOptions?: SwrOptions<Wishlist | null, UseWishlistInput>
|
||||||
|
swrOptions?: any
|
||||||
|
) {
|
||||||
|
const useWishlist = ({ includeProducts }: UseWishlistOptions = {}) => {
|
||||||
|
return { data: null }
|
||||||
|
}
|
||||||
|
|
||||||
|
useWishlist.extend = extendHook
|
||||||
|
|
||||||
|
return useWishlist
|
||||||
|
}
|
||||||
|
|
||||||
|
export default extendHook(fetcher)
|
@ -18,7 +18,9 @@ export const handler: MutationHook<LogoutHook> = {
|
|||||||
})
|
})
|
||||||
return null
|
return null
|
||||||
},
|
},
|
||||||
useHook: ({ fetch }) => () => {
|
useHook:
|
||||||
|
({ fetch }) =>
|
||||||
|
() => {
|
||||||
const { mutate } = useCustomer()
|
const { mutate } = useCustomer()
|
||||||
|
|
||||||
return useCallback(
|
return useCallback(
|
||||||
|
11033
package-lock.json
generated
Normal file
11033
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load Diff
@ -29,6 +29,7 @@
|
|||||||
"dot-object": "^2.1.4",
|
"dot-object": "^2.1.4",
|
||||||
"email-validator": "^2.0.4",
|
"email-validator": "^2.0.4",
|
||||||
"immutability-helper": "^3.1.1",
|
"immutability-helper": "^3.1.1",
|
||||||
|
"isomorphic-unfetch": "^3.1.0",
|
||||||
"js-cookie": "^2.2.1",
|
"js-cookie": "^2.2.1",
|
||||||
"keen-slider": "^5.4.1",
|
"keen-slider": "^5.4.1",
|
||||||
"lodash.debounce": "^4.0.8",
|
"lodash.debounce": "^4.0.8",
|
||||||
|
@ -8,6 +8,7 @@ import { Text } from '@components/ui'
|
|||||||
import { Layout } from '@components/common'
|
import { Layout } from '@components/common'
|
||||||
import getSlug from '@lib/get-slug'
|
import getSlug from '@lib/get-slug'
|
||||||
import { missingLocaleInPages } from '@lib/usage-warns'
|
import { missingLocaleInPages } from '@lib/usage-warns'
|
||||||
|
import type { Page } from '@commerce/types/page'
|
||||||
|
|
||||||
export async function getStaticProps({
|
export async function getStaticProps({
|
||||||
preview,
|
preview,
|
||||||
@ -22,7 +23,9 @@ export async function getStaticProps({
|
|||||||
const { categories } = await siteInfoPromise
|
const { categories } = await siteInfoPromise
|
||||||
const path = params?.pages.join('/')
|
const path = params?.pages.join('/')
|
||||||
const slug = locale ? `${locale}/${path}` : path
|
const slug = locale ? `${locale}/${path}` : path
|
||||||
const pageItem = pages.find((p) => (p.url ? getSlug(p.url) === slug : false))
|
const pageItem = pages.find((p: Page) =>
|
||||||
|
p.url ? getSlug(p.url) === slug : false
|
||||||
|
)
|
||||||
const data =
|
const data =
|
||||||
pageItem &&
|
pageItem &&
|
||||||
(await commerce.getPage({
|
(await commerce.getPage({
|
||||||
@ -45,7 +48,7 @@ export async function getStaticProps({
|
|||||||
|
|
||||||
export async function getStaticPaths({ locales }: GetStaticPathsContext) {
|
export async function getStaticPaths({ locales }: GetStaticPathsContext) {
|
||||||
const config = { locales }
|
const config = { locales }
|
||||||
const { pages } = await commerce.getAllPages({ config })
|
const { pages }: { pages: Page[] } = await commerce.getAllPages({ config })
|
||||||
const [invalidPaths, log] = missingLocaleInPages()
|
const [invalidPaths, log] = missingLocaleInPages()
|
||||||
const paths = pages
|
const paths = pages
|
||||||
.map((page) => page.url)
|
.map((page) => page.url)
|
||||||
|
@ -12,6 +12,13 @@ export async function getStaticProps({
|
|||||||
locale,
|
locale,
|
||||||
locales,
|
locales,
|
||||||
}: GetStaticPropsContext) {
|
}: GetStaticPropsContext) {
|
||||||
|
// Disabling page if Feature is not available
|
||||||
|
if (!process.env.COMMERCE_CART_ENABLED) {
|
||||||
|
return {
|
||||||
|
notFound: true,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const config = { locale, locales }
|
const config = { locale, locales }
|
||||||
const pagesPromise = commerce.getAllPages({ config, preview })
|
const pagesPromise = commerce.getAllPages({ config, preview })
|
||||||
const siteInfoPromise = commerce.getSiteInfo({ config, preview })
|
const siteInfoPromise = commerce.getSiteInfo({ config, preview })
|
||||||
@ -79,7 +86,7 @@ export default function Cart() {
|
|||||||
<Text variant="pageHeading">My Cart</Text>
|
<Text variant="pageHeading">My Cart</Text>
|
||||||
<Text variant="sectionHeading">Review your Order</Text>
|
<Text variant="sectionHeading">Review your Order</Text>
|
||||||
<ul className="py-6 space-y-6 sm:py-0 sm:space-y-0 sm:divide-y sm:divide-accent-2 border-b border-accent-2">
|
<ul className="py-6 space-y-6 sm:py-0 sm:space-y-0 sm:divide-y sm:divide-accent-2 border-b border-accent-2">
|
||||||
{data!.lineItems.map((item) => (
|
{data!.lineItems.map((item: any) => (
|
||||||
<CartItem
|
<CartItem
|
||||||
key={item.id}
|
key={item.id}
|
||||||
item={item}
|
item={item}
|
||||||
|
@ -39,7 +39,7 @@ export default function Home({
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Grid variant="filled">
|
<Grid variant="filled">
|
||||||
{products.slice(0, 3).map((product, i) => (
|
{products.slice(0, 3).map((product: any, i: number) => (
|
||||||
<ProductCard
|
<ProductCard
|
||||||
key={product.id}
|
key={product.id}
|
||||||
product={product}
|
product={product}
|
||||||
@ -51,7 +51,7 @@ export default function Home({
|
|||||||
))}
|
))}
|
||||||
</Grid>
|
</Grid>
|
||||||
<Marquee variant="secondary">
|
<Marquee variant="secondary">
|
||||||
{products.slice(0, 3).map((product, i) => (
|
{products.slice(0, 3).map((product: any, i: number) => (
|
||||||
<ProductCard key={product.id} product={product} variant="slim" />
|
<ProductCard key={product.id} product={product} variant="slim" />
|
||||||
))}
|
))}
|
||||||
</Marquee>
|
</Marquee>
|
||||||
@ -60,7 +60,7 @@ export default function Home({
|
|||||||
description="Cupcake ipsum dolor sit amet lemon drops pastry cotton candy. Sweet carrot cake macaroon bonbon croissant fruitcake jujubes macaroon oat cake. Soufflé bonbon caramels jelly beans. Tiramisu sweet roll cheesecake pie carrot cake. "
|
description="Cupcake ipsum dolor sit amet lemon drops pastry cotton candy. Sweet carrot cake macaroon bonbon croissant fruitcake jujubes macaroon oat cake. Soufflé bonbon caramels jelly beans. Tiramisu sweet roll cheesecake pie carrot cake. "
|
||||||
/>
|
/>
|
||||||
<Grid layout="B" variant="filled">
|
<Grid layout="B" variant="filled">
|
||||||
{products.slice(0, 3).map((product, i) => (
|
{products.slice(0, 3).map((product: any, i: number) => (
|
||||||
<ProductCard
|
<ProductCard
|
||||||
key={product.id}
|
key={product.id}
|
||||||
product={product}
|
product={product}
|
||||||
@ -72,7 +72,7 @@ export default function Home({
|
|||||||
))}
|
))}
|
||||||
</Grid>
|
</Grid>
|
||||||
<Marquee>
|
<Marquee>
|
||||||
{products.slice(3).map((product, i) => (
|
{products.slice(3).map((product: any, i: number) => (
|
||||||
<ProductCard key={product.id} product={product} variant="slim" />
|
<ProductCard key={product.id} product={product} variant="slim" />
|
||||||
))}
|
))}
|
||||||
</Marquee>
|
</Marquee>
|
||||||
|
@ -55,12 +55,12 @@ export async function getStaticPaths({ locales }: GetStaticPathsContext) {
|
|||||||
paths: locales
|
paths: locales
|
||||||
? locales.reduce<string[]>((arr, locale) => {
|
? locales.reduce<string[]>((arr, locale) => {
|
||||||
// Add a product path for every locale
|
// Add a product path for every locale
|
||||||
products.forEach((product) => {
|
products.forEach((product: any) => {
|
||||||
arr.push(`/${locale}/product${product.path}`)
|
arr.push(`/${locale}/product${product.path}`)
|
||||||
})
|
})
|
||||||
return arr
|
return arr
|
||||||
}, [])
|
}, [])
|
||||||
: products.map((product) => `/product${product.path}`),
|
: products.map((product: any) => `/product${product.path}`),
|
||||||
fallback: 'blocking',
|
fallback: 'blocking',
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -22,8 +22,8 @@
|
|||||||
"@components/*": ["components/*"],
|
"@components/*": ["components/*"],
|
||||||
"@commerce": ["framework/commerce"],
|
"@commerce": ["framework/commerce"],
|
||||||
"@commerce/*": ["framework/commerce/*"],
|
"@commerce/*": ["framework/commerce/*"],
|
||||||
"@framework": ["framework/shopify"],
|
"@framework": ["framework/local"],
|
||||||
"@framework/*": ["framework/shopify/*"]
|
"@framework/*": ["framework/local/*"]
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"include": ["next-env.d.ts", "**/*.d.ts", "**/*.ts", "**/*.tsx", "**/*.js"],
|
"include": ["next-env.d.ts", "**/*.d.ts", "**/*.ts", "**/*.tsx", "**/*.js"],
|
||||||
|
13
yarn.lock
13
yarn.lock
@ -3804,6 +3804,14 @@ isomorphic-form-data@2.0.0:
|
|||||||
dependencies:
|
dependencies:
|
||||||
form-data "^2.3.2"
|
form-data "^2.3.2"
|
||||||
|
|
||||||
|
isomorphic-unfetch@^3.1.0:
|
||||||
|
version "3.1.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/isomorphic-unfetch/-/isomorphic-unfetch-3.1.0.tgz#87341d5f4f7b63843d468438128cb087b7c3e98f"
|
||||||
|
integrity sha512-geDJjpoZ8N0kWexiwkX8F9NkTsXhetLPVbZFQ+JTW239QNOwvB0gniuR1Wc6f0AMTn7/mFGyXvHTifrCp/GH8Q==
|
||||||
|
dependencies:
|
||||||
|
node-fetch "^2.6.1"
|
||||||
|
unfetch "^4.2.0"
|
||||||
|
|
||||||
isomorphic-ws@4.0.1:
|
isomorphic-ws@4.0.1:
|
||||||
version "4.0.1"
|
version "4.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/isomorphic-ws/-/isomorphic-ws-4.0.1.tgz#55fd4cd6c5e6491e76dc125938dd863f5cd4f2dc"
|
resolved "https://registry.yarnpkg.com/isomorphic-ws/-/isomorphic-ws-4.0.1.tgz#55fd4cd6c5e6491e76dc125938dd863f5cd4f2dc"
|
||||||
@ -6648,6 +6656,11 @@ unc-path-regex@^0.1.2:
|
|||||||
resolved "https://registry.yarnpkg.com/unc-path-regex/-/unc-path-regex-0.1.2.tgz#e73dd3d7b0d7c5ed86fbac6b0ae7d8c6a69d50fa"
|
resolved "https://registry.yarnpkg.com/unc-path-regex/-/unc-path-regex-0.1.2.tgz#e73dd3d7b0d7c5ed86fbac6b0ae7d8c6a69d50fa"
|
||||||
integrity sha1-5z3T17DXxe2G+6xrCufYxqadUPo=
|
integrity sha1-5z3T17DXxe2G+6xrCufYxqadUPo=
|
||||||
|
|
||||||
|
unfetch@^4.2.0:
|
||||||
|
version "4.2.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/unfetch/-/unfetch-4.2.0.tgz#7e21b0ef7d363d8d9af0fb929a5555f6ef97a3be"
|
||||||
|
integrity sha512-F9p7yYCn6cIW9El1zi0HI6vqpeIvBsr3dSuRO6Xuppb1u5rXpCPmMvLSyECLhybr9isec8Ohl0hPekMVrEinDA==
|
||||||
|
|
||||||
uniq@^1.0.1:
|
uniq@^1.0.1:
|
||||||
version "1.0.1"
|
version "1.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/uniq/-/uniq-1.0.1.tgz#b31c5ae8254844a3a8281541ce2b04b865a734ff"
|
resolved "https://registry.yarnpkg.com/uniq/-/uniq-1.0.1.tgz#b31c5ae8254844a3a8281541ce2b04b865a734ff"
|
||||||
|
Loading…
x
Reference in New Issue
Block a user