Add checkout & customer types

This commit is contained in:
Catalin Pinte 2022-09-19 11:06:22 +03:00
parent 5b6e50e7d0
commit 6bdfe56e9f
11 changed files with 101 additions and 92 deletions

View File

@ -169,7 +169,7 @@ export interface CartItemBody {
} }
/** /**
* Hooks for add, update & remove items from the cart. * Cart Hooks for add, update and remove items from the cart
*/ */
export type CartHooks = { export type CartHooks = {
getCart: GetCartHook getCart: GetCartHook
@ -178,9 +178,6 @@ export type CartHooks = {
removeItem: RemoveItemHook removeItem: RemoveItemHook
} }
/**
* Hook for getting the cart.
*/
export interface GetCartHook { export interface GetCartHook {
data: Cart | null data: Cart | null
input: {} input: {}
@ -188,9 +185,6 @@ export interface GetCartHook {
swrState: { isEmpty: boolean } swrState: { isEmpty: boolean }
} }
/**
* Hook for adding an item to the cart.
*/
export interface AddItemHook { export interface AddItemHook {
data: Cart data: Cart
input?: CartItemBody input?: CartItemBody
@ -199,9 +193,6 @@ export interface AddItemHook {
actionInput: CartItemBody actionInput: CartItemBody
} }
/**
* Hook for updating an item in the cart.
*/
export interface UpdateItemHook { export interface UpdateItemHook {
data: Cart | null | undefined data: Cart | null | undefined
input: { item?: LineItem; wait?: number } input: { item?: LineItem; wait?: number }
@ -210,9 +201,6 @@ export interface UpdateItemHook {
actionInput: CartItemBody & { id: string } actionInput: CartItemBody & { id: string }
} }
/**
* Hook for removing an item from the cart.
*/
export interface RemoveItemHook { export interface RemoveItemHook {
data: Cart | null | undefined data: Cart | null | undefined
input: { item?: LineItem } input: { item?: LineItem }
@ -222,7 +210,7 @@ export interface RemoveItemHook {
} }
/** /**
* Cart API Schema. * Cart API endpoitns & handlers for add, update and remove items from the cart
*/ */
export type CartSchema = { export type CartSchema = {
endpoint: { endpoint: {
@ -231,9 +219,6 @@ export type CartSchema = {
} }
} }
/**
* API Handlers for adding, updating & removing items from the cart.
*/
export type CartHandlers = { export type CartHandlers = {
getCart: GetCartHandler getCart: GetCartHandler
addItem: AddItemHandler addItem: AddItemHandler
@ -241,31 +226,19 @@ export type CartHandlers = {
removeItem: RemoveItemHandler removeItem: RemoveItemHandler
} }
/**
* API Handler for getting the cart.
*/
export type GetCartHandler = GetCartHook & { export type GetCartHandler = GetCartHook & {
body: { cartId?: string } body: { cartId?: string }
} }
/**
* API Handler for adding an item to the cart.
*/
export type AddItemHandler = AddItemHook & { export type AddItemHandler = AddItemHook & {
body: { cartId: string } body: { cartId: string }
} }
/**
* API Handler for updating an item in the cart.
*/
export type UpdateItemHandler = UpdateItemHook & { export type UpdateItemHandler = UpdateItemHook & {
data: Cart data: Cart
body: { cartId: string } body: { cartId: string }
} }
/**
* API Handler for removing an item from the cart.
*/
export type RemoveItemHandler = RemoveItemHook & { export type RemoveItemHandler = RemoveItemHook & {
body: { cartId: string } body: { cartId: string }
} }

View File

@ -1,13 +1,53 @@
import type { UseSubmitCheckout } from '../checkout/use-submit-checkout' import type { UseSubmitCheckout } from '../checkout/use-submit-checkout'
import type { Address, AddressFields } from './customer/address' import type { Address, AddressFields } from './customer/address'
import type { Card, CardFields } from './customer/card' import type { Card, CardFields } from './customer/card'
import type { LineItem } from './cart'
// Index export type Checkout = {
export type Checkout = any /**
* Indicates if the payment has been submitted.
*/
hasPayment: boolean
/**
* Indicates if the checkout has shipping information collected.
*/
hasShipping: boolean
/**
* The unique identifier for the address that the customer has selected for shipping.
*/
addressId: string
/**
* The list of payments that the customer has selected for the checkout.
*/
payments?: Card[]
/**
* The unique identifier of the card that the customer has selected for payment.
*/
cardId?: string
/**
* List of items in the checkout.
*/
lineItems?: LineItem[]
}
export type CheckoutBody = any export type CheckoutBody = {
/**
* The unique identifier for the cart.
*/
cartId?: string
/**
* The Card information.
* @see @vercel/commerce/types/customer/card/CardFields
*/
card: CardFields
/**
* The Address information.
* @see AddressFields
*/
address: AddressFields
}
export type CheckoutTypes = { export interface CheckoutTypes {
card?: Card | CardFields card?: Card | CardFields
address?: Address | AddressFields address?: Address | AddressFields
checkout?: Checkout checkout?: Checkout
@ -15,7 +55,7 @@ export type CheckoutTypes = {
hasShipping?: boolean hasShipping?: boolean
} }
export type SubmitCheckoutHook = { export interface SubmitCheckoutHook {
data: Checkout data: Checkout
input?: CheckoutBody input?: CheckoutBody
fetcherInput: CheckoutBody fetcherInput: CheckoutBody
@ -23,7 +63,7 @@ export type SubmitCheckoutHook = {
actionInput: CheckoutBody actionInput: CheckoutBody
} }
export type GetCheckoutHook = { export interface GetCheckoutHook {
data: Checkout | null | undefined data: Checkout | null | undefined
input: {} input: {}
fetcherInput: { cartId?: string } fetcherInput: { cartId?: string }
@ -31,7 +71,7 @@ export type GetCheckoutHook = {
mutations: { submit: UseSubmitCheckout } mutations: { submit: UseSubmitCheckout }
} }
export type CheckoutHooks = { export interface CheckoutHooks {
submitCheckout?: SubmitCheckoutHook submitCheckout?: SubmitCheckoutHook
getCheckout: GetCheckoutHook getCheckout: GetCheckoutHook
} }

View File

@ -50,8 +50,9 @@ export interface AddressFields {
} }
/** /**
* Hook for getting a customer's addresses. * Hooks for managing a customer's addresses.
*/ */
export interface GetAddressesHook { export interface GetAddressesHook {
data: Address[] | null data: Address[] | null
input: {} input: {}
@ -59,9 +60,6 @@ export interface GetAddressesHook {
swrState: { isEmpty: boolean } swrState: { isEmpty: boolean }
} }
/**
* Hook for adding an address to a customer's account.
*/
export interface AddItemHook { export interface AddItemHook {
data: Address data: Address
input?: AddressFields input?: AddressFields
@ -70,9 +68,6 @@ export interface AddItemHook {
actionInput: AddressFields actionInput: AddressFields
} }
/**
* Hook for updating an address to a customer's account.
*/
export interface UpdateItemHook { export interface UpdateItemHook {
data: Address | null data: Address | null
input: { item?: AddressFields; wait?: number } input: { item?: AddressFields; wait?: number }
@ -81,9 +76,6 @@ export interface UpdateItemHook {
actionInput: AddressFields & { id: string } actionInput: AddressFields & { id: string }
} }
/**
* Hook for deliting an address to a customer's account.
*/
export interface RemoveItemHook { export interface RemoveItemHook {
data: Address | null | undefined data: Address | null | undefined
input: { item?: Address } input: { item?: Address }
@ -92,9 +84,6 @@ export interface RemoveItemHook {
actionInput: { id: string } actionInput: { id: string }
} }
/**
* Hooks for managing a customer's addresses.
*/
export interface CustomerAddressHooks { export interface CustomerAddressHooks {
getAddresses: GetAddressesHook getAddresses: GetAddressesHook
addItem: AddItemHook addItem: AddItemHook

View File

@ -67,8 +67,9 @@ export interface CardFields {
} }
/** /**
* Hook for getting a customer's cards. * Hooks for managing a customer's cards.
*/ */
export interface GetCardsHook { export interface GetCardsHook {
data: Card[] | null data: Card[] | null
input: {} input: {}
@ -76,9 +77,6 @@ export interface GetCardsHook {
swrState: { isEmpty: boolean } swrState: { isEmpty: boolean }
} }
/**
* Hook for adding a card to a customer's account.
*/
export interface AddItemHook { export interface AddItemHook {
data: Card data: Card
input?: CardFields input?: CardFields
@ -87,9 +85,6 @@ export interface AddItemHook {
actionInput: CardFields actionInput: CardFields
} }
/**
* Hook for updating a card from a customer's account.
*/
export interface UpdateItemHook { export interface UpdateItemHook {
data: Card | null | undefined data: Card | null | undefined
input: { item?: CardFields; wait?: number } input: { item?: CardFields; wait?: number }
@ -98,9 +93,6 @@ export interface UpdateItemHook {
actionInput: CardFields & { id: string } actionInput: CardFields & { id: string }
} }
/**
* Hook for removing a card from a customer's account.
*/
export interface RemoveItemHook { export interface RemoveItemHook {
data: Card | null | undefined data: Card | null | undefined
input: { item?: Card } input: { item?: Card }
@ -109,9 +101,6 @@ export interface RemoveItemHook {
actionInput: { id: string } actionInput: { id: string }
} }
/**
* Hooks for add, update & remove items from the cart.
*/
export interface CustomerCardHooks { export interface CustomerCardHooks {
getCards: GetCardsHook getCards: GetCardsHook
addItem: AddItemHook addItem: AddItemHook
@ -120,7 +109,7 @@ export interface CustomerCardHooks {
} }
/** /**
* Customer card API handler * Customer card API handlers.
*/ */
export type AddItemHandler = AddItemHook & { export type AddItemHandler = AddItemHook & {
body: { cartId: string } body: { cartId: string }
@ -135,9 +124,6 @@ export type RemoveItemHandler = RemoveItemHook & {
body: { cartId: string } body: { cartId: string }
} }
/**
* Customer card API handlers.
*/
export type CustomerCardHandlers = { export type CustomerCardHandlers = {
getCards: GetCardsHook getCards: GetCardsHook
addItem: AddItemHandler addItem: AddItemHandler
@ -145,9 +131,6 @@ export type CustomerCardHandlers = {
removeItem: RemoveItemHandler removeItem: RemoveItemHandler
} }
/**
* Customer card API endpoints.
*/
export type CustomerCardSchema = { export type CustomerCardSchema = {
endpoint: { endpoint: {
options: {} options: {}

View File

@ -7,6 +7,7 @@ export interface ProductPrice {
value: number value: number
/** /**
* The currency code for the price. This is a 3-letter ISO 4217 code. * The currency code for the price. This is a 3-letter ISO 4217 code.
* @example USD
*/ */
currencyCode?: 'USD' | 'EUR' | 'ARS' | 'GBP' | string currencyCode?: 'USD' | 'EUR' | 'ARS' | 'GBP' | string
/** /**
@ -23,10 +24,12 @@ export interface ProductOption {
id: string id: string
/** /**
* The product options name. * The product options name.
* @example `Color` or `Size`
*/ */
displayName: string displayName: string
/** /**
* List of option values. * List of option values.
* @example `["Red", "Green", "Blue"]`
*/ */
values: ProductOptionValues[] values: ProductOptionValues[]
} }
@ -156,6 +159,9 @@ export interface SearchProductsBody {
locale?: string locale?: string
} }
/**
* Fetches a list of products based on the given search criteria.
*/
export interface SearchProductsHook { export interface SearchProductsHook {
data: { data: {
/** /**
@ -175,6 +181,7 @@ export interface SearchProductsHook {
/** /**
* Product API schema * Product API schema
*/ */
export interface ProductsSchema { export interface ProductsSchema {
endpoint: { endpoint: {
options: {} options: {}
@ -184,6 +191,10 @@ export interface ProductsSchema {
} }
} }
/**
* Product operations
*/
export interface GetAllProductPathsOperation { export interface GetAllProductPathsOperation {
data: { products: Pick<Product, 'path'>[] } data: { products: Pick<Product, 'path'>[] }
variables: { first?: number } variables: { first?: number }
@ -199,11 +210,6 @@ export interface GetAllProductsOperation {
} }
export interface GetProductOperation { export interface GetProductOperation {
/**
* Returned data from the operation.
*/
data: { product?: Product } data: { product?: Product }
/**
* The variables to pass to the operation.*/
variables: { path: string; slug?: never } | { path?: never; slug: string } variables: { path: string; slug?: never } | { path?: never; slug: string }
} }

View File

@ -30,23 +30,22 @@ export interface Wishlist {
items: WishlistItem[] items: WishlistItem[]
/** /**
* TODO: Spree provider specific * Some providers require a token to add an item to a wishlist
*/ */
token?: string token?: string
} }
export interface WishlistItemBody { export interface WishlistItemBody {
/** /**
* The product's variant id. * The unique identifier for the product variant to associate with the wishlist.
*/ */
variantId: string variantId: string
/** /**
* The product's ID. * The unique identifier for the product to associate with the wishlist.
*/ */
productId: string productId: string
/** /**
* TODO: Spree provider specific * Some providers require to provide a token to make a request
*/ */
wishlistToken?: string wishlistToken?: string
} }

View File

@ -39,6 +39,8 @@ const getCheckout: CheckoutEndpoint['handlers']['getCheckout'] = async ({
data: { data: {
hasPayment: payments.length > 0, hasPayment: payments.length > 0,
hasShipping: Boolean(address), hasShipping: Boolean(address),
addressId: address,
cardId: payments[0]?.ID,
}, },
errors: [], errors: [],
}) })

View File

@ -2,7 +2,9 @@ import type { GetCheckoutHook } from '@vercel/commerce/types/checkout'
import { useMemo } from 'react' import { useMemo } from 'react'
import { SWRHook } from '@vercel/commerce/utils/types' import { SWRHook } from '@vercel/commerce/utils/types'
import useCheckout, { UseCheckout } from '@vercel/commerce/checkout/use-checkout' import useCheckout, {
UseCheckout,
} from '@vercel/commerce/checkout/use-checkout'
import useSubmitCheckout from './use-submit-checkout' import useSubmitCheckout from './use-submit-checkout'
export default useCheckout as UseCheckout<typeof handler> export default useCheckout as UseCheckout<typeof handler>
@ -24,7 +26,7 @@ export const handler: SWRHook<GetCheckoutHook> = {
Object.create(response, { Object.create(response, {
isEmpty: { isEmpty: {
get() { get() {
return (response.data?.lineItems?.length ?? 0) <= 0 return response.data?.lineItems?.length ?? 0
}, },
enumerable: true, enumerable: true,
}, },

View File

@ -13,7 +13,13 @@ import {
import fetchGraphqlApi from './utils/fetch-graphql-api' import fetchGraphqlApi from './utils/fetch-graphql-api'
import * as operations from './operations' import getAllPages from './operations/get-all-pages'
import getPage from './operations/get-page'
import getAllProducts from './operations/get-all-products'
import getAllProductPaths from './operations/get-all-product-paths'
import getProduct from './operations/get-product'
import getSiteInfo from './operations/get-site-info'
import login from './operations/login'
if (!API_URL) { if (!API_URL) {
throw new Error( throw new Error(
@ -41,7 +47,15 @@ const config: ShopifyConfig = {
export const provider = { export const provider = {
config, config,
operations, operations: {
login,
getSiteInfo,
getAllPages,
getPage,
getAllProducts,
getAllProductPaths,
getProduct,
},
} }
export type Provider = typeof provider export type Provider = typeof provider

View File

@ -1,7 +0,0 @@
export { default as getAllPages } from './get-all-pages'
export { default as getPage } from './get-page'
export { default as getAllProducts } from './get-all-products'
export { default as getAllProductPaths } from './get-all-product-paths'
export { default as getProduct } from './get-product'
export { default as getSiteInfo } from './get-site-info'
export { default as login } from './login'

12
pnpm-lock.yaml generated
View File

@ -677,6 +677,7 @@ importers:
tabbable: ^5.2.1 tabbable: ^5.2.1
tailwindcss: ^3.0.13 tailwindcss: ^3.0.13
typescript: 4.7.4 typescript: 4.7.4
zod: ^3.19.0
dependencies: dependencies:
'@radix-ui/react-dropdown-menu': 1.0.0_7ey2zzynotv32rpkwno45fsx4e '@radix-ui/react-dropdown-menu': 1.0.0_7ey2zzynotv32rpkwno45fsx4e
'@react-spring/web': 9.5.4_biqbaboplfbrettd7655fr4n2y '@react-spring/web': 9.5.4_biqbaboplfbrettd7655fr4n2y
@ -710,7 +711,8 @@ importers:
react-merge-refs: 2.0.1 react-merge-refs: 2.0.1
react-use-measure: 2.1.1_biqbaboplfbrettd7655fr4n2y react-use-measure: 2.1.1_biqbaboplfbrettd7655fr4n2y
tabbable: 5.3.3 tabbable: 5.3.3
tailwindcss: 3.1.8 tailwindcss: 3.1.8_postcss@8.4.16
zod: 3.19.1
devDependencies: devDependencies:
'@next/bundle-analyzer': 12.3.0 '@next/bundle-analyzer': 12.3.0
'@types/body-scroll-lock': 3.1.0 '@types/body-scroll-lock': 3.1.0
@ -9044,10 +9046,12 @@ packages:
resolution: {integrity: sha512-QD9qKY3StfbZqWOPLp0++pOrAVb/HbUi5xCc8cUo4XjP19808oaMiDzn0leBY5mCespIBM0CIZePzZjgzR83kA==} resolution: {integrity: sha512-QD9qKY3StfbZqWOPLp0++pOrAVb/HbUi5xCc8cUo4XjP19808oaMiDzn0leBY5mCespIBM0CIZePzZjgzR83kA==}
dev: false dev: false
/tailwindcss/3.1.8: /tailwindcss/3.1.8_postcss@8.4.16:
resolution: {integrity: sha512-YSneUCZSFDYMwk+TGq8qYFdCA3yfBRdBlS7txSq0LUmzyeqRe3a8fBQzbz9M3WS/iFT4BNf/nmw9mEzrnSaC0g==} resolution: {integrity: sha512-YSneUCZSFDYMwk+TGq8qYFdCA3yfBRdBlS7txSq0LUmzyeqRe3a8fBQzbz9M3WS/iFT4BNf/nmw9mEzrnSaC0g==}
engines: {node: '>=12.13.0'} engines: {node: '>=12.13.0'}
hasBin: true hasBin: true
peerDependencies:
postcss: ^8.0.9
dependencies: dependencies:
arg: 5.0.2 arg: 5.0.2
chokidar: 3.5.3 chokidar: 3.5.3
@ -9844,3 +9848,7 @@ packages:
resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==}
engines: {node: '>=10'} engines: {node: '>=10'}
dev: true dev: true
/zod/3.19.1:
resolution: {integrity: sha512-LYjZsEDhCdYET9ikFu6dVPGp2YH9DegXjdJToSzD9rO6fy4qiRYFoyEYwps88OseJlPyl2NOe2iJuhEhL7IpEA==}
dev: false