@ekomerc/storefront 0.1.0

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.
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sources":["../src/cache.ts","../src/storage.ts","../src/account.ts","../src/auth.ts","../src/tracking-attribution.ts","../src/url.ts","../src/cart.ts","../src/categories.ts","../src/checkout.ts","../src/collections.ts","../src/graphql-client.ts","../src/payments.ts","../src/products.ts","../src/analytics.ts","../src/shipping.ts","../src/client.ts"],"sourcesContent":["interface CacheEntry<T> {\n value: T;\n expiresAt: number;\n}\n\nexport interface QueryCache {\n get<T>(key: string): T | null;\n set<T>(key: string, value: T, ttl: number): void;\n clear(): void;\n}\n\nexport function createQueryCache(): QueryCache {\n const cache = new Map<string, CacheEntry<unknown>>();\n\n return {\n get<T>(key: string): T | null {\n const entry = cache.get(key);\n if (!entry) return null;\n if (Date.now() > entry.expiresAt) {\n cache.delete(key);\n return null;\n }\n return entry.value as T;\n },\n\n set<T>(key: string, value: T, ttl: number): void {\n cache.set(key, {\n value,\n expiresAt: Date.now() + ttl,\n });\n },\n\n clear(): void {\n cache.clear();\n },\n };\n}\n","import type { StorageAdapter } from \"./types.ts\";\n\nexport const CART_TOKEN_KEY = \"ekomerc_cart_token\";\nexport const CUSTOMER_TOKEN_KEY = \"ekomerc_customer_token\";\n\n/**\n * localStorage adapter for browser environments\n */\nexport function createLocalStorageAdapter(): StorageAdapter {\n return {\n get(key: string): string | null {\n if (typeof localStorage === \"undefined\") return null;\n return localStorage.getItem(key);\n },\n set(key: string, value: string): void {\n if (typeof localStorage === \"undefined\") return;\n localStorage.setItem(key, value);\n },\n remove(key: string): void {\n if (typeof localStorage === \"undefined\") return;\n localStorage.removeItem(key);\n },\n };\n}\n\n/**\n * In-memory adapter for SSR or testing\n */\nexport function createMemoryAdapter(): StorageAdapter {\n const store = new Map<string, string>();\n\n return {\n get(key: string): string | null {\n return store.get(key) ?? null;\n },\n set(key: string, value: string): void {\n store.set(key, value);\n },\n remove(key: string): void {\n store.delete(key);\n },\n };\n}\n\n/**\n * Detect environment and create appropriate default adapter\n */\nexport function createDefaultAdapter(): StorageAdapter {\n if (typeof localStorage !== \"undefined\") {\n return createLocalStorageAdapter();\n }\n return createMemoryAdapter();\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { AuthError, ValidationError } from \"./errors.ts\";\nimport { CUSTOMER_TOKEN_KEY } from \"./storage.ts\";\nimport type {\n Customer,\n CustomerAddress,\n CustomerAddressInput,\n CustomerAddressUpdateInput,\n CustomerOrder,\n CustomerUpdateInput,\n PaginatedResult,\n StorageAdapter,\n} from \"./types.ts\";\n\ninterface UserError {\n field: string | null;\n message: string;\n code: string | null;\n}\n\ninterface OrderItemData {\n id: string;\n productTitle: string;\n variantTitle: string | null;\n sku: string | null;\n quantity: number;\n unitPrice: number;\n totalPrice: number;\n}\n\ninterface OrderNodeData {\n id: string;\n orderNumber: string;\n status: string;\n customerEmail: string;\n customerPhone: string | null;\n subtotal: number;\n total: number;\n note: string | null;\n items: OrderItemData[];\n createdAt: string;\n}\n\ninterface AddressData {\n id: string;\n label: string | null;\n firstName: string | null;\n lastName: string | null;\n addressLine1: string;\n addressLine2: string | null;\n city: string;\n postalCode: string | null;\n phone: string | null;\n isDefault: boolean;\n createdAt: string;\n}\n\ninterface CustomerData {\n id: string;\n name: string | null;\n email: string;\n emailVerified: boolean;\n}\n\ninterface CustomerOrdersResponse {\n customerOrders: {\n edges: Array<{ node: OrderNodeData; cursor: string }>;\n pageInfo: {\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n startCursor: string | null;\n endCursor: string | null;\n };\n };\n}\n\ninterface CustomerAddressesResponse {\n customerAddresses: AddressData[];\n}\n\ninterface CustomerAddressCreateResponse {\n customerAddressCreate: {\n address: AddressData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerAddressUpdateResponse {\n customerAddressUpdate: {\n address: AddressData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerAddressDeleteResponse {\n customerAddressDelete: {\n deletedAddressId: string | null;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerUpdateResponse {\n customerUpdate: {\n customer: CustomerData | null;\n userErrors: UserError[];\n };\n}\n\nconst ORDER_ITEM_FRAGMENT = `\n id\n productTitle\n variantTitle\n sku\n quantity\n unitPrice\n totalPrice\n`;\n\nconst CUSTOMER_ORDERS_QUERY = `\nquery CustomerOrders($first: Int, $after: String, $last: Int, $before: String) {\n customerOrders(first: $first, after: $after, last: $last, before: $before) {\n edges {\n node {\n id\n orderNumber\n status\n customerEmail\n customerPhone\n subtotal\n total\n note\n items { ${ORDER_ITEM_FRAGMENT} }\n createdAt\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n}\n`;\n\nconst ADDRESS_FRAGMENT = `\n id\n label\n firstName\n lastName\n addressLine1\n addressLine2\n city\n postalCode\n phone\n isDefault\n createdAt\n`;\n\nconst CUSTOMER_ADDRESSES_QUERY = `\nquery CustomerAddresses {\n customerAddresses { ${ADDRESS_FRAGMENT} }\n}\n`;\n\nconst CUSTOMER_ADDRESS_CREATE_MUTATION = `\nmutation CustomerAddressCreate($input: CustomerAddressCreateInput!) {\n customerAddressCreate(input: $input) {\n address { ${ADDRESS_FRAGMENT} }\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_ADDRESS_UPDATE_MUTATION = `\nmutation CustomerAddressUpdate($addressId: String!, $input: CustomerAddressUpdateInput!) {\n customerAddressUpdate(addressId: $addressId, input: $input) {\n address { ${ADDRESS_FRAGMENT} }\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_ADDRESS_DELETE_MUTATION = `\nmutation CustomerAddressDelete($addressId: String!) {\n customerAddressDelete(addressId: $addressId) {\n deletedAddressId\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_UPDATE_MUTATION = `\nmutation CustomerUpdate($input: CustomerUpdateInput!) {\n customerUpdate(input: $input) {\n customer {\n id\n name\n email\n emailVerified\n }\n userErrors { field message code }\n }\n}\n`;\n\nfunction mapOrderNode(data: OrderNodeData): CustomerOrder {\n return {\n id: data.id,\n orderNumber: data.orderNumber,\n status: data.status,\n email: data.customerEmail,\n phone: data.customerPhone,\n subtotal: data.subtotal,\n total: data.total,\n note: data.note,\n items: data.items.map((item) => ({\n id: item.id,\n productTitle: item.productTitle,\n variantTitle: item.variantTitle,\n sku: item.sku,\n quantity: item.quantity,\n unitPrice: item.unitPrice,\n totalPrice: item.totalPrice,\n })),\n createdAt: data.createdAt,\n };\n}\n\nfunction mapAddressData(data: AddressData): CustomerAddress {\n return {\n id: data.id,\n label: data.label,\n firstName: data.firstName,\n lastName: data.lastName,\n addressLine1: data.addressLine1,\n addressLine2: data.addressLine2,\n city: data.city,\n postalCode: data.postalCode,\n phone: data.phone,\n isDefault: data.isDefault,\n createdAt: data.createdAt,\n };\n}\n\nfunction handleUserErrors(userErrors: UserError[]): ValidationError | null {\n if (userErrors.length === 0) return null;\n const messages = userErrors.map((e) => e.message).join(\"; \");\n return new ValidationError(\n messages,\n userErrors.map((e) => ({ field: e.field, message: e.message })),\n );\n}\n\nexport interface AccountOperations {\n orders(args?: {\n first?: number;\n after?: string;\n last?: number;\n before?: string;\n }): Promise<Result<PaginatedResult<CustomerOrder>, StorefrontError>>;\n addresses(): Promise<Result<CustomerAddress[], StorefrontError>>;\n createAddress(input: CustomerAddressInput): Promise<Result<CustomerAddress, StorefrontError>>;\n updateAddress(\n addressId: string,\n input: CustomerAddressUpdateInput,\n ): Promise<Result<CustomerAddress, StorefrontError>>;\n deleteAddress(addressId: string): Promise<Result<string, StorefrontError>>;\n update(input: CustomerUpdateInput): Promise<Result<Customer, StorefrontError>>;\n}\n\nexport function createAccountOperations(client: StorefrontClient, storage: StorageAdapter): AccountOperations {\n function requireAuth(): Result<void, AuthError> {\n if (!storage.get(CUSTOMER_TOKEN_KEY)) {\n return err(new AuthError(\"Not authenticated. Call auth.login() or auth.register() first.\"));\n }\n return ok(undefined);\n }\n\n return {\n async orders(args) {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const variables: Record<string, unknown> = {};\n if (args?.first !== undefined) variables.first = args.first;\n if (args?.after !== undefined) variables.after = args.after;\n if (args?.last !== undefined) variables.last = args.last;\n if (args?.before !== undefined) variables.before = args.before;\n if (!variables.first && !variables.last) variables.first = 20;\n\n const result = await client.query<CustomerOrdersResponse>(\n { query: CUSTOMER_ORDERS_QUERY, variables },\n { cache: false },\n );\n\n if (result.isErr()) return err(result.error);\n\n const { edges, pageInfo } = result.value.customerOrders;\n return ok({\n items: edges.map((edge) => mapOrderNode(edge.node)),\n pageInfo,\n });\n },\n\n async addresses() {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const result = await client.query<CustomerAddressesResponse>(\n { query: CUSTOMER_ADDRESSES_QUERY },\n { cache: false },\n );\n\n if (result.isErr()) return err(result.error);\n\n return ok(result.value.customerAddresses.map(mapAddressData));\n },\n\n async createAddress(input) {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const result = await client.mutate<CustomerAddressCreateResponse>({\n query: CUSTOMER_ADDRESS_CREATE_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerAddressCreate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.address) {\n return err(new ValidationError(\"Failed to create address\", []));\n }\n\n return ok(mapAddressData(payload.address));\n },\n\n async updateAddress(addressId, input) {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const result = await client.mutate<CustomerAddressUpdateResponse>({\n query: CUSTOMER_ADDRESS_UPDATE_MUTATION,\n variables: { addressId, input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerAddressUpdate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.address) {\n return err(new ValidationError(\"Failed to update address\", []));\n }\n\n return ok(mapAddressData(payload.address));\n },\n\n async deleteAddress(addressId) {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const result = await client.mutate<CustomerAddressDeleteResponse>({\n query: CUSTOMER_ADDRESS_DELETE_MUTATION,\n variables: { addressId },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerAddressDelete;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.deletedAddressId) {\n return err(new ValidationError(\"Failed to delete address\", []));\n }\n\n return ok(payload.deletedAddressId);\n },\n\n async update(input) {\n const authCheck = requireAuth();\n if (authCheck.isErr()) return err(authCheck.error);\n\n const result = await client.mutate<CustomerUpdateResponse>({\n query: CUSTOMER_UPDATE_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerUpdate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.customer) {\n return err(new ValidationError(\"Failed to update profile\", []));\n }\n\n return ok({\n id: payload.customer.id,\n name: payload.customer.name,\n email: payload.customer.email,\n emailVerified: payload.customer.emailVerified,\n });\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { ValidationError } from \"./errors.ts\";\nimport { CUSTOMER_TOKEN_KEY } from \"./storage.ts\";\nimport type { Customer, StorageAdapter } from \"./types.ts\";\n\ninterface UserError {\n field: string | null;\n message: string;\n code: string | null;\n}\n\ninterface CustomerData {\n id: string;\n name: string | null;\n email: string;\n emailVerified: boolean;\n}\n\ninterface CustomerRegisterResponse {\n customerRegister: {\n customer: CustomerData | null;\n token: string | null;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerLoginResponse {\n customerLogin: {\n customer: CustomerData | null;\n token: string | null;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerPasswordResetRequestResponse {\n customerPasswordResetRequest: {\n success: boolean;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerPasswordResetResponse {\n customerPasswordReset: {\n success: boolean;\n userErrors: UserError[];\n };\n}\n\ninterface CustomerVerifyEmailResponse {\n customerVerifyEmail: {\n customer: CustomerData | null;\n userErrors: UserError[];\n };\n}\n\ninterface MeResponse {\n me: CustomerData | null;\n}\n\nconst CUSTOMER_FRAGMENT = `\n id\n name\n email\n emailVerified\n`;\n\nconst CUSTOMER_REGISTER_MUTATION = `\nmutation CustomerRegister($input: CustomerRegisterInput!) {\n customerRegister(input: $input) {\n customer { ${CUSTOMER_FRAGMENT} }\n token\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_LOGIN_MUTATION = `\nmutation CustomerLogin($input: CustomerLoginInput!) {\n customerLogin(input: $input) {\n customer { ${CUSTOMER_FRAGMENT} }\n token\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_PASSWORD_RESET_REQUEST_MUTATION = `\nmutation CustomerPasswordResetRequest($input: CustomerPasswordResetRequestInput!) {\n customerPasswordResetRequest(input: $input) {\n success\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_PASSWORD_RESET_MUTATION = `\nmutation CustomerPasswordReset($input: CustomerPasswordResetInput!) {\n customerPasswordReset(input: $input) {\n success\n userErrors { field message code }\n }\n}\n`;\n\nconst CUSTOMER_VERIFY_EMAIL_MUTATION = `\nmutation CustomerVerifyEmail($input: CustomerVerifyEmailInput!) {\n customerVerifyEmail(input: $input) {\n customer { ${CUSTOMER_FRAGMENT} }\n userErrors { field message code }\n }\n}\n`;\n\nconst ME_QUERY = `\nquery Me {\n me { ${CUSTOMER_FRAGMENT} }\n}\n`;\n\nfunction mapCustomerData(data: CustomerData): Customer {\n return {\n id: data.id,\n name: data.name,\n email: data.email,\n emailVerified: data.emailVerified,\n };\n}\n\nfunction handleUserErrors(userErrors: UserError[]): ValidationError | null {\n if (userErrors.length === 0) return null;\n const messages = userErrors.map((e) => e.message).join(\"; \");\n return new ValidationError(\n messages,\n userErrors.map((e) => ({ field: e.field, message: e.message })),\n );\n}\n\nexport interface AuthOperations {\n register(input: {\n email: string;\n password: string;\n name?: string;\n }): Promise<Result<{ customer: Customer; token: string }, StorefrontError>>;\n login(input: {\n email: string;\n password: string;\n }): Promise<Result<{ customer: Customer; token: string }, StorefrontError>>;\n logout(): void;\n requestPasswordReset(email: string): Promise<Result<{ success: boolean }, StorefrontError>>;\n resetPassword(input: { token: string; newPassword: string }): Promise<Result<{ success: boolean }, StorefrontError>>;\n verifyEmail(token: string): Promise<Result<Customer, StorefrontError>>;\n me(): Promise<Result<Customer | null, StorefrontError>>;\n isLoggedIn(): boolean;\n}\n\nexport function createAuthOperations(client: StorefrontClient, storage: StorageAdapter): AuthOperations {\n return {\n async register(input) {\n const result = await client.mutate<CustomerRegisterResponse>({\n query: CUSTOMER_REGISTER_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerRegister;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.customer || !payload.token) {\n return err(new ValidationError(\"Registration failed\", []));\n }\n\n storage.set(CUSTOMER_TOKEN_KEY, payload.token);\n return ok({ customer: mapCustomerData(payload.customer), token: payload.token });\n },\n\n async login(input) {\n const result = await client.mutate<CustomerLoginResponse>({\n query: CUSTOMER_LOGIN_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerLogin;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.customer || !payload.token) {\n return err(new ValidationError(\"Login failed\", []));\n }\n\n storage.set(CUSTOMER_TOKEN_KEY, payload.token);\n return ok({ customer: mapCustomerData(payload.customer), token: payload.token });\n },\n\n logout() {\n storage.remove(CUSTOMER_TOKEN_KEY);\n },\n\n async requestPasswordReset(email) {\n const result = await client.mutate<CustomerPasswordResetRequestResponse>({\n query: CUSTOMER_PASSWORD_RESET_REQUEST_MUTATION,\n variables: { input: { email } },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerPasswordResetRequest;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n return ok({ success: payload.success });\n },\n\n async resetPassword(input) {\n const result = await client.mutate<CustomerPasswordResetResponse>({\n query: CUSTOMER_PASSWORD_RESET_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerPasswordReset;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n return ok({ success: payload.success });\n },\n\n async verifyEmail(token) {\n const result = await client.mutate<CustomerVerifyEmailResponse>({\n query: CUSTOMER_VERIFY_EMAIL_MUTATION,\n variables: { input: { token } },\n });\n\n if (result.isErr()) return err(result.error);\n\n const payload = result.value.customerVerifyEmail;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) return err(userError);\n\n if (!payload.customer) {\n return err(new ValidationError(\"Email verification failed\", []));\n }\n\n return ok(mapCustomerData(payload.customer));\n },\n\n async me() {\n if (!storage.get(CUSTOMER_TOKEN_KEY)) return ok(null);\n\n const result = await client.query<MeResponse>({ query: ME_QUERY }, { cache: false });\n if (result.isErr()) return err(result.error);\n\n return ok(result.value.me ? mapCustomerData(result.value.me) : null);\n },\n\n isLoggedIn() {\n return storage.get(CUSTOMER_TOKEN_KEY) !== null;\n },\n };\n}\n","const TRACKING_SCHEMA_VERSION = 1 as const;\nconst TRACKING_ATTRIBUTION_STORAGE_KEY = \"srb_tracking_attribution\";\n\ninterface TrackingUtmSnapshot {\n schemaVersion: 1;\n source: string | null;\n medium: string | null;\n campaign: string | null;\n term: string | null;\n content: string | null;\n}\n\ninterface TrackingClickIdsSnapshot {\n schemaVersion: 1;\n capturedAt: string | null;\n gclid: string | null;\n gbraid: string | null;\n wbraid: string | null;\n ttclid: string | null;\n fbclid: string | null;\n}\n\nexport interface TrackingAttributionSnapshot {\n schemaVersion: 1;\n capturedAt: string;\n utm: TrackingUtmSnapshot;\n clickIds: TrackingClickIdsSnapshot;\n}\n\nfunction hasBrowserContext(): boolean {\n return typeof window !== \"undefined\";\n}\n\nfunction normalizeParam(value: string | null): string | null {\n if (value === null) return null;\n const trimmed = value.trim();\n return trimmed.length > 0 ? trimmed : null;\n}\n\nfunction hasAttributionValue(snapshot: TrackingAttributionSnapshot): boolean {\n return [\n snapshot.utm.source,\n snapshot.utm.medium,\n snapshot.utm.campaign,\n snapshot.utm.term,\n snapshot.utm.content,\n snapshot.clickIds.gclid,\n snapshot.clickIds.gbraid,\n snapshot.clickIds.wbraid,\n snapshot.clickIds.ttclid,\n snapshot.clickIds.fbclid,\n ].some((value) => value !== null);\n}\n\nfunction parseStoredSnapshot(raw: string | null): TrackingAttributionSnapshot | null {\n if (!raw) return null;\n\n try {\n const parsed = JSON.parse(raw) as Partial<TrackingAttributionSnapshot>;\n if (parsed.schemaVersion !== TRACKING_SCHEMA_VERSION || typeof parsed.capturedAt !== \"string\") {\n return null;\n }\n\n const utm = parsed.utm;\n const clickIds = parsed.clickIds;\n if (!utm || !clickIds) return null;\n\n return {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n capturedAt: parsed.capturedAt,\n utm: {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n source: typeof utm.source === \"string\" ? utm.source : null,\n medium: typeof utm.medium === \"string\" ? utm.medium : null,\n campaign: typeof utm.campaign === \"string\" ? utm.campaign : null,\n term: typeof utm.term === \"string\" ? utm.term : null,\n content: typeof utm.content === \"string\" ? utm.content : null,\n },\n clickIds: {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n capturedAt: typeof clickIds.capturedAt === \"string\" ? clickIds.capturedAt : null,\n gclid: typeof clickIds.gclid === \"string\" ? clickIds.gclid : null,\n gbraid: typeof clickIds.gbraid === \"string\" ? clickIds.gbraid : null,\n wbraid: typeof clickIds.wbraid === \"string\" ? clickIds.wbraid : null,\n ttclid: typeof clickIds.ttclid === \"string\" ? clickIds.ttclid : null,\n fbclid: typeof clickIds.fbclid === \"string\" ? clickIds.fbclid : null,\n },\n };\n } catch {\n return null;\n }\n}\n\nfunction readStoredSnapshot(): TrackingAttributionSnapshot | null {\n if (!hasBrowserContext()) return null;\n\n try {\n return parseStoredSnapshot(window.localStorage.getItem(TRACKING_ATTRIBUTION_STORAGE_KEY));\n } catch {\n return null;\n }\n}\n\nfunction writeStoredSnapshot(snapshot: TrackingAttributionSnapshot): void {\n if (!hasBrowserContext()) return;\n\n try {\n window.localStorage.setItem(TRACKING_ATTRIBUTION_STORAGE_KEY, JSON.stringify(snapshot));\n } catch {\n // ignore storage failures\n }\n}\n\nfunction buildSnapshotFromSearch(search: string): TrackingAttributionSnapshot {\n const params = new URLSearchParams(search);\n const capturedAt = new Date().toISOString();\n\n return {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n capturedAt,\n utm: {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n source: normalizeParam(params.get(\"utm_source\")),\n medium: normalizeParam(params.get(\"utm_medium\")),\n campaign: normalizeParam(params.get(\"utm_campaign\")),\n term: normalizeParam(params.get(\"utm_term\")),\n content: normalizeParam(params.get(\"utm_content\")),\n },\n clickIds: {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n capturedAt,\n gclid: normalizeParam(params.get(\"gclid\")),\n gbraid: normalizeParam(params.get(\"gbraid\")),\n wbraid: normalizeParam(params.get(\"wbraid\")),\n ttclid: normalizeParam(params.get(\"ttclid\")),\n fbclid: normalizeParam(params.get(\"fbclid\")),\n },\n };\n}\n\nexport function captureLandingTrackingAttribution(): TrackingAttributionSnapshot | null {\n if (!hasBrowserContext()) return null;\n\n const snapshot = buildSnapshotFromSearch(window.location.search);\n if (hasAttributionValue(snapshot)) {\n writeStoredSnapshot(snapshot);\n return snapshot;\n }\n\n return readStoredSnapshot();\n}\n\nexport function getTrackingAttributionSnapshot(): TrackingAttributionSnapshot | null {\n return readStoredSnapshot();\n}\n","import type { Collection, Product } from \"./types.ts\";\n\nfunction isAbsoluteUrl(value: string): boolean {\n return /^https?:\\/\\//i.test(value);\n}\n\nfunction toOrigin(endpoint: string): string | null {\n try {\n return new URL(endpoint).origin;\n } catch {\n return null;\n }\n}\n\nexport function resolveAssetUrl(url: string, endpoint: string): string {\n if (!url) {\n return url;\n }\n\n if (isAbsoluteUrl(url)) {\n return url;\n }\n\n const origin = toOrigin(endpoint);\n if (!origin) {\n return url;\n }\n\n try {\n return new URL(url, origin).toString();\n } catch {\n return url;\n }\n}\n\nexport function normalizeProductAssetUrls(product: Product, endpoint: string): Product {\n return {\n ...product,\n media: product.media.map((media) => ({\n ...media,\n url: resolveAssetUrl(media.url, endpoint),\n })),\n variants: product.variants.map((variant) => ({\n ...variant,\n image: variant.image\n ? {\n ...variant.image,\n url: resolveAssetUrl(variant.image.url, endpoint),\n }\n : null,\n })),\n };\n}\n\nexport function normalizeCollectionAssetUrls(collection: Collection, endpoint: string): Collection {\n return {\n ...collection,\n imageAsset: collection.imageAsset\n ? { ...collection.imageAsset, url: resolveAssetUrl(collection.imageAsset.url, endpoint) }\n : null,\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError, StateError, ValidationError } from \"./errors.ts\";\nimport { CART_TOKEN_KEY } from \"./storage.ts\";\nimport { captureLandingTrackingAttribution } from \"./tracking-attribution.ts\";\nimport type { Address, Cart, CartStatus, ProductVariant } from \"./types.ts\";\nimport { resolveAssetUrl } from \"./url.ts\";\n\ninterface UserError {\n field: string | null;\n message: string;\n code: string | null;\n}\n\ninterface CartItemData {\n id: string;\n variantId: string;\n quantity: number;\n priceAtAdd: number;\n effectiveUnitPrice: number;\n lineTotal: number;\n taxAmount: number;\n variant:\n | (Pick<\n ProductVariant,\n | \"id\"\n | \"title\"\n | \"sku\"\n | \"price\"\n | \"compareAtPrice\"\n | \"weight\"\n | \"weightUnit\"\n | \"requiresShipping\"\n | \"availableForSale\"\n | \"quantity\"\n | \"selectedOptions\"\n | \"image\"\n | \"isOnSale\"\n | \"quantityPricing\"\n > & {})\n | null;\n}\n\ninterface AppliedPromoCodeData {\n code: string;\n discountType: string;\n discountAmount: number;\n description: string;\n}\n\ninterface AppliedDiscountData {\n promotionId: string;\n discountClass: string;\n discountType: string;\n discountAmount: number;\n description: string;\n isAutomatic: boolean;\n}\n\ninterface CartData {\n id: string;\n token: string;\n status: CartStatus;\n items: CartItemData[];\n totalItems: number;\n totalPrice: number;\n taxTotal: number;\n shippingTotal: number;\n total: number;\n discountTotal: number;\n appliedPromoCode: AppliedPromoCodeData | null;\n appliedDiscounts: AppliedDiscountData[];\n customerEmail: string | null;\n customerPhone: string | null;\n shippingAddress: Address | null;\n billingAddress: Address | null;\n paymentMethod: string | null;\n shippingRateId: string | null;\n notes: string | null;\n checkoutStartedAt?: string | null;\n checkoutExpiresAt?: string | null;\n createdAt: string;\n updatedAt: string;\n}\n\ninterface CartQueryResponse {\n cart: CartData | null;\n}\n\ninterface CartCreateResponse {\n cartCreate: {\n cart: CartData | null;\n token: string | null;\n userErrors: UserError[];\n };\n}\n\ninterface CartItemAddResponse {\n cartItemAdd: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CartItemUpdateResponse {\n cartItemUpdate: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CartItemRemoveResponse {\n cartItemRemove: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CartClearResponse {\n cartClear: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\nconst CART_FRAGMENT = `\n id\n token\n status\n items {\n id\n variantId\n quantity\n priceAtAdd\n effectiveUnitPrice\n lineTotal\n taxAmount\n variant {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions { id value position }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing { minQuantity price }\n }\n }\n totalItems\n totalPrice\n taxTotal\n shippingTotal\n total\n discountTotal\n appliedPromoCode {\n code\n discountType\n discountAmount\n description\n }\n appliedDiscounts {\n promotionId\n discountClass\n discountType\n discountAmount\n description\n isAutomatic\n }\n customerEmail\n customerPhone\n shippingAddress\n billingAddress\n paymentMethod\n shippingRateId\n notes\n checkoutStartedAt\n checkoutExpiresAt\n createdAt\n updatedAt\n`;\n\nconst CART_QUERY = `\nquery Cart {\n cart {\n ${CART_FRAGMENT}\n }\n}\n`;\n\nconst CART_CREATE_MUTATION = `\nmutation CartCreate {\n cartCreate {\n cart {\n ${CART_FRAGMENT}\n }\n token\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_ITEM_ADD_MUTATION = `\nmutation CartItemAdd($input: CartItemAddInput!) {\n cartItemAdd(input: $input) {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_ITEM_UPDATE_MUTATION = `\nmutation CartItemUpdate($input: CartItemUpdateInput!) {\n cartItemUpdate(input: $input) {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_ITEM_REMOVE_MUTATION = `\nmutation CartItemRemove($input: CartItemRemoveInput!) {\n cartItemRemove(input: $input) {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_CLEAR_MUTATION = `\nmutation CartClear {\n cartClear {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_PROMO_CODE_APPLY_MUTATION = `\nmutation CartPromoCodeApply($input: CartPromoCodeApplyInput!) {\n cartPromoCodeApply(input: $input) {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CART_PROMO_CODE_REMOVE_MUTATION = `\nmutation CartPromoCodeRemove {\n cartPromoCodeRemove {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\ninterface CartPromoCodeApplyResponse {\n cartPromoCodeApply: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CartPromoCodeRemoveResponse {\n cartPromoCodeRemove: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\nconst INVALID_CART_STATES: CartStatus[] = [\"checkout\", \"converted\", \"abandoned\", \"expired\"];\n\nfunction mapCartData(data: CartData, endpoint: string): Cart {\n return {\n id: data.id,\n token: data.token,\n status: data.status,\n items: data.items.map((item) => ({\n id: item.id,\n variantId: item.variantId,\n quantity: item.quantity,\n priceAtAdd: item.priceAtAdd,\n effectiveUnitPrice: item.effectiveUnitPrice,\n lineTotal: item.lineTotal,\n taxAmount: item.taxAmount,\n variant: item.variant\n ? {\n ...item.variant,\n image: item.variant.image\n ? { ...item.variant.image, url: resolveAssetUrl(item.variant.image.url, endpoint) }\n : null,\n }\n : null,\n })),\n totalItems: data.totalItems,\n totalPrice: data.totalPrice,\n taxTotal: data.taxTotal,\n shippingTotal: data.shippingTotal,\n total: data.total,\n discountTotal: data.discountTotal,\n appliedPromoCode: data.appliedPromoCode,\n appliedDiscounts: data.appliedDiscounts,\n customerEmail: data.customerEmail,\n customerPhone: data.customerPhone,\n shippingAddress: data.shippingAddress,\n billingAddress: data.billingAddress,\n paymentMethod: data.paymentMethod,\n shippingRateId: data.shippingRateId,\n notes: data.notes,\n checkoutStartedAt: data.checkoutStartedAt ?? null,\n checkoutExpiresAt: data.checkoutExpiresAt ?? null,\n createdAt: data.createdAt,\n updatedAt: data.updatedAt,\n };\n}\n\nfunction checkCartState(status: CartStatus): Result<void, StateError> {\n if (INVALID_CART_STATES.includes(status)) {\n return err(\n new StateError(\n `Cannot modify cart in '${status}' state. Cart operations are only allowed when cart is in 'active' state.`,\n status,\n ),\n );\n }\n return ok(undefined);\n}\n\nfunction handleUserErrors(userErrors: UserError[]): ValidationError | StateError | null {\n if (userErrors.length === 0) return null;\n\n const messages = userErrors.map((e) => e.message).join(\"; \");\n const stateError = userErrors.find((e) => e.code?.includes(\"STATE\") || e.message.includes(\"state\"));\n\n if (stateError) {\n return new StateError(messages, \"unknown\");\n }\n\n return new ValidationError(\n messages,\n userErrors.map((e) => ({ field: e.field, message: e.message })),\n );\n}\n\nexport interface CartOperations {\n get(): Promise<Result<Cart | null, StorefrontError>>;\n create(): Promise<Result<Cart, StorefrontError>>;\n addItem(variantId: string, quantity: number): Promise<Result<Cart, StorefrontError>>;\n updateItem(variantId: string, quantity: number): Promise<Result<Cart, StorefrontError>>;\n removeItem(variantId: string): Promise<Result<Cart, StorefrontError>>;\n clear(): Promise<Result<Cart, StorefrontError>>;\n applyPromoCode(code: string): Promise<Result<Cart, StorefrontError>>;\n removePromoCode(): Promise<Result<Cart, StorefrontError>>;\n}\n\nexport function createCartOperations(\n client: StorefrontClient,\n storage: { get(key: string): string | null; set(key: string, value: string): void; remove(key: string): void },\n): CartOperations {\n return {\n async get(): Promise<Result<Cart | null, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return ok(null);\n }\n\n const result = await client.query<CartQueryResponse>({ query: CART_QUERY }, { cache: false });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.cart) {\n storage.remove(CART_TOKEN_KEY);\n return ok(null);\n }\n\n return ok(mapCartData(result.value.cart, client.config.endpoint));\n },\n\n async create(): Promise<Result<Cart, StorefrontError>> {\n const result = await client.mutate<CartCreateResponse>({\n query: CART_CREATE_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartCreate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart || !payload.token) {\n return err(new NotFoundError(\"Failed to create cart\"));\n }\n\n storage.set(CART_TOKEN_KEY, payload.token);\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async addItem(variantId: string, quantity: number): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartItemAddResponse>({\n query: CART_ITEM_ADD_MUTATION,\n variables: {\n input: {\n variantId,\n quantity,\n trackingAttribution: captureLandingTrackingAttribution() ?? undefined,\n },\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartItemAdd;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n const stateCheck = checkCartState(payload.cart.status);\n if (stateCheck.isErr()) {\n return err(stateCheck.error);\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async updateItem(variantId: string, quantity: number): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartItemUpdateResponse>({\n query: CART_ITEM_UPDATE_MUTATION,\n variables: {\n input: {\n variantId,\n quantity,\n trackingAttribution: captureLandingTrackingAttribution() ?? undefined,\n },\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartItemUpdate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n const stateCheck = checkCartState(payload.cart.status);\n if (stateCheck.isErr()) {\n return err(stateCheck.error);\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async removeItem(variantId: string): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartItemRemoveResponse>({\n query: CART_ITEM_REMOVE_MUTATION,\n variables: {\n input: {\n variantId,\n trackingAttribution: captureLandingTrackingAttribution() ?? undefined,\n },\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartItemRemove;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n const stateCheck = checkCartState(payload.cart.status);\n if (stateCheck.isErr()) {\n return err(stateCheck.error);\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async clear(): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartClearResponse>({\n query: CART_CLEAR_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartClear;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n const stateCheck = checkCartState(payload.cart.status);\n if (stateCheck.isErr()) {\n return err(stateCheck.error);\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async applyPromoCode(code: string): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartPromoCodeApplyResponse>({\n query: CART_PROMO_CODE_APPLY_MUTATION,\n variables: { input: { code } },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartPromoCodeApply;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async removePromoCode(): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CartPromoCodeRemoveResponse>({\n query: CART_PROMO_CODE_REMOVE_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.cartPromoCodeRemove;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError } from \"./errors.ts\";\nimport type { Category, FlatCategory, PaginatedResult, Product } from \"./types.ts\";\nimport { normalizeProductAssetUrls, resolveAssetUrl } from \"./url.ts\";\n\nexport interface CategoryProductsOptions {\n first?: number;\n after?: string;\n includeDescendants?: boolean;\n}\n\ninterface CategoryImage {\n url: string;\n altText: string | null;\n width: number | null;\n height: number | null;\n}\n\ninterface RawCategory {\n id: string;\n name: string;\n handle: string;\n description: string | null;\n metaTitle: string | null;\n metaDescription: string | null;\n imageAsset: CategoryImage | null;\n parent: RawCategory | null;\n children: RawCategory[];\n ancestors: RawCategory[];\n productCount: number;\n}\n\ninterface CategoriesTreeQueryResponse {\n storefrontCategories: RawCategory[];\n}\n\ninterface CategoryQueryResponse {\n storefrontCategory: RawCategory | null;\n}\n\ninterface ProductEdge {\n node: Product;\n cursor: string;\n}\n\ninterface ProductConnection {\n edges: ProductEdge[];\n pageInfo: {\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n startCursor: string | null;\n endCursor: string | null;\n };\n}\n\ninterface CategoryWithProducts {\n id: string;\n products: ProductConnection;\n}\n\ninterface CategoryProductsQueryResponse {\n storefrontCategory: CategoryWithProducts | null;\n}\n\nconst CATEGORY_FIELDS = `\n id\n name\n handle\n description\n metaTitle\n metaDescription\n imageAsset {\n url\n altText\n width\n height\n }\n productCount\n`;\n\nconst CATEGORIES_TREE_QUERY = `\nquery CategoriesTree {\n storefrontCategories {\n ${CATEGORY_FIELDS}\n children {\n ${CATEGORY_FIELDS}\n children {\n ${CATEGORY_FIELDS}\n children {\n ${CATEGORY_FIELDS}\n children {\n ${CATEGORY_FIELDS}\n }\n }\n }\n }\n }\n}\n`;\n\nconst CATEGORY_BY_ID_QUERY = `\nquery CategoryById($id: ID!) {\n storefrontCategory(id: $id) {\n ${CATEGORY_FIELDS}\n parent {\n ${CATEGORY_FIELDS}\n }\n children {\n ${CATEGORY_FIELDS}\n }\n ancestors {\n ${CATEGORY_FIELDS}\n }\n }\n}\n`;\n\nconst CATEGORY_BY_HANDLE_QUERY = `\nquery CategoryByHandle($handle: String!) {\n storefrontCategory(handle: $handle) {\n ${CATEGORY_FIELDS}\n parent {\n ${CATEGORY_FIELDS}\n }\n children {\n ${CATEGORY_FIELDS}\n }\n ancestors {\n ${CATEGORY_FIELDS}\n }\n }\n}\n`;\n\nconst CATEGORY_PRODUCTS_BY_ID_QUERY = `\nquery CategoryProductsById($id: ID!, $first: Int, $after: String, $includeDescendants: Boolean) {\n storefrontCategory(id: $id) {\n id\n products(first: $first, after: $after, includeDescendants: $includeDescendants) {\n edges {\n node {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n primaryCategory {\n id\n name\n handle\n }\n tags {\n id\n name\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n }\n}\n`;\n\nconst CATEGORY_PRODUCTS_BY_HANDLE_QUERY = `\nquery CategoryProductsByHandle($handle: String!, $first: Int, $after: String, $includeDescendants: Boolean) {\n storefrontCategory(handle: $handle) {\n id\n products(first: $first, after: $after, includeDescendants: $includeDescendants) {\n edges {\n node {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n primaryCategory {\n id\n name\n handle\n }\n tags {\n id\n name\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n }\n}\n`;\n\nfunction mapRawCategory(raw: RawCategory, endpoint: string): Category {\n return {\n id: raw.id,\n name: raw.name,\n handle: raw.handle,\n description: raw.description,\n metaTitle: raw.metaTitle,\n metaDescription: raw.metaDescription,\n imageAsset: raw.imageAsset\n ? {\n url: resolveAssetUrl(raw.imageAsset.url, endpoint),\n altText: raw.imageAsset.altText,\n width: raw.imageAsset.width,\n height: raw.imageAsset.height,\n }\n : null,\n parent: raw.parent ? mapRawCategory(raw.parent, endpoint) : null,\n children: raw.children?.map((child) => mapRawCategory(child, endpoint)) ?? [],\n ancestors: raw.ancestors?.map((ancestor) => mapRawCategory(ancestor, endpoint)) ?? [],\n productCount: raw.productCount,\n };\n}\n\nfunction flattenTree(categories: Category[], parentId: string | null, depth: number): FlatCategory[] {\n const result: FlatCategory[] = [];\n for (const cat of categories) {\n result.push({\n id: cat.id,\n name: cat.name,\n handle: cat.handle,\n description: cat.description,\n metaTitle: cat.metaTitle,\n metaDescription: cat.metaDescription,\n imageUrl: cat.imageAsset?.url ?? null,\n parentId,\n depth,\n hasChildren: cat.children.length > 0,\n productCount: cat.productCount,\n });\n result.push(...flattenTree(cat.children, cat.id, depth + 1));\n }\n return result;\n}\n\nfunction isGlobalId(value: string): boolean {\n if (!value.includes(\":\")) {\n try {\n const decoded = atob(value);\n return decoded.includes(\":\");\n } catch {\n return false;\n }\n }\n return false;\n}\n\nexport interface CategoriesOperations {\n tree(): Promise<Result<Category[], StorefrontError>>;\n flat(): Promise<Result<FlatCategory[], StorefrontError>>;\n get(idOrHandle: string): Promise<Result<Category, StorefrontError>>;\n getProducts(\n idOrHandle: string,\n options?: CategoryProductsOptions,\n ): Promise<Result<PaginatedResult<Product>, StorefrontError>>;\n}\n\nexport function createCategoriesOperations(client: StorefrontClient): CategoriesOperations {\n return {\n async tree(): Promise<Result<Category[], StorefrontError>> {\n const result = await client.query<CategoriesTreeQueryResponse>({\n query: CATEGORIES_TREE_QUERY,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n return ok(result.value.storefrontCategories.map((category) => mapRawCategory(category, client.config.endpoint)));\n },\n\n async flat(): Promise<Result<FlatCategory[], StorefrontError>> {\n const result = await client.query<CategoriesTreeQueryResponse>({\n query: CATEGORIES_TREE_QUERY,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const tree = result.value.storefrontCategories.map((category) =>\n mapRawCategory(category, client.config.endpoint),\n );\n return ok(flattenTree(tree, null, 0));\n },\n\n async get(idOrHandle: string): Promise<Result<Category, StorefrontError>> {\n const useId = isGlobalId(idOrHandle);\n\n const result = await client.query<CategoryQueryResponse>({\n query: useId ? CATEGORY_BY_ID_QUERY : CATEGORY_BY_HANDLE_QUERY,\n variables: useId ? { id: idOrHandle } : { handle: idOrHandle },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.storefrontCategory) {\n return err(new NotFoundError(`Category not found: ${idOrHandle}`));\n }\n\n return ok(mapRawCategory(result.value.storefrontCategory, client.config.endpoint));\n },\n\n async getProducts(\n idOrHandle: string,\n options?: CategoryProductsOptions,\n ): Promise<Result<PaginatedResult<Product>, StorefrontError>> {\n const useId = isGlobalId(idOrHandle);\n\n const result = await client.query<CategoryProductsQueryResponse>({\n query: useId ? CATEGORY_PRODUCTS_BY_ID_QUERY : CATEGORY_PRODUCTS_BY_HANDLE_QUERY,\n variables: {\n ...(useId ? { id: idOrHandle } : { handle: idOrHandle }),\n first: options?.first,\n after: options?.after,\n ...(options?.includeDescendants !== undefined && { includeDescendants: options.includeDescendants }),\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.storefrontCategory) {\n return err(new NotFoundError(`Category not found: ${idOrHandle}`));\n }\n\n const connection = result.value.storefrontCategory.products;\n return ok({\n items: connection.edges.map((edge) => normalizeProductAssetUrls(edge.node, client.config.endpoint)),\n pageInfo: {\n hasNextPage: connection.pageInfo.hasNextPage,\n hasPreviousPage: connection.pageInfo.hasPreviousPage,\n startCursor: connection.pageInfo.startCursor,\n endCursor: connection.pageInfo.endCursor,\n },\n });\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError, StateError, ValidationError } from \"./errors.ts\";\nimport { CART_TOKEN_KEY } from \"./storage.ts\";\nimport type { Address, Cart, CartStatus, CheckoutData, Order, ProductVariant } from \"./types.ts\";\nimport { resolveAssetUrl } from \"./url.ts\";\n\ninterface UserError {\n field: string | null;\n message: string;\n code: string | null;\n}\n\ninterface CartItemData {\n id: string;\n variantId: string;\n quantity: number;\n priceAtAdd: number;\n effectiveUnitPrice: number;\n lineTotal: number;\n taxAmount: number;\n variant:\n | (Pick<\n ProductVariant,\n | \"id\"\n | \"title\"\n | \"sku\"\n | \"price\"\n | \"compareAtPrice\"\n | \"weight\"\n | \"weightUnit\"\n | \"requiresShipping\"\n | \"availableForSale\"\n | \"quantity\"\n | \"selectedOptions\"\n | \"image\"\n | \"isOnSale\"\n | \"quantityPricing\"\n > & {})\n | null;\n}\n\ninterface AppliedPromoCodeData {\n code: string;\n discountType: string;\n discountAmount: number;\n description: string;\n}\n\ninterface AppliedDiscountData {\n promotionId: string;\n discountClass: string;\n discountType: string;\n discountAmount: number;\n description: string;\n isAutomatic: boolean;\n}\n\ninterface CartData {\n id: string;\n token: string;\n status: CartStatus;\n items: CartItemData[];\n totalItems: number;\n totalPrice: number;\n taxTotal: number;\n shippingTotal: number;\n total: number;\n discountTotal: number;\n appliedPromoCode: AppliedPromoCodeData | null;\n appliedDiscounts: AppliedDiscountData[];\n customerEmail: string | null;\n customerPhone: string | null;\n shippingAddress: Address | null;\n billingAddress: Address | null;\n paymentMethod: string | null;\n shippingRateId: string | null;\n notes: string | null;\n checkoutStartedAt?: string | null;\n checkoutExpiresAt?: string | null;\n createdAt: string;\n updatedAt: string;\n}\n\ninterface OrderItemData {\n id: string;\n productTitle: string;\n variantTitle: string | null;\n sku: string | null;\n quantity: number;\n unitPrice: number;\n totalPrice: number;\n}\n\ninterface OrderData {\n id: string;\n orderNumber: string;\n status: string;\n customerEmail: string;\n customerPhone: string | null;\n shippingAddress: unknown;\n billingAddress: unknown;\n subtotal: number;\n total: number;\n note: string | null;\n items: OrderItemData[];\n createdAt: string;\n}\n\ninterface CheckoutStartResponse {\n checkoutStart: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CheckoutUpdateResponse {\n checkoutUpdate: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\ninterface PaymentInstructionsData {\n bankAccount: string;\n recipientName: string;\n referenceNumber: string;\n ipsQrCodeBase64: string;\n expiresAt: string;\n}\n\ninterface CheckoutConvertResponse {\n checkoutConvert: {\n order: OrderData | null;\n paymentInstructions: PaymentInstructionsData | null;\n userErrors: UserError[];\n };\n}\n\ninterface CheckoutAbandonResponse {\n checkoutAbandon: {\n cart: CartData | null;\n userErrors: UserError[];\n };\n}\n\nconst CART_FRAGMENT = `\n id\n token\n status\n items {\n id\n variantId\n quantity\n priceAtAdd\n effectiveUnitPrice\n lineTotal\n taxAmount\n variant {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions { id value position }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing { minQuantity price }\n }\n }\n totalItems\n totalPrice\n taxTotal\n shippingTotal\n total\n discountTotal\n appliedPromoCode {\n code\n discountType\n discountAmount\n description\n }\n appliedDiscounts {\n promotionId\n discountClass\n discountType\n discountAmount\n description\n isAutomatic\n }\n customerEmail\n customerPhone\n shippingAddress\n billingAddress\n paymentMethod\n shippingRateId\n notes\n checkoutStartedAt\n checkoutExpiresAt\n createdAt\n updatedAt\n`;\n\nconst CHECKOUT_START_MUTATION = `\nmutation CheckoutStart {\n checkoutStart {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CHECKOUT_UPDATE_MUTATION = `\nmutation CheckoutUpdate($input: CheckoutUpdateInput!) {\n checkoutUpdate(input: $input) {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CHECKOUT_CONVERT_MUTATION = `\nmutation CheckoutConvert {\n checkoutConvert {\n order {\n id\n orderNumber\n status\n customerEmail\n customerPhone\n shippingAddress\n billingAddress\n subtotal\n total\n note\n items {\n id\n productTitle\n variantTitle\n sku\n quantity\n unitPrice\n totalPrice\n }\n createdAt\n }\n paymentInstructions {\n bankAccount\n recipientName\n referenceNumber\n ipsQrCodeBase64\n expiresAt\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nconst CHECKOUT_ABANDON_MUTATION = `\nmutation CheckoutAbandon {\n checkoutAbandon {\n cart {\n ${CART_FRAGMENT}\n }\n userErrors {\n field\n message\n code\n }\n }\n}\n`;\n\nfunction mapCartData(data: CartData, endpoint: string): Cart {\n return {\n id: data.id,\n token: data.token,\n status: data.status,\n items: data.items.map((item) => ({\n id: item.id,\n variantId: item.variantId,\n quantity: item.quantity,\n priceAtAdd: item.priceAtAdd,\n effectiveUnitPrice: item.effectiveUnitPrice,\n lineTotal: item.lineTotal,\n taxAmount: item.taxAmount,\n variant: item.variant\n ? {\n ...item.variant,\n image: item.variant.image\n ? { ...item.variant.image, url: resolveAssetUrl(item.variant.image.url, endpoint) }\n : null,\n }\n : null,\n })),\n totalItems: data.totalItems,\n totalPrice: data.totalPrice,\n taxTotal: data.taxTotal,\n shippingTotal: data.shippingTotal,\n total: data.total,\n discountTotal: data.discountTotal,\n appliedPromoCode: data.appliedPromoCode,\n appliedDiscounts: data.appliedDiscounts,\n customerEmail: data.customerEmail,\n customerPhone: data.customerPhone,\n shippingAddress: data.shippingAddress,\n billingAddress: data.billingAddress,\n paymentMethod: data.paymentMethod,\n shippingRateId: data.shippingRateId,\n notes: data.notes,\n checkoutStartedAt: data.checkoutStartedAt ?? null,\n checkoutExpiresAt: data.checkoutExpiresAt ?? null,\n createdAt: data.createdAt,\n updatedAt: data.updatedAt,\n };\n}\n\nfunction mapOrderData(data: OrderData, paymentInstructions: PaymentInstructionsData | null): Order {\n return {\n id: data.id,\n orderNumber: data.orderNumber,\n email: data.customerEmail,\n phone: data.customerPhone,\n status: data.status,\n shippingAddress: data.shippingAddress as Address | null,\n subtotal: data.subtotal,\n total: data.total,\n note: data.note,\n items: data.items.map((item) => ({\n id: item.id,\n productTitle: item.productTitle,\n variantTitle: item.variantTitle,\n sku: item.sku,\n quantity: item.quantity,\n unitPrice: item.unitPrice,\n totalPrice: item.totalPrice,\n })),\n paymentInstructions: paymentInstructions ?? null,\n createdAt: data.createdAt,\n };\n}\n\nfunction handleUserErrors(userErrors: UserError[]): ValidationError | StateError | null {\n if (userErrors.length === 0) return null;\n\n const messages = userErrors.map((e) => e.message).join(\"; \");\n\n const stateErrorCodes = [\"CART_NOT_IN_CHECKOUT\", \"CHECKOUT_START_ERROR\", \"CHECKOUT_ABANDON_ERROR\"];\n const stateError = userErrors.find(\n (e) => e.code?.includes(\"STATE\") || e.message.includes(\"state\") || (e.code && stateErrorCodes.includes(e.code)),\n );\n\n if (stateError) {\n return new StateError(messages, \"unknown\");\n }\n\n return new ValidationError(\n messages,\n userErrors.map((e) => ({ field: e.field, message: e.message })),\n );\n}\n\nfunction checkCartIsInCheckout(status: CartStatus): Result<void, StateError> {\n if (status !== \"checkout\") {\n return err(\n new StateError(`Cart must be in 'checkout' state for this operation. Current state: '${status}'.`, status),\n );\n }\n return ok(undefined);\n}\n\nexport interface CheckoutOperations {\n start(): Promise<Result<Cart, StorefrontError>>;\n update(data: CheckoutData): Promise<Result<Cart, StorefrontError>>;\n complete(): Promise<Result<Order, StorefrontError>>;\n abandon(): Promise<Result<Cart, StorefrontError>>;\n}\n\nexport function createCheckoutOperations(\n client: StorefrontClient,\n storage: { get(key: string): string | null; set(key: string, value: string): void; remove(key: string): void },\n): CheckoutOperations {\n return {\n async start(): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CheckoutStartResponse>({\n query: CHECKOUT_START_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.checkoutStart;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async update(data: CheckoutData): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const input: Record<string, unknown> = {};\n if (data.email !== undefined) input.customerEmail = data.email;\n if (data.phone !== undefined) input.customerPhone = data.phone;\n if (data.shippingAddress !== undefined) input.shippingAddress = data.shippingAddress;\n if (data.billingAddress !== undefined) input.billingAddress = data.billingAddress;\n if (data.notes !== undefined) input.notes = data.notes;\n if (data.emailMarketingConsent !== undefined) input.emailMarketingConsent = data.emailMarketingConsent;\n if (data.paymentMethod !== undefined) input.paymentMethod = data.paymentMethod;\n if (data.shippingRateId !== undefined) input.shippingRateId = data.shippingRateId;\n\n const result = await client.mutate<CheckoutUpdateResponse>({\n query: CHECKOUT_UPDATE_MUTATION,\n variables: { input },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.checkoutUpdate;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n const stateCheck = checkCartIsInCheckout(payload.cart.status);\n if (stateCheck.isErr()) {\n return err(stateCheck.error);\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n\n async complete(): Promise<Result<Order, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CheckoutConvertResponse>({\n query: CHECKOUT_CONVERT_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.checkoutConvert;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.order) {\n return err(new NotFoundError(\"Order not found\"));\n }\n\n // Clear cart token on successful order creation\n storage.remove(CART_TOKEN_KEY);\n\n return ok(mapOrderData(payload.order, payload.paymentInstructions));\n },\n\n async abandon(): Promise<Result<Cart, StorefrontError>> {\n const token = storage.get(CART_TOKEN_KEY);\n if (!token) {\n return err(new NotFoundError(\"No cart exists. Call cart.create() first.\"));\n }\n\n const result = await client.mutate<CheckoutAbandonResponse>({\n query: CHECKOUT_ABANDON_MUTATION,\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const payload = result.value.checkoutAbandon;\n const userError = handleUserErrors(payload.userErrors);\n if (userError) {\n return err(userError);\n }\n\n if (!payload.cart) {\n return err(new NotFoundError(\"Cart not found\"));\n }\n\n return ok(mapCartData(payload.cart, client.config.endpoint));\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError } from \"./errors.ts\";\nimport type { Collection, PaginatedResult, Product } from \"./types.ts\";\nimport { normalizeCollectionAssetUrls, normalizeProductAssetUrls, resolveAssetUrl } from \"./url.ts\";\n\nexport interface CollectionsListOptions {\n first?: number;\n after?: string;\n search?: string;\n}\n\nexport type CollectionProductSort = \"manual\" | \"best_selling\" | \"newest\" | \"price_asc\" | \"price_desc\";\n\nexport interface CollectionProductsOptions {\n first?: number;\n after?: string;\n sort?: CollectionProductSort;\n}\n\ninterface CollectionImage {\n url: string;\n altText: string | null;\n width: number | null;\n height: number | null;\n}\n\ninterface RawCollection {\n id: string;\n handle: string;\n title: string;\n description: string | null;\n type: string;\n sortOrder: string;\n metaTitle: string | null;\n metaDescription: string | null;\n productCount: number;\n imageAsset: CollectionImage | null;\n}\n\ninterface CollectionEdge {\n node: RawCollection;\n cursor: string;\n}\n\ninterface CollectionConnection {\n edges: CollectionEdge[];\n pageInfo: {\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n startCursor: string | null;\n endCursor: string | null;\n };\n}\n\ninterface CollectionsQueryResponse {\n collections: CollectionConnection;\n}\n\ninterface CollectionQueryResponse {\n collection: RawCollection | null;\n}\n\nfunction mapRawCollection(raw: RawCollection, endpoint: string): Collection {\n return {\n id: raw.id,\n handle: raw.handle,\n title: raw.title,\n description: raw.description,\n type: raw.type as Collection[\"type\"],\n sortOrder: raw.sortOrder as Collection[\"sortOrder\"],\n metaTitle: raw.metaTitle,\n metaDescription: raw.metaDescription,\n productCount: raw.productCount,\n imageAsset: raw.imageAsset\n ? {\n url: resolveAssetUrl(raw.imageAsset.url, endpoint),\n altText: raw.imageAsset.altText,\n width: raw.imageAsset.width,\n height: raw.imageAsset.height,\n }\n : null,\n };\n}\n\ninterface ProductEdge {\n node: Product;\n cursor: string;\n}\n\ninterface ProductConnection {\n edges: ProductEdge[];\n pageInfo: {\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n startCursor: string | null;\n endCursor: string | null;\n };\n}\n\ninterface CollectionWithProducts {\n id: string;\n products: ProductConnection;\n}\n\ninterface CollectionProductsQueryResponse {\n collection: CollectionWithProducts | null;\n}\n\nconst COLLECTIONS_QUERY = `\nquery Collections($first: Int, $after: String, $search: String) {\n collections(first: $first, after: $after, search: $search) {\n edges {\n node {\n id\n handle\n title\n description\n type\n sortOrder\n metaTitle\n metaDescription\n productCount\n imageAsset {\n url\n altText\n width\n height\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n}\n`;\n\nconst COLLECTION_BY_ID_QUERY = `\nquery CollectionById($id: ID!) {\n collection(id: $id) {\n id\n handle\n title\n description\n type\n sortOrder\n metaTitle\n metaDescription\n productCount\n imageAsset {\n url\n altText\n width\n height\n }\n }\n}\n`;\n\nconst COLLECTION_BY_HANDLE_QUERY = `\nquery CollectionByHandle($handle: String!) {\n collection(handle: $handle) {\n id\n handle\n title\n description\n type\n sortOrder\n metaTitle\n metaDescription\n productCount\n imageAsset {\n url\n altText\n width\n height\n }\n }\n}\n`;\n\nconst COLLECTION_PRODUCTS_BY_ID_QUERY = `\nquery CollectionProductsById($id: ID!, $first: Int, $after: String, $sort: CollectionSortOrder) {\n collection(id: $id) {\n id\n products(first: $first, after: $after, sort: $sort) {\n edges {\n node {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n }\n categories {\n id\n name\n handle\n description\n }\n primaryCategory {\n id\n name\n handle\n }\n tags {\n id\n name\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n }\n}\n`;\n\nconst COLLECTION_PRODUCTS_BY_HANDLE_QUERY = `\nquery CollectionProductsByHandle($handle: String!, $first: Int, $after: String, $sort: CollectionSortOrder) {\n collection(handle: $handle) {\n id\n products(first: $first, after: $after, sort: $sort) {\n edges {\n node {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n }\n categories {\n id\n name\n handle\n description\n }\n primaryCategory {\n id\n name\n handle\n }\n tags {\n id\n name\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n }\n}\n`;\n\nfunction isGlobalId(value: string): boolean {\n if (!value.includes(\":\")) {\n try {\n const decoded = atob(value);\n return decoded.includes(\":\");\n } catch {\n return false;\n }\n }\n return false;\n}\n\nexport interface CollectionsOperations {\n list(options?: CollectionsListOptions): Promise<Result<PaginatedResult<Collection>, StorefrontError>>;\n get(idOrHandle: string): Promise<Result<Collection, StorefrontError>>;\n getProducts(\n idOrHandle: string,\n options?: CollectionProductsOptions,\n ): Promise<Result<PaginatedResult<Product>, StorefrontError>>;\n}\n\nexport function createCollectionsOperations(client: StorefrontClient): CollectionsOperations {\n return {\n async list(options?: CollectionsListOptions): Promise<Result<PaginatedResult<Collection>, StorefrontError>> {\n const result = await client.query<CollectionsQueryResponse>({\n query: COLLECTIONS_QUERY,\n variables: {\n first: options?.first,\n after: options?.after,\n search: options?.search,\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const connection = result.value.collections;\n return ok({\n items: connection.edges.map((edge) => mapRawCollection(edge.node, client.config.endpoint)),\n pageInfo: {\n hasNextPage: connection.pageInfo.hasNextPage,\n hasPreviousPage: connection.pageInfo.hasPreviousPage,\n startCursor: connection.pageInfo.startCursor,\n endCursor: connection.pageInfo.endCursor,\n },\n });\n },\n\n async get(idOrHandle: string): Promise<Result<Collection, StorefrontError>> {\n const useId = isGlobalId(idOrHandle);\n\n const result = await client.query<CollectionQueryResponse>({\n query: useId ? COLLECTION_BY_ID_QUERY : COLLECTION_BY_HANDLE_QUERY,\n variables: useId ? { id: idOrHandle } : { handle: idOrHandle },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.collection) {\n return err(new NotFoundError(`Collection not found: ${idOrHandle}`));\n }\n\n const collection = mapRawCollection(result.value.collection, client.config.endpoint);\n return ok(normalizeCollectionAssetUrls(collection, client.config.endpoint));\n },\n\n async getProducts(\n idOrHandle: string,\n options?: CollectionProductsOptions,\n ): Promise<Result<PaginatedResult<Product>, StorefrontError>> {\n const useId = isGlobalId(idOrHandle);\n\n const result = await client.query<CollectionProductsQueryResponse>({\n query: useId ? COLLECTION_PRODUCTS_BY_ID_QUERY : COLLECTION_PRODUCTS_BY_HANDLE_QUERY,\n variables: {\n ...(useId ? { id: idOrHandle } : { handle: idOrHandle }),\n first: options?.first,\n after: options?.after,\n ...(options?.sort !== undefined && { sort: options.sort }),\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.collection) {\n return err(new NotFoundError(`Collection not found: ${idOrHandle}`));\n }\n\n const connection = result.value.collection.products;\n return ok({\n items: connection.edges.map((edge) => normalizeProductAssetUrls(edge.node, client.config.endpoint)),\n pageInfo: {\n hasNextPage: connection.pageInfo.hasNextPage,\n hasPreviousPage: connection.pageInfo.hasPreviousPage,\n startCursor: connection.pageInfo.startCursor,\n endCursor: connection.pageInfo.endCursor,\n },\n });\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { QueryCache } from \"./cache.ts\";\nimport {\n AuthError,\n GraphQLError,\n NetworkError,\n NotFoundError,\n type StorefrontError,\n ValidationError,\n} from \"./errors.ts\";\n\nexport interface GraphQLRequest {\n query: string;\n variables?: Record<string, unknown>;\n operationName?: string;\n}\n\nexport interface GraphQLResponse<T = unknown> {\n data?: T;\n errors?: Array<{ message: string; path?: readonly (string | number)[] }>;\n}\n\nexport interface GraphQLClientConfig {\n endpoint: string;\n apiKey: string;\n getCartToken: () => string | null;\n getCustomerToken: () => string | null;\n cache: QueryCache;\n cacheTTL: number;\n}\n\nexport interface GraphQLClient {\n query<T>(request: GraphQLRequest, options?: { cache?: boolean }): Promise<Result<T, StorefrontError>>;\n mutate<T>(request: GraphQLRequest): Promise<Result<T, StorefrontError>>;\n}\n\nfunction mapHttpError(status: number, body: string): StorefrontError {\n if (status === 401 || status === 403) {\n let message = \"Authentication failed\";\n try {\n const parsed = JSON.parse(body) as { error?: string; message?: string };\n message = parsed.error ?? parsed.message ?? message;\n } catch {\n // Use default message\n }\n return new AuthError(message);\n }\n\n if (status === 404) {\n return new NotFoundError(\"Resource not found\");\n }\n\n return new GraphQLError(`HTTP error ${status}`, [{ message: body }]);\n}\n\nfunction mapGraphQLErrors(errors: Array<{ message: string; path?: readonly (string | number)[] }>): StorefrontError {\n const messages = errors.map((e) => e.message).join(\"; \");\n return new GraphQLError(messages, errors);\n}\n\nfunction getCacheKey(request: GraphQLRequest): string {\n return JSON.stringify({\n query: request.query,\n variables: request.variables ?? {},\n operationName: request.operationName,\n });\n}\n\nexport function createGraphQLClient(config: GraphQLClientConfig): GraphQLClient {\n async function execute<T>(request: GraphQLRequest): Promise<Result<GraphQLResponse<T>, StorefrontError>> {\n const headers: Record<string, string> = {\n \"Content-Type\": \"application/json\",\n \"x-storefront-key\": config.apiKey,\n };\n\n const cartToken = config.getCartToken();\n if (cartToken) {\n headers[\"x-cart-token\"] = cartToken;\n }\n\n const customerToken = config.getCustomerToken();\n if (customerToken) {\n headers[\"Authorization\"] = `Bearer ${customerToken}`;\n }\n\n let response: Response;\n try {\n response = await fetch(config.endpoint, {\n method: \"POST\",\n headers,\n body: JSON.stringify({\n query: request.query,\n variables: request.variables,\n operationName: request.operationName,\n }),\n });\n } catch (error) {\n const message = error instanceof Error ? error.message : \"Network request failed\";\n return err(new NetworkError(message, { cause: error instanceof Error ? error : undefined }));\n }\n\n if (!response.ok) {\n const body = await response.text().catch(() => \"\");\n return err(mapHttpError(response.status, body));\n }\n\n let json: GraphQLResponse<T>;\n try {\n json = (await response.json()) as GraphQLResponse<T>;\n } catch {\n return err(new GraphQLError(\"Invalid JSON response\", [{ message: \"Failed to parse response\" }]));\n }\n\n return ok(json);\n }\n\n return {\n async query<T>(request: GraphQLRequest, options?: { cache?: boolean }): Promise<Result<T, StorefrontError>> {\n const useCache = options?.cache !== false;\n const cacheKey = getCacheKey(request);\n\n if (useCache) {\n const cached = config.cache.get<T>(cacheKey);\n if (cached !== null) {\n return ok(cached);\n }\n }\n\n const result = await execute<T>(request);\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const response = result.value;\n\n if (response.errors && response.errors.length > 0) {\n return err(mapGraphQLErrors(response.errors));\n }\n\n if (!response.data) {\n return err(new GraphQLError(\"No data in response\", [{ message: \"Response has no data\" }]));\n }\n\n if (useCache) {\n config.cache.set(cacheKey, response.data, config.cacheTTL);\n }\n\n return ok(response.data);\n },\n\n async mutate<T>(request: GraphQLRequest): Promise<Result<T, StorefrontError>> {\n const result = await execute<T>(request);\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const response = result.value;\n\n if (response.errors && response.errors.length > 0) {\n return err(mapGraphQLErrors(response.errors));\n }\n\n if (!response.data) {\n return err(new GraphQLError(\"No data in response\", [{ message: \"Response has no data\" }]));\n }\n\n return ok(response.data);\n },\n };\n}\n\n/**\n * Extract userErrors from mutation result and convert to ValidationError if present\n */\nexport function extractUserErrors<T extends { userErrors?: Array<{ field: string | null; message: string }> }>(\n data: T,\n fieldName: keyof T,\n): Result<Exclude<T[keyof T], undefined>, ValidationError> {\n const payload = data[fieldName];\n if (!payload || typeof payload !== \"object\") {\n return err(new ValidationError(\"Unexpected response format\", []));\n }\n\n const typedPayload = payload as { userErrors?: Array<{ field: string | null; message: string }>; data?: unknown };\n\n if (typedPayload.userErrors && typedPayload.userErrors.length > 0) {\n const messages = typedPayload.userErrors.map((e) => e.message).join(\"; \");\n return err(new ValidationError(messages, typedPayload.userErrors));\n }\n\n return ok(payload as Exclude<T[keyof T], undefined>);\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError } from \"./errors.ts\";\nimport type { AvailablePaymentMethod } from \"./types.ts\";\n\ninterface AvailablePaymentMethodData {\n method: string;\n displayName: string;\n additionalFee: number;\n}\n\ninterface AvailablePaymentMethodsResponse {\n availablePaymentMethods: AvailablePaymentMethodData[];\n}\n\nconst AVAILABLE_PAYMENT_METHODS_QUERY = `\nquery AvailablePaymentMethods {\n availablePaymentMethods {\n method\n displayName\n additionalFee\n }\n}\n`;\n\nfunction mapPaymentMethod(data: AvailablePaymentMethodData): AvailablePaymentMethod {\n return {\n method: data.method,\n displayName: data.displayName,\n additionalFee: data.additionalFee,\n };\n}\n\nexport interface PaymentsOperations {\n getAvailableMethods(): Promise<Result<AvailablePaymentMethod[], StorefrontError>>;\n}\n\nexport function createPaymentsOperations(client: StorefrontClient): PaymentsOperations {\n return {\n async getAvailableMethods(): Promise<Result<AvailablePaymentMethod[], StorefrontError>> {\n const result = await client.query<AvailablePaymentMethodsResponse>(\n { query: AVAILABLE_PAYMENT_METHODS_QUERY },\n { cache: true },\n );\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.availablePaymentMethods) {\n return err(new NotFoundError(\"Payment methods not available\"));\n }\n\n return ok(result.value.availablePaymentMethods.map(mapPaymentMethod));\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError } from \"./errors.ts\";\nimport type { PaginatedResult, Product, ProductFilter, ProductSortKey } from \"./types.ts\";\nimport { normalizeProductAssetUrls } from \"./url.ts\";\n\nexport interface ProductsListOptions {\n first?: number;\n after?: string;\n filter?: ProductFilter;\n sort?: ProductSortKey;\n}\n\ninterface ProductEdge {\n node: Product;\n cursor: string;\n}\n\ninterface ProductConnection {\n edges: ProductEdge[];\n pageInfo: {\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n startCursor: string | null;\n endCursor: string | null;\n };\n}\n\ninterface ProductsQueryResponse {\n products: ProductConnection;\n}\n\ninterface ProductQueryResponse {\n product: Product | null;\n}\n\ninterface ProductsByHandlesQueryResponse {\n productsByHandles: (Product | null)[];\n}\n\nconst PRODUCTS_QUERY = `\nquery Products($first: Int, $after: String, $filter: ProductFilter, $sort: ProductSortKey) {\n products(first: $first, after: $after, filter: $filter, sort: $sort) {\n edges {\n node {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n primaryCategory {\n id\n name\n handle\n }\n tags {\n id\n name\n }\n }\n cursor\n }\n pageInfo {\n hasNextPage\n hasPreviousPage\n startCursor\n endCursor\n }\n }\n}\n`;\n\nconst PRODUCT_BY_ID_QUERY = `\nquery ProductById($id: ID!) {\n product(id: $id) {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n tags {\n id\n name\n }\n }\n}\n`;\n\nconst PRODUCT_BY_HANDLE_QUERY = `\nquery ProductByHandle($handle: String!) {\n product(handle: $handle) {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n tags {\n id\n name\n }\n }\n}\n`;\n\nconst PRODUCTS_BY_HANDLES_QUERY = `\nquery ProductsByHandles($handles: [String!]!) {\n productsByHandles(handles: $handles) {\n id\n handle\n title\n description\n vendor\n productType\n metaTitle\n metaDescription\n publishedAt\n createdAt\n availableForSale\n media {\n id\n url\n altText\n position\n }\n options {\n id\n name\n position\n values {\n id\n value\n position\n }\n }\n variants {\n id\n title\n sku\n price\n compareAtPrice\n weight\n weightUnit\n requiresShipping\n availableForSale\n quantity\n selectedOptions {\n id\n value\n position\n }\n image {\n id\n url\n altText\n position\n }\n isOnSale\n quantityPricing {\n minQuantity\n price\n }\n }\n categories {\n id\n name\n handle\n description\n }\n tags {\n id\n name\n }\n }\n}\n`;\n\nfunction isGlobalId(value: string): boolean {\n if (!value.includes(\":\")) {\n try {\n const decoded = atob(value);\n return decoded.includes(\":\");\n } catch {\n return false;\n }\n }\n return false;\n}\n\nexport interface ProductsOperations {\n list(options?: ProductsListOptions): Promise<Result<PaginatedResult<Product>, StorefrontError>>;\n get(idOrHandle: string): Promise<Result<Product, StorefrontError>>;\n getByHandles(handles: string[]): Promise<Result<(Product | null)[], StorefrontError>>;\n}\n\nexport function createProductsOperations(client: StorefrontClient): ProductsOperations {\n return {\n async list(options?: ProductsListOptions): Promise<Result<PaginatedResult<Product>, StorefrontError>> {\n const result = await client.query<ProductsQueryResponse>({\n query: PRODUCTS_QUERY,\n variables: {\n first: options?.first,\n after: options?.after,\n filter: options?.filter,\n sort: options?.sort,\n },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n const connection = result.value.products;\n return ok({\n items: connection.edges.map((edge) => normalizeProductAssetUrls(edge.node, client.config.endpoint)),\n pageInfo: {\n hasNextPage: connection.pageInfo.hasNextPage,\n hasPreviousPage: connection.pageInfo.hasPreviousPage,\n startCursor: connection.pageInfo.startCursor,\n endCursor: connection.pageInfo.endCursor,\n },\n });\n },\n\n async get(idOrHandle: string): Promise<Result<Product, StorefrontError>> {\n const useId = isGlobalId(idOrHandle);\n\n const result = await client.query<ProductQueryResponse>({\n query: useId ? PRODUCT_BY_ID_QUERY : PRODUCT_BY_HANDLE_QUERY,\n variables: useId ? { id: idOrHandle } : { handle: idOrHandle },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.product) {\n return err(new NotFoundError(`Product not found: ${idOrHandle}`));\n }\n\n return ok(normalizeProductAssetUrls(result.value.product, client.config.endpoint));\n },\n\n async getByHandles(handles: string[]): Promise<Result<(Product | null)[], StorefrontError>> {\n if (handles.length === 0) {\n return ok([]);\n }\n\n const result = await client.query<ProductsByHandlesQueryResponse>({\n query: PRODUCTS_BY_HANDLES_QUERY,\n variables: { handles },\n });\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n return ok(\n result.value.productsByHandles.map((product) =>\n product ? normalizeProductAssetUrls(product, client.config.endpoint) : null,\n ),\n );\n },\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NetworkError } from \"./errors.ts\";\nimport { captureLandingTrackingAttribution, getTrackingAttributionSnapshot } from \"./tracking-attribution.ts\";\n\nconst ANALYTICS_PATH = \"/analytics/ingest\";\nconst VISITOR_COOKIE_NAME = \"srb_vid\";\nconst SESSION_STORAGE_KEY = \"srb_sid\";\nconst SESSION_TIMEOUT_MS = 30 * 60 * 1000;\nconst TRACKING_SCHEMA_VERSION = 1 as const;\nconst UUID_REGEX = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i;\n\n/**\n * Checkout step identifiers for `checkout_step_completed` analytics events.\n */\nexport type CheckoutStep = \"contact\" | \"shipping\" | \"payment\" | \"review\";\n\n/**\n * Canonical analytics event type values accepted by the storefront ingest endpoint.\n */\nexport type AnalyticsEventType =\n | \"analytics.page_view\"\n | \"analytics.product_view\"\n | \"analytics.collection_view\"\n | \"analytics.search_performed\"\n | \"analytics.add_to_cart\"\n | \"analytics.remove_from_cart\"\n | \"analytics.checkout_started\"\n | \"analytics.checkout_step_completed\"\n | \"analytics.checkout_completed\"\n | \"analytics.custom\";\n\nconst ANALYTICS_PRESET_EVENT_MAP = {\n page_view: \"analytics.page_view\",\n product_view: \"analytics.product_view\",\n collection_view: \"analytics.collection_view\",\n search_performed: \"analytics.search_performed\",\n add_to_cart: \"analytics.add_to_cart\",\n remove_from_cart: \"analytics.remove_from_cart\",\n checkout_started: \"analytics.checkout_started\",\n checkout_step_completed: \"analytics.checkout_step_completed\",\n checkout_completed: \"analytics.checkout_completed\",\n} as const;\n\n/**\n * Supported preset event names accepted by `track()`.\n */\nexport type AnalyticsPresetEventName =\n | \"page_view\"\n | \"product_view\"\n | \"collection_view\"\n | \"search_performed\"\n | \"add_to_cart\"\n | \"remove_from_cart\"\n | \"checkout_started\"\n | \"checkout_step_completed\"\n | \"checkout_completed\";\n\n/**\n * Event name accepted by `track()`.\n * Preset names (e.g. `product_view`) are normalized to `analytics.*` types.\n * Unknown names are sent as `analytics.custom` with `{ eventName: <name> }`.\n */\nexport type AnalyticsTrackEventName = AnalyticsPresetEventName | AnalyticsEventType | string;\nexport type AnalyticsConsentState = \"granted\" | \"denied\" | \"unknown\";\n\nexport interface AnalyticsUtm {\n schemaVersion: 1;\n source: string | null;\n medium: string | null;\n campaign: string | null;\n term: string | null;\n content: string | null;\n}\n\nexport interface AnalyticsClickIds {\n schemaVersion: 1;\n capturedAt: string | null;\n gclid: string | null;\n gbraid: string | null;\n wbraid: string | null;\n ttclid: string | null;\n fbclid: string | null;\n}\n\nexport interface AnalyticsEventContextPayload {\n schemaVersion: 1;\n path: string;\n}\n\ntype PresetEventProperties = {\n page_view: {};\n product_view: {\n productId: string;\n variantId?: string | null;\n };\n collection_view: {\n collectionId: string;\n };\n search_performed: {\n query: string;\n resultsCount: number;\n };\n add_to_cart: {\n cartId: string;\n quantity: number;\n itemsCount: number;\n cartValue: number;\n };\n remove_from_cart: {\n cartId: string;\n quantity: number;\n itemsCount: number;\n cartValue: number;\n };\n checkout_started: {\n cartId: string;\n };\n checkout_step_completed: {\n cartId: string;\n step: CheckoutStep;\n };\n checkout_completed: {\n orderId: string;\n cartId: string;\n orderTotal: number;\n };\n};\n\ntype PresetPropertiesByName<T extends AnalyticsPresetEventName> = PresetEventProperties[T];\n\ninterface NormalizedPresetEvent {\n eventType: AnalyticsEventType;\n customEventName?: string;\n}\n\n/**\n * Primitive value allowed in analytics custom event properties.\n */\nexport type AnalyticsJsonPrimitive = string | number | boolean | null;\n\n/**\n * Recursive JSON value allowed in analytics custom event properties.\n */\nexport type AnalyticsJsonValue = AnalyticsJsonPrimitive | AnalyticsJsonValue[] | { [key: string]: AnalyticsJsonValue };\n\n/**\n * Generic analytics event property bag.\n */\nexport interface AnalyticsProperties {\n [key: string]: AnalyticsJsonValue;\n}\n\n/**\n * Optional context overrides for a tracking call.\n */\nexport interface AnalyticsContext {\n storeSlug?: string;\n path?: string;\n referrer?: string | null;\n occurredAt?: Date | string;\n sessionId?: string;\n visitorId?: string;\n customerId?: string | null;\n utmSource?: string | null;\n utmMedium?: string | null;\n utmCampaign?: string | null;\n utmTerm?: string | null;\n utmContent?: string | null;\n consentState?: AnalyticsConsentState;\n clickIds?: Partial<Omit<AnalyticsClickIds, \"schemaVersion\">>;\n deviceType?: string;\n deviceOs?: string | null;\n deviceBrowser?: string | null;\n}\n\n/**\n * Error detail for a single ingest payload item.\n */\nexport interface AnalyticsErrorItem {\n /**\n * Index of the event in the request `events` array.\n */\n index: number;\n\n /**\n * Server-assigned identifier for the event, if available.\n */\n eventId: string | null;\n\n /**\n * Validation or processing error code.\n */\n code: string;\n\n /**\n * Human-readable description of the failure.\n */\n message: string;\n}\n\n/**\n * Response summary from the analytics ingest endpoint.\n */\nexport interface AnalyticsIngestResponse {\n /**\n * Number of events accepted and persisted.\n */\n acceptedCount: number;\n\n /**\n * Number of events recognized as duplicates.\n */\n duplicateCount: number;\n\n /**\n * Number of events rejected by validation or storage.\n */\n rejectedCount: number;\n\n /**\n * Per-item errors, aligned by event index.\n */\n errors: AnalyticsErrorItem[];\n}\n\ninterface AnalyticsEvent {\n schemaVersion: 1;\n eventId: string;\n eventType: AnalyticsEventType | string;\n occurredAt: string;\n sessionId: string;\n visitorId: string;\n customerId: string | null;\n consentState: AnalyticsConsentState;\n context: AnalyticsEventContextPayload;\n referrer: string | null;\n utm: AnalyticsUtm;\n clickIds: AnalyticsClickIds;\n device: {\n deviceType: string;\n deviceOs: string | null;\n deviceBrowser: string | null;\n };\n properties: AnalyticsProperties;\n}\n\ninterface AnalyticsIngestPayload {\n storeSlug: string;\n events: AnalyticsEvent[];\n}\n\ninterface AddToCartProperties {\n cartId: string;\n quantity: number;\n itemsCount: number;\n cartValue: number;\n}\n\ninterface CheckoutCompletedProperties {\n orderId: string;\n cartId: string;\n orderTotal: number;\n}\n\ninterface SessionState {\n id: string;\n startedAt: number;\n lastSeenAt: number;\n}\n\ninterface DeviceInfo {\n deviceType: string;\n deviceOs: string | null;\n deviceBrowser: string | null;\n}\n\ninterface AnalyticsIngestErrorResponse {\n error?: string;\n details?: { message?: string }[];\n}\n\nfunction hasBrowserContext(): boolean {\n return typeof window !== \"undefined\" && typeof document !== \"undefined\";\n}\n\nfunction getDocument(): Document | null {\n return hasBrowserContext() ? document : null;\n}\n\nfunction getWindow(): Window | null {\n return hasBrowserContext() ? window : null;\n}\n\nfunction isUuid(value: string): boolean {\n return UUID_REGEX.test(value);\n}\n\nfunction randomUuid(): string {\n if (typeof crypto !== \"undefined\" && typeof crypto.randomUUID === \"function\") {\n return crypto.randomUUID();\n }\n\n const template = \"xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx\";\n return template.replace(/[xy]/g, (character) => {\n const random = Math.floor(Math.random() * 16);\n const value = character === \"x\" ? random : (random & 0x3) | 0x8;\n return value.toString(16);\n });\n}\n\nfunction getOrCreateVisitorId(): string {\n const doc = getDocument();\n if (doc) {\n const raw = doc.cookie;\n for (const pair of raw.split(\";\")) {\n const [name, ...valueParts] = pair.trim().split(\"=\");\n if (name === VISITOR_COOKIE_NAME) {\n return valueParts.join(\"=\") ? decodeURIComponent(valueParts.join(\"=\")) : randomUuid();\n }\n }\n }\n\n const value = randomUuid();\n if (doc) {\n const maxAge = 60 * 60 * 24 * 365 * 2;\n doc.cookie = `${VISITOR_COOKIE_NAME}=${encodeURIComponent(value)}; Max-Age=${maxAge}; Path=/; SameSite=Lax`;\n }\n\n return value;\n}\n\nlet fallbackSessionState: SessionState | null = null;\n\nfunction getSessionStorageState(): SessionState | null {\n const win = getWindow();\n if (!win) return fallbackSessionState;\n\n try {\n const raw = win.localStorage.getItem(SESSION_STORAGE_KEY);\n if (!raw) return fallbackSessionState;\n\n const parsed = JSON.parse(raw);\n if (typeof parsed !== \"object\" || parsed === null) return null;\n\n const id = parsed.id;\n const startedAt = parsed.startedAt;\n const lastSeenAt = parsed.lastSeenAt;\n if (typeof id !== \"string\" || !id) return null;\n if (typeof startedAt !== \"number\" || typeof lastSeenAt !== \"number\") return null;\n\n return { id, startedAt, lastSeenAt };\n } catch {\n return fallbackSessionState;\n }\n}\n\nfunction setSessionStorageState(state: SessionState): void {\n fallbackSessionState = state;\n const win = getWindow();\n if (!win) return;\n\n try {\n win.localStorage.setItem(SESSION_STORAGE_KEY, JSON.stringify(state));\n } catch {\n // ignore localStorage failures\n }\n}\n\nfunction resolveSessionState(existing: SessionState | null, nowMs: number): SessionState {\n if (!existing) {\n return { id: randomUuid(), startedAt: nowMs, lastSeenAt: nowMs };\n }\n\n if (nowMs - existing.lastSeenAt > SESSION_TIMEOUT_MS) {\n return { id: randomUuid(), startedAt: nowMs, lastSeenAt: nowMs };\n }\n\n return { id: existing.id, startedAt: existing.startedAt, lastSeenAt: nowMs };\n}\n\nfunction getSessionId(nowMs: number): string {\n const existing = getSessionStorageState();\n const state = resolveSessionState(existing, nowMs);\n setSessionStorageState(state);\n return state.id;\n}\n\nfunction normalizeNumber(value: number): number {\n return Number.isFinite(value) ? value : 0;\n}\n\nfunction toCents(amount: number): number {\n return Math.max(0, Math.round(normalizeNumber(amount) * 100));\n}\n\nfunction base64UrlDecode(value: string): string {\n const normalized = value.replace(/-/g, \"+\").replace(/_/g, \"/\");\n const padding = normalized.length % 4;\n const padded = padding === 0 ? normalized : normalized + \"=\".repeat(4 - padding);\n return atob(padded);\n}\n\nfunction parseJWT(payload: string): Record<string, unknown> | null {\n try {\n const decoded = base64UrlDecode(payload);\n const parsed = JSON.parse(decoded);\n return typeof parsed === \"object\" && parsed !== null ? (parsed as Record<string, unknown>) : null;\n } catch {\n return null;\n }\n}\n\nfunction parseCustomerIdFromToken(token: string | null): string | null {\n if (!token) return null;\n\n const payload = token.split(\".\");\n const encodedPayload = payload[1];\n if (!encodedPayload) return null;\n\n const parsed = parseJWT(encodedPayload);\n if (!parsed) return null;\n\n const customerId = parsed.customerId;\n return typeof customerId === \"string\" && isUuid(customerId) ? customerId : null;\n}\n\nfunction decodeAnalyticsEntityId(value: string | null | undefined): string | null {\n if (!value) return null;\n if (isUuid(value)) return value;\n\n if (value.startsWith(\"gid://\")) {\n const parts = value.split(\"/\");\n const candidate = parts[parts.length - 1];\n return candidate && isUuid(candidate) ? candidate : null;\n }\n\n try {\n const decoded = atob(value);\n const parts = decoded.split(\":\");\n const candidate = parts[parts.length - 1];\n return candidate && isUuid(candidate) ? candidate : null;\n } catch {\n return null;\n }\n}\n\nfunction resolveDeviceInfo(): DeviceInfo {\n const win = getWindow();\n if (!win) {\n return { deviceType: \"server\", deviceOs: null, deviceBrowser: null };\n }\n\n const ua = win.navigator.userAgent.toLowerCase();\n\n const deviceType = /ipad|tablet|playbook|silk/.test(ua)\n ? \"tablet\"\n : /mobi|android|iphone|ipod|windows phone/.test(ua)\n ? \"mobile\"\n : \"desktop\";\n\n let deviceOs: string | null = null;\n if (ua.includes(\"windows\")) {\n deviceOs = \"Windows\";\n } else if (ua.includes(\"mac os\") || ua.includes(\"macintosh\")) {\n deviceOs = \"macOS\";\n } else if (ua.includes(\"android\")) {\n deviceOs = \"Android\";\n } else if (ua.includes(\"iphone\") || ua.includes(\"ipad\") || ua.includes(\"ios\")) {\n deviceOs = \"iOS\";\n } else if (ua.includes(\"linux\")) {\n deviceOs = \"Linux\";\n }\n\n let deviceBrowser: string | null = null;\n if (ua.includes(\"edg/\")) {\n deviceBrowser = \"Edge\";\n } else if (ua.includes(\"firefox/\")) {\n deviceBrowser = \"Firefox\";\n } else if (ua.includes(\"chrome/\") && !ua.includes(\"edg/\")) {\n deviceBrowser = \"Chrome\";\n } else if (ua.includes(\"safari/\") && !ua.includes(\"chrome/\")) {\n deviceBrowser = \"Safari\";\n }\n\n return { deviceType, deviceOs, deviceBrowser };\n}\n\nfunction parseStoreSlugFromBase(basePath: string | undefined): string | null {\n if (!basePath) return null;\n\n const segments = basePath.split(\"/\").filter(Boolean);\n if (segments.length < 2) return null;\n\n const [mode, slug] = segments;\n if (mode !== \"preview\" && mode !== \"live\") return null;\n return slug ?? null;\n}\n\nfunction parseStoreSlugFromHostname(hostname: string): string | null {\n if (hostname === \"localhost\") return null;\n if (/^\\d+\\.\\d+\\.\\d+\\.\\d+$/.test(hostname)) return null;\n\n const [candidate] = hostname.split(\".\");\n if (!candidate || candidate === \"www\") return null;\n return candidate;\n}\n\nfunction normalizePath(pathname: string): string {\n return pathname.trim().length > 0 ? pathname : \"/\";\n}\n\nfunction toIsoTimestamp(value: Date | string | number | null | undefined): string | null {\n if (value == null) return null;\n const date = value instanceof Date ? value : new Date(value);\n return Number.isNaN(date.getTime()) ? null : date.toISOString();\n}\n\nfunction buildUtmPayload(context: AnalyticsContext): AnalyticsUtm {\n const persisted = getTrackingAttributionSnapshot();\n return {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n source: context.utmSource ?? persisted?.utm.source ?? null,\n medium: context.utmMedium ?? persisted?.utm.medium ?? null,\n campaign: context.utmCampaign ?? persisted?.utm.campaign ?? null,\n term: context.utmTerm ?? persisted?.utm.term ?? null,\n content: context.utmContent ?? persisted?.utm.content ?? null,\n };\n}\n\nfunction buildClickIdsPayload(context: AnalyticsContext): AnalyticsClickIds {\n const persisted = getTrackingAttributionSnapshot();\n const clickIds = context.clickIds;\n return {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n capturedAt: toIsoTimestamp(clickIds?.capturedAt) ?? persisted?.clickIds.capturedAt ?? null,\n gclid: clickIds?.gclid ?? persisted?.clickIds.gclid ?? null,\n gbraid: clickIds?.gbraid ?? persisted?.clickIds.gbraid ?? null,\n wbraid: clickIds?.wbraid ?? persisted?.clickIds.wbraid ?? null,\n ttclid: clickIds?.ttclid ?? persisted?.clickIds.ttclid ?? null,\n fbclid: clickIds?.fbclid ?? persisted?.clickIds.fbclid ?? null,\n };\n}\n\nfunction buildDefaultContext(storeFallback?: string): AnalyticsContext {\n const context: AnalyticsContext = {};\n const device = resolveDeviceInfo();\n\n const win = getWindow();\n if (win) {\n const { pathname, search, hostname } = win.location;\n context.path = pathname + search;\n context.referrer = win.document.referrer.length > 0 ? win.document.referrer : null;\n const params = new URLSearchParams(win.location.search);\n context.utmSource = params.get(\"utm_source\");\n context.utmMedium = params.get(\"utm_medium\");\n context.utmCampaign = params.get(\"utm_campaign\");\n context.utmTerm = params.get(\"utm_term\");\n context.utmContent = params.get(\"utm_content\");\n context.storeSlug = parseStoreSlugFromBase(pathname) ?? parseStoreSlugFromHostname(hostname) ?? undefined;\n context.deviceType = device.deviceType;\n context.deviceOs = device.deviceOs;\n context.deviceBrowser = device.deviceBrowser;\n }\n\n if (!context.deviceType) {\n context.deviceType = \"unknown\";\n }\n\n if (!context.storeSlug) {\n context.storeSlug = storeFallback;\n }\n\n context.deviceOs ??= null;\n context.deviceBrowser ??= null;\n\n return context;\n}\n\nfunction normalizeEventContext(\n context: AnalyticsContext | undefined,\n storeFallback?: string,\n): { context: AnalyticsContext; storeSlug: string | null } {\n const defaults = buildDefaultContext(storeFallback);\n const merged = { ...defaults, ...context };\n\n return {\n context: merged,\n storeSlug: merged.storeSlug ?? null,\n };\n}\n\nfunction isIngestResponse(value: unknown): value is AnalyticsIngestResponse {\n if (typeof value !== \"object\" || value === null) return false;\n\n const response = value as Record<string, unknown>;\n\n return (\n typeof response.acceptedCount === \"number\" &&\n typeof response.duplicateCount === \"number\" &&\n typeof response.rejectedCount === \"number\" &&\n Array.isArray(response.errors)\n );\n}\n\nfunction extractErrorMessage(response: Response): Promise<string> {\n return response\n .json()\n .then((payload: AnalyticsIngestErrorResponse) => {\n if (typeof payload.error === \"string\" && payload.error.length > 0) {\n return payload.error;\n }\n\n const firstMessage = Array.isArray(payload.details)\n ? payload.details\n .map((error) => (typeof error?.message === \"string\" ? error.message : null))\n .find((message) => message !== null)\n : null;\n\n if (firstMessage) {\n return firstMessage;\n }\n\n return `Analytics ingest failed with status ${response.status}`;\n })\n .catch(() => `Analytics ingest failed with status ${response.status}`);\n}\n\nfunction isPlainObject(value: unknown): value is Record<string, unknown> {\n return typeof value === \"object\" && value !== null && !Array.isArray(value);\n}\n\nfunction resolveTrackEvent(eventName: AnalyticsTrackEventName): NormalizedPresetEvent {\n const normalized = eventName.startsWith(\"analytics.\") ? eventName.slice(\"analytics.\".length) : eventName;\n if (normalized in ANALYTICS_PRESET_EVENT_MAP) {\n return { eventType: ANALYTICS_PRESET_EVENT_MAP[normalized as AnalyticsPresetEventName] };\n }\n\n return {\n eventType: \"analytics.custom\",\n customEventName: eventName,\n };\n}\n\nexport interface AnalyticsOperations {\n /**\n * Track an analytics event.\n *\n * Supports preset event names (`page_view`, `product_view`, `add_to_cart`, etc.),\n * canonical names (`analytics.page_view`, ...), and custom events.\n *\n * Custom event names are sent as `analytics.custom` with `eventName` included in `properties`.\n *\n * @param eventName - Preset/event-name to track.\n * @param context - Optional per-call context overrides.\n * @returns Tracking result with ingest summary, or network/validation error.\n */\n track(eventName: \"page_view\", context?: AnalyticsContext): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track a product page view.\n */\n track(\n eventName: \"product_view\",\n input: PresetPropertiesByName<\"product_view\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track a collection page view.\n */\n track(\n eventName: \"collection_view\",\n input: PresetPropertiesByName<\"collection_view\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track search execution.\n */\n track(\n eventName: \"search_performed\",\n input: PresetPropertiesByName<\"search_performed\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track adding items to cart.\n */\n track(\n eventName: \"add_to_cart\",\n input: PresetPropertiesByName<\"add_to_cart\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track removing items from cart.\n */\n track(\n eventName: \"remove_from_cart\",\n input: PresetPropertiesByName<\"remove_from_cart\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track checkout start.\n */\n track(\n eventName: \"checkout_started\",\n input: PresetPropertiesByName<\"checkout_started\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track checkout step completion.\n */\n track(\n eventName: \"checkout_step_completed\",\n input: PresetPropertiesByName<\"checkout_step_completed\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track successful checkout completion.\n */\n track(\n eventName: \"checkout_completed\",\n input: PresetPropertiesByName<\"checkout_completed\">,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n /**\n * Track a custom analytics event.\n *\n * Example:\n * `client.analytics.track(\"homepage.hero_clicked\", { section: \"hero\", position: 1 })`\n */\n track(\n eventName: string,\n properties: AnalyticsProperties,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>>;\n}\n\n/**\n * Create analytics operations bound to a StorefrontClient.\n */\nexport function createAnalyticsOperations(client: StorefrontClient): AnalyticsOperations {\n captureLandingTrackingAttribution();\n\n const endpoint = (() => {\n try {\n const parsedEndpoint = new URL(client.config.endpoint);\n return `${parsedEndpoint.origin}${ANALYTICS_PATH}`;\n } catch {\n return null;\n }\n })();\n\n const configStoreSlug = client.config.storeSlug;\n\n async function sendEvent(\n eventType: string,\n properties: AnalyticsProperties,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>> {\n if (!endpoint) {\n return err(new NetworkError(\"Invalid storefront endpoint\"));\n }\n\n const resolved = normalizeEventContext(context, configStoreSlug);\n const storeSlug = resolved.storeSlug;\n const eventContext = resolved.context;\n\n if (!storeSlug) {\n return err(new NetworkError(\"Missing storeSlug. Provide storeSlug in client config or event context.\"));\n }\n\n const now = new Date(eventContext.occurredAt ?? Date.now());\n const nowIso = Number.isNaN(now.getTime()) ? new Date().toISOString() : now.toISOString();\n\n const customerId =\n eventContext.customerId === undefined\n ? parseCustomerIdFromToken(client.getCustomerToken())\n : eventContext.customerId;\n\n const event: AnalyticsEvent = {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n eventId: randomUuid(),\n eventType,\n occurredAt: nowIso,\n sessionId: eventContext.sessionId ?? getSessionId(now.getTime()),\n visitorId: eventContext.visitorId ?? getOrCreateVisitorId(),\n customerId: customerId ?? null,\n consentState: eventContext.consentState ?? \"unknown\",\n context: {\n schemaVersion: TRACKING_SCHEMA_VERSION,\n path: normalizePath(eventContext.path ?? \"/\"),\n },\n referrer: eventContext.referrer ?? null,\n utm: buildUtmPayload(eventContext),\n clickIds: buildClickIdsPayload(eventContext),\n device: {\n deviceType: eventContext.deviceType ?? \"unknown\",\n deviceOs: eventContext.deviceOs ?? null,\n deviceBrowser: eventContext.deviceBrowser ?? null,\n },\n properties,\n };\n\n const payload: AnalyticsIngestPayload = {\n storeSlug,\n events: [event],\n };\n\n try {\n const response = await fetch(endpoint, {\n method: \"POST\",\n headers: {\n \"content-type\": \"application/json\",\n },\n body: JSON.stringify(payload),\n });\n\n if (!response.ok) {\n const message = response.headers.get(\"content-type\")?.includes(\"application/json\")\n ? await extractErrorMessage(response)\n : `Analytics ingest failed with status ${response.status}`;\n return err(new NetworkError(message));\n }\n\n const parsed = (await response.json()) as unknown;\n if (!isIngestResponse(parsed)) {\n return err(new NetworkError(\"Analytics response shape is invalid\"));\n }\n\n return ok(parsed);\n } catch (error) {\n return err(\n new NetworkError(\"Failed to send analytics event\", { cause: error instanceof Error ? error : undefined }),\n );\n }\n }\n\n async function track(\n eventName: AnalyticsTrackEventName,\n eventPayload?: AnalyticsProperties | PresetPropertiesByName<AnalyticsPresetEventName> | AnalyticsContext,\n context?: AnalyticsContext,\n ): Promise<Result<AnalyticsIngestResponse, StorefrontError>> {\n const normalized = resolveTrackEvent(eventName);\n\n if (normalized.eventType !== \"analytics.custom\") {\n switch (normalized.eventType) {\n case \"analytics.page_view\": {\n const eventContext =\n context ?? (isPlainObject(eventPayload) ? (eventPayload as AnalyticsContext) : undefined);\n return sendEvent(\"analytics.page_view\", {}, eventContext);\n }\n\n case \"analytics.product_view\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"productId is required\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"product_view\">;\n const decodedProductId = decodeAnalyticsEntityId(payload.productId);\n if (!decodedProductId) {\n return err(new NetworkError(\"Invalid productId\"));\n }\n\n const decodedVariantId = decodeAnalyticsEntityId(payload.variantId);\n return sendEvent(\n \"analytics.product_view\",\n { productId: decodedProductId, variantId: decodedVariantId },\n context,\n );\n }\n\n case \"analytics.collection_view\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"collectionId is required\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"collection_view\">;\n const decodedCollectionId = decodeAnalyticsEntityId(payload.collectionId);\n if (!decodedCollectionId) {\n return err(new NetworkError(\"Invalid collectionId\"));\n }\n\n return sendEvent(\"analytics.collection_view\", { collectionId: decodedCollectionId }, context);\n }\n\n case \"analytics.search_performed\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"query is required\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"search_performed\">;\n const trimmed = payload.query.trim();\n if (!trimmed) {\n return err(new NetworkError(\"query is required\"));\n }\n\n return sendEvent(\n \"analytics.search_performed\",\n { query: trimmed, resultsCount: Math.max(0, Math.floor(payload.resultsCount)) },\n context,\n );\n }\n\n case \"analytics.add_to_cart\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"add_to_cart\">;\n const cartId = decodeAnalyticsEntityId(payload.cartId);\n if (!cartId) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n return sendEvent(\n \"analytics.add_to_cart\",\n {\n cartId,\n quantity: Math.max(1, Math.floor(payload.quantity)),\n itemsCount: Math.max(0, Math.floor(payload.itemsCount)),\n cartValueCents: toCents(payload.cartValue),\n },\n context,\n );\n }\n\n case \"analytics.remove_from_cart\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"remove_from_cart\">;\n const cartId = decodeAnalyticsEntityId(payload.cartId);\n if (!cartId) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n return sendEvent(\n \"analytics.remove_from_cart\",\n {\n cartId,\n quantity: Math.max(1, Math.floor(payload.quantity)),\n itemsCount: Math.max(0, Math.floor(payload.itemsCount)),\n cartValueCents: toCents(payload.cartValue),\n },\n context,\n );\n }\n\n case \"analytics.checkout_started\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"checkout_started\">;\n const decodedCartId = decodeAnalyticsEntityId(payload.cartId);\n if (!decodedCartId) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n return sendEvent(\"analytics.checkout_started\", { cartId: decodedCartId }, context);\n }\n\n case \"analytics.checkout_step_completed\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"checkout_step_completed\">;\n const decodedCartId = decodeAnalyticsEntityId(payload.cartId);\n if (!decodedCartId) {\n return err(new NetworkError(\"Invalid cartId\"));\n }\n\n return sendEvent(\"analytics.checkout_step_completed\", { cartId: decodedCartId, step: payload.step }, context);\n }\n\n case \"analytics.checkout_completed\": {\n if (!isPlainObject(eventPayload)) {\n return err(new NetworkError(\"Invalid orderId or cartId\"));\n }\n\n const payload = eventPayload as PresetPropertiesByName<\"checkout_completed\">;\n const orderId = decodeAnalyticsEntityId(payload.orderId);\n const cartId = decodeAnalyticsEntityId(payload.cartId);\n if (!orderId || !cartId) {\n return err(new NetworkError(\"Invalid orderId or cartId\"));\n }\n\n return sendEvent(\n \"analytics.checkout_completed\",\n {\n orderId,\n cartId,\n orderTotalCents: toCents(payload.orderTotal),\n },\n context,\n );\n }\n }\n }\n\n const properties = isPlainObject(eventPayload) ? eventPayload : {};\n return sendEvent(\n \"analytics.custom\",\n { ...properties, eventName: normalized.customEventName ?? eventName },\n context,\n );\n }\n\n return {\n track,\n };\n}\n","import { err, ok, type Result } from \"neverthrow\";\nimport type { StorefrontClient } from \"./client.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { NotFoundError } from \"./errors.ts\";\nimport type { ShippingRate } from \"./types.ts\";\n\ninterface ShippingRateData {\n id: string;\n name: string;\n price: number;\n minOrderAmount: number | null;\n estimatedDaysMin: number | null;\n estimatedDaysMax: number | null;\n isFree: boolean;\n}\n\ninterface AvailableShippingRatesResponse {\n availableShippingRates: ShippingRateData[];\n}\n\nconst AVAILABLE_SHIPPING_RATES_QUERY = `\nquery AvailableShippingRates {\n availableShippingRates {\n id\n name\n price\n minOrderAmount\n estimatedDaysMin\n estimatedDaysMax\n isFree\n }\n}\n`;\n\nfunction mapShippingRate(data: ShippingRateData): ShippingRate {\n return {\n id: data.id,\n name: data.name,\n price: data.price,\n minOrderAmount: data.minOrderAmount,\n estimatedDaysMin: data.estimatedDaysMin,\n estimatedDaysMax: data.estimatedDaysMax,\n isFree: data.isFree,\n };\n}\n\nexport interface ShippingOperations {\n getAvailableRates(): Promise<Result<ShippingRate[], StorefrontError>>;\n}\n\nexport function createShippingOperations(client: StorefrontClient): ShippingOperations {\n return {\n async getAvailableRates(): Promise<Result<ShippingRate[], StorefrontError>> {\n const result = await client.query<AvailableShippingRatesResponse>(\n { query: AVAILABLE_SHIPPING_RATES_QUERY },\n { cache: true },\n );\n\n if (result.isErr()) {\n return err(result.error);\n }\n\n if (!result.value.availableShippingRates) {\n return err(new NotFoundError(\"Shipping rates not available\"));\n }\n\n return ok(result.value.availableShippingRates.map(mapShippingRate));\n },\n };\n}\n","import type { Result } from \"neverthrow\";\nimport { type AccountOperations, createAccountOperations } from \"./account.ts\";\nimport { type AuthOperations, createAuthOperations } from \"./auth.ts\";\nimport { createQueryCache, type QueryCache } from \"./cache.ts\";\nimport { type CartOperations, createCartOperations } from \"./cart.ts\";\nimport { type CategoriesOperations, createCategoriesOperations } from \"./categories.ts\";\nimport { type CheckoutOperations, createCheckoutOperations } from \"./checkout.ts\";\nimport { type CollectionsOperations, createCollectionsOperations } from \"./collections.ts\";\nimport type { StorefrontError } from \"./errors.ts\";\nimport { createGraphQLClient, type GraphQLClient, type GraphQLRequest } from \"./graphql-client.ts\";\nimport { createPaymentsOperations, type PaymentsOperations } from \"./payments.ts\";\nimport { createProductsOperations, type ProductsOperations } from \"./products.ts\";\nimport { createAnalyticsOperations, type AnalyticsOperations } from \"./analytics.ts\";\nimport { createShippingOperations, type ShippingOperations } from \"./shipping.ts\";\nimport { CART_TOKEN_KEY, CUSTOMER_TOKEN_KEY, createDefaultAdapter } from \"./storage.ts\";\nimport type { StorageAdapter, StorefrontClientConfig } from \"./types.ts\";\n\nconst DEFAULT_CACHE_TTL = 5 * 60 * 1000; // 5 minutes\n\nexport interface CacheHelpers {\n clear(): void;\n}\n\nexport interface StorefrontClient {\n readonly config: StorefrontClientConfig;\n readonly cache: CacheHelpers;\n readonly products: ProductsOperations;\n readonly collections: CollectionsOperations;\n readonly categories: CategoriesOperations;\n readonly cart: CartOperations;\n readonly checkout: CheckoutOperations;\n readonly payments: PaymentsOperations;\n readonly auth: AuthOperations;\n readonly account: AccountOperations;\n readonly shipping: ShippingOperations;\n readonly analytics: AnalyticsOperations;\n\n /**\n * Execute a GraphQL query with optional caching\n */\n query<T>(request: GraphQLRequest, options?: { cache?: boolean }): Promise<Result<T, StorefrontError>>;\n\n /**\n * Execute a GraphQL mutation (never cached)\n */\n mutate<T>(request: GraphQLRequest): Promise<Result<T, StorefrontError>>;\n\n /**\n * Get the current cart token from storage\n */\n getCartToken(): string | null;\n\n /**\n * Set the cart token in storage\n */\n setCartToken(token: string): void;\n\n /**\n * Clear the cart token from storage\n */\n clearCartToken(): void;\n\n /**\n * Get the current customer JWT token from storage\n */\n getCustomerToken(): string | null;\n\n /**\n * Set the customer JWT token in storage\n */\n setCustomerToken(token: string): void;\n\n /**\n * Clear the customer JWT token from storage\n */\n clearCustomerToken(): void;\n}\n\ninterface InternalClient extends StorefrontClient {\n readonly _graphql: GraphQLClient;\n readonly _storage: StorageAdapter;\n readonly _queryCache: QueryCache;\n}\n\nexport type { AccountOperations } from \"./account.ts\";\nexport type { AuthOperations } from \"./auth.ts\";\nexport type { CartOperations } from \"./cart.ts\";\nexport type { CategoriesOperations } from \"./categories.ts\";\nexport type { CheckoutOperations } from \"./checkout.ts\";\nexport type { CollectionProductSort, CollectionsOperations } from \"./collections.ts\";\nexport type { PaymentsOperations } from \"./payments.ts\";\nexport type { AnalyticsOperations } from \"./analytics.ts\";\nexport type { ProductsOperations } from \"./products.ts\";\nexport type { ShippingOperations } from \"./shipping.ts\";\n\n/**\n * Create a new Storefront SDK client\n *\n * @param config - Client configuration including endpoint, API key, and optional storage adapter\n * @returns A configured StorefrontClient instance\n *\n * @example\n * ```typescript\n * import { createStorefrontClient } from \"@ekomerc/storefront\";\n *\n * const client = createStorefrontClient({\n * endpoint: \"https://api.mystore.com/storefront\",\n * apiKey: \"sfk_abc123...\",\n * });\n *\n * // Query products\n * const result = await client.query({\n * query: `query { products { edges { node { id title } } } }`,\n * });\n *\n * if (result.isOk()) {\n * console.log(result.value);\n * } else {\n * console.error(result.error);\n * }\n * ```\n */\nexport function createStorefrontClient(config: StorefrontClientConfig): StorefrontClient {\n const storage = config.storage ?? createDefaultAdapter();\n const queryCache = createQueryCache();\n const cacheTTL = config.cacheTTL ?? DEFAULT_CACHE_TTL;\n\n const graphqlClient = createGraphQLClient({\n endpoint: config.endpoint,\n apiKey: config.apiKey,\n getCartToken: () => storage.get(CART_TOKEN_KEY),\n getCustomerToken: () => storage.get(CUSTOMER_TOKEN_KEY),\n cache: queryCache,\n cacheTTL,\n });\n\n const client: InternalClient = {\n config,\n _graphql: graphqlClient,\n _storage: storage,\n _queryCache: queryCache,\n\n cache: {\n clear(): void {\n queryCache.clear();\n },\n },\n\n // Placeholder - will be assigned below\n products: null as unknown as ProductsOperations,\n collections: null as unknown as CollectionsOperations,\n categories: null as unknown as CategoriesOperations,\n cart: null as unknown as CartOperations,\n checkout: null as unknown as CheckoutOperations,\n payments: null as unknown as PaymentsOperations,\n auth: null as unknown as AuthOperations,\n account: null as unknown as AccountOperations,\n shipping: null as unknown as ShippingOperations,\n analytics: null as unknown as AnalyticsOperations,\n\n query<T>(request: GraphQLRequest, options?: { cache?: boolean }): Promise<Result<T, StorefrontError>> {\n return graphqlClient.query<T>(request, options);\n },\n\n mutate<T>(request: GraphQLRequest): Promise<Result<T, StorefrontError>> {\n return graphqlClient.mutate<T>(request);\n },\n\n getCartToken(): string | null {\n return storage.get(CART_TOKEN_KEY);\n },\n\n setCartToken(token: string): void {\n storage.set(CART_TOKEN_KEY, token);\n },\n\n clearCartToken(): void {\n storage.remove(CART_TOKEN_KEY);\n },\n\n getCustomerToken(): string | null {\n return storage.get(CUSTOMER_TOKEN_KEY);\n },\n\n setCustomerToken(token: string): void {\n storage.set(CUSTOMER_TOKEN_KEY, token);\n },\n\n clearCustomerToken(): void {\n storage.remove(CUSTOMER_TOKEN_KEY);\n },\n };\n\n // Create operations after client is created to avoid circular reference\n (client as { products: ProductsOperations }).products = createProductsOperations(client);\n (client as { collections: CollectionsOperations }).collections = createCollectionsOperations(client);\n (client as { categories: CategoriesOperations }).categories = createCategoriesOperations(client);\n (client as { cart: CartOperations }).cart = createCartOperations(client, storage);\n (client as { checkout: CheckoutOperations }).checkout = createCheckoutOperations(client, storage);\n (client as { payments: PaymentsOperations }).payments = createPaymentsOperations(client);\n (client as { auth: AuthOperations }).auth = createAuthOperations(client, storage);\n (client as { account: AccountOperations }).account = createAccountOperations(client, storage);\n (client as { shipping: ShippingOperations }).shipping = createShippingOperations(client);\n (client as { analytics: AnalyticsOperations }).analytics = createAnalyticsOperations(client);\n\n return client;\n}\n"],"names":["handleUserErrors","TRACKING_SCHEMA_VERSION","hasBrowserContext","CART_FRAGMENT","mapCartData","isGlobalId"],"mappings":"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;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAwFvB,MAAM,sBAAsB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAwE5B,MAAM,0BAA0B;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAwEhC,MAAM,4BAA4B;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AA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"}
package/dist/types.cjs ADDED
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ //# sourceMappingURL=types.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.cjs","sources":[],"sourcesContent":[],"names":[],"mappings":""}
@@ -0,0 +1 @@
1
+ export { }
package/dist/types.js ADDED
@@ -0,0 +1,2 @@
1
+
2
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sources":[],"sourcesContent":[],"names":[],"mappings":""}
package/package.json ADDED
@@ -0,0 +1,68 @@
1
+ {
2
+ "name": "@ekomerc/storefront",
3
+ "version": "0.1.0",
4
+ "description": "TypeScript SDK for ekomerc storefronts",
5
+ "type": "module",
6
+ "main": "./dist/index.cjs",
7
+ "module": "./dist/index.js",
8
+ "types": "./dist/index.d.ts",
9
+ "exports": {
10
+ ".": {
11
+ "import": {
12
+ "types": "./dist/index.d.ts",
13
+ "default": "./dist/index.js"
14
+ },
15
+ "require": {
16
+ "types": "./dist/index.d.cts",
17
+ "default": "./dist/index.cjs"
18
+ }
19
+ },
20
+ "./types": {
21
+ "import": {
22
+ "types": "./dist/types.d.ts",
23
+ "default": "./dist/types.js"
24
+ },
25
+ "require": {
26
+ "types": "./dist/types.d.cts",
27
+ "default": "./dist/types.cjs"
28
+ }
29
+ },
30
+ "./errors": {
31
+ "import": {
32
+ "types": "./dist/errors.d.ts",
33
+ "default": "./dist/errors.js"
34
+ },
35
+ "require": {
36
+ "types": "./dist/errors.d.cts",
37
+ "default": "./dist/errors.cjs"
38
+ }
39
+ }
40
+ },
41
+ "files": [
42
+ "dist"
43
+ ],
44
+ "sideEffects": false,
45
+ "scripts": {
46
+ "build": "vite build",
47
+ "typecheck": "tsc -b --noEmit",
48
+ "codegen": "graphql-codegen --config codegen.ts",
49
+ "lint": "biome lint --fix ./src",
50
+ "lint:check": "biome lint ./src",
51
+ "format": "biome format --write ./src",
52
+ "format:check": "biome format ./src",
53
+ "test": "vitest run"
54
+ },
55
+ "dependencies": {
56
+ "neverthrow": "catalog:"
57
+ },
58
+ "devDependencies": {
59
+ "@graphql-codegen/cli": "^6.1.1",
60
+ "@graphql-codegen/typescript": "^4.1.5",
61
+ "@graphql-codegen/typescript-operations": "^4.5.1",
62
+ "@yourcompany/configs": "workspace:*",
63
+ "typescript": "catalog:",
64
+ "vite": "catalog:",
65
+ "vite-plugin-dts": "^4.5.4",
66
+ "vitest": "catalog:"
67
+ }
68
+ }