@commercengine/storefront-sdk 0.14.0 → 0.14.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +21 -16
- package/dist/index.iife.js +39 -24
- package/dist/index.iife.js.map +1 -1
- package/dist/index.mjs +39 -24
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.iife.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.iife.js","names":[],"sources":["../../../node_modules/.pnpm/openapi-fetch@0.17.0/node_modules/openapi-fetch/dist/index.mjs","../../sdk-core/dist/index.mjs","../src/lib/shared/url-utils.ts","../src/lib/shared/client.ts","../src/lib/session/client.ts","../src/lib/shared/catalog.ts","../src/lib/public/catalog.ts","../src/lib/catalog.ts","../src/lib/cart.ts","../src/lib/auth.ts","../src/lib/order.ts","../src/lib/payments.ts","../src/lib/shared/helper.ts","../src/lib/public/helper.ts","../src/lib/helper.ts","../src/lib/customer.ts","../src/lib/shared/store-config.ts","../src/lib/public/store-config.ts","../src/lib/store-config.ts","../src/lib/storage/token-storage.ts","../src/lib/session/jwt-utils.ts","../src/types/auth-operation-metadata.ts","../src/lib/session/auth-utils.ts","../src/lib/session/manager.ts","../src/lib/public/client.ts","../src/index.ts"],"sourcesContent":["const PATH_PARAM_RE = /\\{[^{}]+\\}/g;\nconst supportsRequestInitExt = () => {\n return typeof process === \"object\" && Number.parseInt(process?.versions?.node?.substring(0, 2)) >= 18 && process.versions.undici;\n};\nfunction randomID() {\n return Math.random().toString(36).slice(2, 11);\n}\nfunction createClient(clientOptions) {\n let {\n baseUrl = \"\",\n Request: CustomRequest = globalThis.Request,\n fetch: baseFetch = globalThis.fetch,\n querySerializer: globalQuerySerializer,\n bodySerializer: globalBodySerializer,\n pathSerializer: globalPathSerializer,\n headers: baseHeaders,\n requestInitExt = void 0,\n ...baseOptions\n } = { ...clientOptions };\n requestInitExt = supportsRequestInitExt() ? requestInitExt : void 0;\n baseUrl = removeTrailingSlash(baseUrl);\n const globalMiddlewares = [];\n async function coreFetch(schemaPath, fetchOptions) {\n const {\n baseUrl: localBaseUrl,\n fetch = baseFetch,\n Request = CustomRequest,\n headers,\n params = {},\n parseAs = \"json\",\n querySerializer: requestQuerySerializer,\n bodySerializer = globalBodySerializer ?? defaultBodySerializer,\n pathSerializer: requestPathSerializer,\n body,\n middleware: requestMiddlewares = [],\n ...init\n } = fetchOptions || {};\n let finalBaseUrl = baseUrl;\n if (localBaseUrl) {\n finalBaseUrl = removeTrailingSlash(localBaseUrl) ?? baseUrl;\n }\n let querySerializer = typeof globalQuerySerializer === \"function\" ? globalQuerySerializer : createQuerySerializer(globalQuerySerializer);\n if (requestQuerySerializer) {\n querySerializer = typeof requestQuerySerializer === \"function\" ? requestQuerySerializer : createQuerySerializer({\n ...typeof globalQuerySerializer === \"object\" ? globalQuerySerializer : {},\n ...requestQuerySerializer\n });\n }\n const pathSerializer = requestPathSerializer || globalPathSerializer || defaultPathSerializer;\n const serializedBody = body === void 0 ? void 0 : bodySerializer(\n body,\n // Note: we declare mergeHeaders() both here and below because it’s a bit of a chicken-or-egg situation:\n // bodySerializer() needs all headers so we aren’t dropping ones set by the user, however,\n // the result of this ALSO sets the lowest-priority content-type header. So we re-merge below,\n // setting the content-type at the very beginning to be overwritten.\n // Lastly, based on the way headers work, it’s not a simple “present-or-not” check becauase null intentionally un-sets headers.\n mergeHeaders(baseHeaders, headers, params.header)\n );\n const finalHeaders = mergeHeaders(\n // with no body, we should not to set Content-Type\n serializedBody === void 0 || // if serialized body is FormData; browser will correctly set Content-Type & boundary expression\n serializedBody instanceof FormData ? {} : {\n \"Content-Type\": \"application/json\"\n },\n baseHeaders,\n headers,\n params.header\n );\n const finalMiddlewares = [...globalMiddlewares, ...requestMiddlewares];\n const requestInit = {\n redirect: \"follow\",\n ...baseOptions,\n ...init,\n body: serializedBody,\n headers: finalHeaders\n };\n let id;\n let options;\n let request = new Request(\n createFinalURL(schemaPath, { baseUrl: finalBaseUrl, params, querySerializer, pathSerializer }),\n requestInit\n );\n let response;\n for (const key in init) {\n if (!(key in request)) {\n request[key] = init[key];\n }\n }\n if (finalMiddlewares.length) {\n id = randomID();\n options = Object.freeze({\n baseUrl: finalBaseUrl,\n fetch,\n parseAs,\n querySerializer,\n bodySerializer,\n pathSerializer\n });\n for (const m of finalMiddlewares) {\n if (m && typeof m === \"object\" && typeof m.onRequest === \"function\") {\n const result = await m.onRequest({\n request,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (result instanceof Request) {\n request = result;\n } else if (result instanceof Response) {\n response = result;\n break;\n } else {\n throw new Error(\"onRequest: must return new Request() or Response() when modifying the request\");\n }\n }\n }\n }\n }\n if (!response) {\n try {\n response = await fetch(request, requestInitExt);\n } catch (error2) {\n let errorAfterMiddleware = error2;\n if (finalMiddlewares.length) {\n for (let i = finalMiddlewares.length - 1; i >= 0; i--) {\n const m = finalMiddlewares[i];\n if (m && typeof m === \"object\" && typeof m.onError === \"function\") {\n const result = await m.onError({\n request,\n error: errorAfterMiddleware,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (result instanceof Response) {\n errorAfterMiddleware = void 0;\n response = result;\n break;\n }\n if (result instanceof Error) {\n errorAfterMiddleware = result;\n continue;\n }\n throw new Error(\"onError: must return new Response() or instance of Error\");\n }\n }\n }\n }\n if (errorAfterMiddleware) {\n throw errorAfterMiddleware;\n }\n }\n if (finalMiddlewares.length) {\n for (let i = finalMiddlewares.length - 1; i >= 0; i--) {\n const m = finalMiddlewares[i];\n if (m && typeof m === \"object\" && typeof m.onResponse === \"function\") {\n const result = await m.onResponse({\n request,\n response,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (!(result instanceof Response)) {\n throw new Error(\"onResponse: must return new Response() when modifying the response\");\n }\n response = result;\n }\n }\n }\n }\n }\n const contentLength = response.headers.get(\"Content-Length\");\n if (response.status === 204 || request.method === \"HEAD\" || contentLength === \"0\" && !response.headers.get(\"Transfer-Encoding\")?.includes(\"chunked\")) {\n return response.ok ? { data: void 0, response } : { error: void 0, response };\n }\n if (response.ok) {\n const getResponseData = async () => {\n if (parseAs === \"stream\") {\n return response.body;\n }\n if (parseAs === \"json\" && !contentLength) {\n const raw = await response.text();\n return raw ? JSON.parse(raw) : void 0;\n }\n return await response[parseAs]();\n };\n return { data: await getResponseData(), response };\n }\n let error = await response.text();\n try {\n error = JSON.parse(error);\n } catch {\n }\n return { error, response };\n }\n return {\n request(method, url, init) {\n return coreFetch(url, { ...init, method: method.toUpperCase() });\n },\n /** Call a GET endpoint */\n GET(url, init) {\n return coreFetch(url, { ...init, method: \"GET\" });\n },\n /** Call a PUT endpoint */\n PUT(url, init) {\n return coreFetch(url, { ...init, method: \"PUT\" });\n },\n /** Call a POST endpoint */\n POST(url, init) {\n return coreFetch(url, { ...init, method: \"POST\" });\n },\n /** Call a DELETE endpoint */\n DELETE(url, init) {\n return coreFetch(url, { ...init, method: \"DELETE\" });\n },\n /** Call a OPTIONS endpoint */\n OPTIONS(url, init) {\n return coreFetch(url, { ...init, method: \"OPTIONS\" });\n },\n /** Call a HEAD endpoint */\n HEAD(url, init) {\n return coreFetch(url, { ...init, method: \"HEAD\" });\n },\n /** Call a PATCH endpoint */\n PATCH(url, init) {\n return coreFetch(url, { ...init, method: \"PATCH\" });\n },\n /** Call a TRACE endpoint */\n TRACE(url, init) {\n return coreFetch(url, { ...init, method: \"TRACE\" });\n },\n /** Register middleware */\n use(...middleware) {\n for (const m of middleware) {\n if (!m) {\n continue;\n }\n if (typeof m !== \"object\" || !(\"onRequest\" in m || \"onResponse\" in m || \"onError\" in m)) {\n throw new Error(\"Middleware must be an object with one of `onRequest()`, `onResponse() or `onError()`\");\n }\n globalMiddlewares.push(m);\n }\n },\n /** Unregister middleware */\n eject(...middleware) {\n for (const m of middleware) {\n const i = globalMiddlewares.indexOf(m);\n if (i !== -1) {\n globalMiddlewares.splice(i, 1);\n }\n }\n }\n };\n}\nclass PathCallForwarder {\n constructor(client, url) {\n this.client = client;\n this.url = url;\n }\n GET = (init) => {\n return this.client.GET(this.url, init);\n };\n PUT = (init) => {\n return this.client.PUT(this.url, init);\n };\n POST = (init) => {\n return this.client.POST(this.url, init);\n };\n DELETE = (init) => {\n return this.client.DELETE(this.url, init);\n };\n OPTIONS = (init) => {\n return this.client.OPTIONS(this.url, init);\n };\n HEAD = (init) => {\n return this.client.HEAD(this.url, init);\n };\n PATCH = (init) => {\n return this.client.PATCH(this.url, init);\n };\n TRACE = (init) => {\n return this.client.TRACE(this.url, init);\n };\n}\nclass PathClientProxyHandler {\n constructor() {\n this.client = null;\n }\n // Assume the property is an URL.\n get(coreClient, url) {\n const forwarder = new PathCallForwarder(coreClient, url);\n this.client[url] = forwarder;\n return forwarder;\n }\n}\nfunction wrapAsPathBasedClient(coreClient) {\n const handler = new PathClientProxyHandler();\n const proxy = new Proxy(coreClient, handler);\n function Client() {\n }\n Client.prototype = proxy;\n const client = new Client();\n handler.client = client;\n return client;\n}\nfunction createPathBasedClient(clientOptions) {\n return wrapAsPathBasedClient(createClient(clientOptions));\n}\nfunction serializePrimitiveParam(name, value, options) {\n if (value === void 0 || value === null) {\n return \"\";\n }\n if (typeof value === \"object\") {\n throw new Error(\n \"Deeply-nested arrays/objects aren\\u2019t supported. Provide your own `querySerializer()` to handle these.\"\n );\n }\n return `${name}=${options?.allowReserved === true ? value : encodeURIComponent(value)}`;\n}\nfunction serializeObjectParam(name, value, options) {\n if (!value || typeof value !== \"object\") {\n return \"\";\n }\n const values = [];\n const joiner = {\n simple: \",\",\n label: \".\",\n matrix: \";\"\n }[options.style] || \"&\";\n if (options.style !== \"deepObject\" && options.explode === false) {\n for (const k in value) {\n values.push(k, options.allowReserved === true ? value[k] : encodeURIComponent(value[k]));\n }\n const final2 = values.join(\",\");\n switch (options.style) {\n case \"form\": {\n return `${name}=${final2}`;\n }\n case \"label\": {\n return `.${final2}`;\n }\n case \"matrix\": {\n return `;${name}=${final2}`;\n }\n default: {\n return final2;\n }\n }\n }\n for (const k in value) {\n const finalName = options.style === \"deepObject\" ? `${name}[${k}]` : k;\n values.push(serializePrimitiveParam(finalName, value[k], options));\n }\n const final = values.join(joiner);\n return options.style === \"label\" || options.style === \"matrix\" ? `${joiner}${final}` : final;\n}\nfunction serializeArrayParam(name, value, options) {\n if (!Array.isArray(value)) {\n return \"\";\n }\n if (options.explode === false) {\n const joiner2 = { form: \",\", spaceDelimited: \"%20\", pipeDelimited: \"|\" }[options.style] || \",\";\n const final = (options.allowReserved === true ? value : value.map((v) => encodeURIComponent(v))).join(joiner2);\n switch (options.style) {\n case \"simple\": {\n return final;\n }\n case \"label\": {\n return `.${final}`;\n }\n case \"matrix\": {\n return `;${name}=${final}`;\n }\n // case \"spaceDelimited\":\n // case \"pipeDelimited\":\n default: {\n return `${name}=${final}`;\n }\n }\n }\n const joiner = { simple: \",\", label: \".\", matrix: \";\" }[options.style] || \"&\";\n const values = [];\n for (const v of value) {\n if (options.style === \"simple\" || options.style === \"label\") {\n values.push(options.allowReserved === true ? v : encodeURIComponent(v));\n } else {\n values.push(serializePrimitiveParam(name, v, options));\n }\n }\n return options.style === \"label\" || options.style === \"matrix\" ? `${joiner}${values.join(joiner)}` : values.join(joiner);\n}\nfunction createQuerySerializer(options) {\n return function querySerializer(queryParams) {\n const search = [];\n if (queryParams && typeof queryParams === \"object\") {\n for (const name in queryParams) {\n const value = queryParams[name];\n if (value === void 0 || value === null) {\n continue;\n }\n if (Array.isArray(value)) {\n if (value.length === 0) {\n continue;\n }\n search.push(\n serializeArrayParam(name, value, {\n style: \"form\",\n explode: true,\n ...options?.array,\n allowReserved: options?.allowReserved || false\n })\n );\n continue;\n }\n if (typeof value === \"object\") {\n search.push(\n serializeObjectParam(name, value, {\n style: \"deepObject\",\n explode: true,\n ...options?.object,\n allowReserved: options?.allowReserved || false\n })\n );\n continue;\n }\n search.push(serializePrimitiveParam(name, value, options));\n }\n }\n return search.join(\"&\");\n };\n}\nfunction defaultPathSerializer(pathname, pathParams) {\n let nextURL = pathname;\n for (const match of pathname.match(PATH_PARAM_RE) ?? []) {\n let name = match.substring(1, match.length - 1);\n let explode = false;\n let style = \"simple\";\n if (name.endsWith(\"*\")) {\n explode = true;\n name = name.substring(0, name.length - 1);\n }\n if (name.startsWith(\".\")) {\n style = \"label\";\n name = name.substring(1);\n } else if (name.startsWith(\";\")) {\n style = \"matrix\";\n name = name.substring(1);\n }\n if (!pathParams || pathParams[name] === void 0 || pathParams[name] === null) {\n continue;\n }\n const value = pathParams[name];\n if (Array.isArray(value)) {\n nextURL = nextURL.replace(match, serializeArrayParam(name, value, { style, explode }));\n continue;\n }\n if (typeof value === \"object\") {\n nextURL = nextURL.replace(match, serializeObjectParam(name, value, { style, explode }));\n continue;\n }\n if (style === \"matrix\") {\n nextURL = nextURL.replace(match, `;${serializePrimitiveParam(name, value)}`);\n continue;\n }\n nextURL = nextURL.replace(match, style === \"label\" ? `.${encodeURIComponent(value)}` : encodeURIComponent(value));\n }\n return nextURL;\n}\nfunction defaultBodySerializer(body, headers) {\n if (body instanceof FormData) {\n return body;\n }\n if (headers) {\n const contentType = headers.get instanceof Function ? headers.get(\"Content-Type\") ?? headers.get(\"content-type\") : headers[\"Content-Type\"] ?? headers[\"content-type\"];\n if (contentType === \"application/x-www-form-urlencoded\") {\n return new URLSearchParams(body).toString();\n }\n }\n return JSON.stringify(body);\n}\nfunction createFinalURL(pathname, options) {\n let finalURL = `${options.baseUrl}${pathname}`;\n if (options.params?.path) {\n finalURL = options.pathSerializer(finalURL, options.params.path);\n }\n let search = options.querySerializer(options.params.query ?? {});\n if (search.startsWith(\"?\")) {\n search = search.substring(1);\n }\n if (search) {\n finalURL += `?${search}`;\n }\n return finalURL;\n}\nfunction mergeHeaders(...allHeaders) {\n const finalHeaders = new Headers();\n for (const h of allHeaders) {\n if (!h || typeof h !== \"object\") {\n continue;\n }\n const iterator = h instanceof Headers ? h.entries() : Object.entries(h);\n for (const [k, v] of iterator) {\n if (v === null) {\n finalHeaders.delete(k);\n } else if (Array.isArray(v)) {\n for (const v2 of v) {\n finalHeaders.append(k, v2);\n }\n } else if (v !== void 0) {\n finalHeaders.set(k, v);\n }\n }\n }\n return finalHeaders;\n}\nfunction removeTrailingSlash(url) {\n if (url.endsWith(\"/\")) {\n return url.substring(0, url.length - 1);\n }\n return url;\n}\n\nexport { createFinalURL, createPathBasedClient, createQuerySerializer, createClient as default, defaultBodySerializer, defaultPathSerializer, mergeHeaders, randomID, removeTrailingSlash, serializeArrayParam, serializeObjectParam, serializePrimitiveParam, wrapAsPathBasedClient };\n//# sourceMappingURL=index.mjs.map\n","import createClient from \"openapi-fetch\";\n\n//#region src/middleware/debug.ts\n/**\n* Response utilities for debugging and working with Response objects\n*/\nvar ResponseUtils = class {\n\t/**\n\t* Get response headers as a plain object\n\t*/\n\tstatic getHeaders(response) {\n\t\treturn Object.fromEntries(response.headers.entries());\n\t}\n\t/**\n\t* Get specific header value\n\t*/\n\tstatic getHeader(response, name) {\n\t\treturn response.headers.get(name);\n\t}\n\t/**\n\t* Check if response was successful\n\t*/\n\tstatic isSuccess(response) {\n\t\treturn response.ok;\n\t}\n\t/**\n\t* Get response metadata\n\t*/\n\tstatic getMetadata(response) {\n\t\treturn {\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\tok: response.ok,\n\t\t\turl: response.url,\n\t\t\tredirected: response.redirected,\n\t\t\ttype: response.type,\n\t\t\theaders: Object.fromEntries(response.headers.entries())\n\t\t};\n\t}\n\t/**\n\t* Clone and read response as text (useful for debugging)\n\t* Note: This can only be called once per response\n\t*/\n\tstatic async getText(response) {\n\t\treturn await response.clone().text();\n\t}\n\t/**\n\t* Clone and read response as JSON (useful for debugging)\n\t* Note: This can only be called once per response\n\t*/\n\tstatic async getJSON(response) {\n\t\treturn await response.clone().json();\n\t}\n\t/**\n\t* Format response information for debugging\n\t*/\n\tstatic format(response) {\n\t\tconst metadata = this.getMetadata(response);\n\t\treturn `${metadata.status} ${metadata.statusText} - ${metadata.url}`;\n\t}\n\t/**\n\t* Format response for logging purposes (enhanced version)\n\t*/\n\tstatic formatResponse(response) {\n\t\treturn {\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\turl: response.url,\n\t\t\tok: response.ok\n\t\t};\n\t}\n};\n/**\n* Debug logging utilities\n*/\nvar DebugLogger = class {\n\tlogger;\n\tconstructor(logger) {\n\t\tthis.logger = logger || ((level, message, data) => {\n\t\t\tconsole.log(`[${level.toUpperCase()}]`, message);\n\t\t\tif (data) console.log(data);\n\t\t});\n\t}\n\t/**\n\t* Log debug information about API request\n\t*/\n\tlogRequest(request, requestBody) {\n\t\tthis.logger(\"info\", \"API Request Debug Info\", {\n\t\t\tmethod: request.method,\n\t\t\turl: request.url,\n\t\t\theaders: Object.fromEntries(request.headers.entries()),\n\t\t\tbody: requestBody,\n\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t});\n\t}\n\t/**\n\t* Log debug information about API response\n\t*/\n\tasync logResponse(response, responseBody) {\n\t\tthis.logger(\"info\", \"API Response Debug Info\", {\n\t\t\turl: response.url,\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\tok: response.ok,\n\t\t\theaders: Object.fromEntries(response.headers.entries()),\n\t\t\tredirected: response.redirected,\n\t\t\ttype: response.type,\n\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t});\n\t\tif (responseBody) this.logger(\"info\", \"API Response Data\", {\n\t\t\tdata: responseBody,\n\t\t\tcontentType: response.headers.get(\"content-type\"),\n\t\t\tcontentLength: response.headers.get(\"content-length\")\n\t\t});\n\t}\n\t/**\n\t* Log error information\n\t*/\n\tlogError(message, error) {\n\t\tthis.logger(\"error\", message, error);\n\t}\n\t/**\n\t* Compatibility shim retained for older internal callers.\n\t* Response bodies are no longer cached by the debug logger.\n\t*/\n\tgetCachedResponseText(_url) {\n\t\treturn null;\n\t}\n\t/**\n\t* Compatibility shim retained for older internal callers.\n\t* Response bodies are no longer cached by the debug logger.\n\t*/\n\tclearCache() {}\n\tinfo(message, data) {\n\t\tthis.logger(\"info\", message, data);\n\t}\n\twarn(message, data) {\n\t\tthis.logger(\"warn\", message, data);\n\t}\n\terror(message, data) {\n\t\tthis.logger(\"error\", message, data);\n\t}\n};\n/**\n* Extract request body for logging\n*/\nasync function extractRequestBody(request) {\n\tif (request.method === \"GET\" || request.method === \"HEAD\") return null;\n\ttry {\n\t\tconst clonedRequest = request.clone();\n\t\tconst contentType = request.headers.get(\"content-type\")?.toLowerCase();\n\t\tif (contentType?.startsWith(\"application/json\")) return await clonedRequest.json();\n\t\telse if (contentType?.startsWith(\"multipart/form-data\")) return \"[FormData - cannot display]\";\n\t\telse if (contentType?.startsWith(\"text/\")) return await clonedRequest.text();\n\t\treturn \"[Request body - unknown format]\";\n\t} catch (error) {\n\t\treturn \"[Request body unavailable]\";\n\t}\n}\n/**\n* Create debug middleware for openapi-fetch (internal use)\n* Enhanced version that combines original functionality with duration tracking\n*/\nfunction createDebugMiddleware(logger) {\n\tconst debugLogger = new DebugLogger(logger);\n\treturn {\n\t\tasync onRequest({ request }) {\n\t\t\trequest.__debugStartTime = Date.now();\n\t\t\tconst requestBody = await extractRequestBody(request);\n\t\t\tdebugLogger.logRequest(request, requestBody);\n\t\t\treturn request;\n\t\t},\n\t\tasync onResponse({ request, response }) {\n\t\t\tconst startTime = request.__debugStartTime;\n\t\t\tconst duration = startTime ? Date.now() - startTime : 0;\n\t\t\tconst cloned = response.clone();\n\t\t\tlet responseBody = null;\n\t\t\ttry {\n\t\t\t\tconst contentType = response.headers.get(\"content-type\")?.toLowerCase();\n\t\t\t\tif (contentType?.startsWith(\"application/json\")) responseBody = await cloned.json();\n\t\t\t\telse if (contentType?.startsWith(\"text/\")) responseBody = await cloned.text();\n\t\t\t} catch (error) {}\n\t\t\tawait debugLogger.logResponse(response, responseBody);\n\t\t\tif (duration > 0) debugLogger.info(`Request completed in ${duration}ms`, {\n\t\t\t\turl: request.url,\n\t\t\t\tmethod: request.method\n\t\t\t});\n\t\t\treturn response;\n\t\t},\n\t\tasync onError({ error, request }) {\n\t\t\tdebugLogger.logError(\"API Request Failed\", {\n\t\t\t\terror: {\n\t\t\t\t\tname: error instanceof Error ? error.name : \"Unknown\",\n\t\t\t\t\tmessage: error instanceof Error ? error.message : String(error),\n\t\t\t\t\tstack: error instanceof Error ? error.stack : void 0\n\t\t\t\t},\n\t\t\t\trequest: {\n\t\t\t\t\tmethod: request.method,\n\t\t\t\t\turl: request.url,\n\t\t\t\t\theaders: Object.fromEntries(request.headers.entries())\n\t\t\t\t},\n\t\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t\t});\n\t\t\tthrow error;\n\t\t}\n\t};\n}\n\n//#endregion\n//#region src/middleware/timeout.ts\n/**\n* Timeout middleware for Commerce Engine SDKs\n*/\n/**\n* Create timeout middleware for openapi-fetch\n* Adds configurable request timeout functionality\n* \n* @param timeoutMs - Timeout duration in milliseconds\n* @returns Middleware object with onRequest handler\n*/\nfunction createTimeoutMiddleware(timeoutMs) {\n\tconst timeouts = /* @__PURE__ */ new WeakMap();\n\tconst clearRequestTimeout = (signal) => {\n\t\tconst timeoutId = timeouts.get(signal);\n\t\tif (timeoutId) {\n\t\t\tclearTimeout(timeoutId);\n\t\t\ttimeouts.delete(signal);\n\t\t}\n\t};\n\treturn {\n\t\tonRequest: async ({ request }) => {\n\t\t\tconst controller = new AbortController();\n\t\t\tconst timeoutId = setTimeout(() => controller.abort(), timeoutMs);\n\t\t\tif (request.signal) request.signal.addEventListener(\"abort\", () => controller.abort(), { once: true });\n\t\t\tconst newRequest = new Request(request, { signal: controller.signal });\n\t\t\ttimeouts.set(newRequest.signal, timeoutId);\n\t\t\tcontroller.signal.addEventListener(\"abort\", () => clearRequestTimeout(newRequest.signal), { once: true });\n\t\t\treturn newRequest;\n\t\t},\n\t\tonResponse: async ({ request, response }) => {\n\t\t\tclearRequestTimeout(request.signal);\n\t\t\treturn response;\n\t\t},\n\t\tonError: async ({ request, error }) => {\n\t\t\tclearRequestTimeout(request.signal);\n\t\t\tthrow error;\n\t\t}\n\t};\n}\n\n//#endregion\n//#region src/middleware/headers.ts\n/**\n* Header transformation and merging utilities for Commerce Engine SDKs\n*/\n/**\n* Merge two header objects\n* Method-level headers take precedence over default headers\n*\n* @param defaultHeaders - Default headers from SDK configuration\n* @param methodHeaders - Headers passed to the specific method call\n* @returns Merged headers object\n*/\nfunction mergeHeaders(defaultHeaders, methodHeaders) {\n\tconst merged = {};\n\tif (defaultHeaders) Object.assign(merged, defaultHeaders);\n\tif (methodHeaders) Object.assign(merged, methodHeaders);\n\tObject.keys(merged).forEach((key) => {\n\t\tif (merged[key] === void 0) delete merged[key];\n\t});\n\treturn merged;\n}\n/**\n* Transform headers using a transformation mapping\n* Headers not in the transformation map are passed through unchanged\n*\n* @param headers - Headers object with original names\n* @param transformations - Mapping of original names to transformed names\n* @returns Headers object with transformed names\n*/\nfunction transformHeaders(headers, transformations) {\n\tconst transformed = {};\n\tfor (const [key, value] of Object.entries(headers)) if (value !== void 0) {\n\t\tconst headerName = transformations[key] || key;\n\t\ttransformed[headerName] = value;\n\t}\n\treturn transformed;\n}\n/**\n* Merge headers with transformation support\n* Transforms default headers, then merges with method headers\n*\n* @param defaultHeaders - Default headers from SDK configuration\n* @param methodHeaders - Headers passed to the specific method call\n* @param transformations - Mapping for header name transformations\n* @returns Merged headers object with transformations applied\n*/\nfunction mergeAndTransformHeaders(defaultHeaders, methodHeaders, transformations) {\n\tconst merged = {};\n\tif (defaultHeaders && transformations) {\n\t\tconst transformedDefaults = transformHeaders(defaultHeaders, transformations);\n\t\tObject.assign(merged, transformedDefaults);\n\t} else if (defaultHeaders) Object.assign(merged, defaultHeaders);\n\tif (methodHeaders) Object.assign(merged, methodHeaders);\n\tObject.keys(merged).forEach((key) => {\n\t\tif (merged[key] === void 0) delete merged[key];\n\t});\n\treturn merged;\n}\n\n//#endregion\n//#region src/utils/response.ts\n/**\n* Execute a request and handle the response consistently\n* This provides unified error handling and response processing across all SDKs\n*\n* @param apiCall - Function that executes the API request\n* @returns Promise with the API response in standardized format\n*/\nasync function executeRequest(apiCall) {\n\ttry {\n\t\tconst { data, error, response } = await apiCall();\n\t\tif (error) return {\n\t\t\tdata: null,\n\t\t\terror,\n\t\t\tresponse\n\t\t};\n\t\tif (data && data.content !== void 0) return {\n\t\t\tdata: data.content,\n\t\t\terror: null,\n\t\t\tresponse\n\t\t};\n\t\treturn {\n\t\t\tdata,\n\t\t\terror: null,\n\t\t\tresponse\n\t\t};\n\t} catch (err) {\n\t\tconst mockResponse = new Response(null, {\n\t\t\tstatus: 503,\n\t\t\tstatusText: \"Service Unavailable\"\n\t\t});\n\t\treturn {\n\t\t\tdata: null,\n\t\t\terror: {\n\t\t\t\tsuccess: false,\n\t\t\t\tcode: \"NETWORK_ERROR\",\n\t\t\t\tmessage: \"Network error occurred\",\n\t\t\t\terror: err\n\t\t\t},\n\t\t\tresponse: mockResponse\n\t\t};\n\t}\n}\n\n//#endregion\n//#region src/base-client.ts\n/**\n* Base API client for Commerce Engine SDKs\n* Provides common functionality without token management\n*/\n/**\n* Generic base API client that all Commerce Engine SDKs can extend\n* Handles common functionality like middleware setup, request execution, and header management\n* Does NOT include token management - that's SDK-specific\n* \n* @template TPaths - OpenAPI paths type\n* @template THeaders - Supported default headers type\n*/\nvar BaseAPIClient = class {\n\tclient;\n\tconfig;\n\tbaseUrl;\n\theaderTransformations;\n\t/**\n\t* Create a new BaseAPIClient\n\t*\n\t* @param config - Configuration for the API client\n\t* @param baseUrl - The base URL for the API (must be provided by subclass)\n\t* @param headerTransformations - Header name transformations for this SDK\n\t*/\n\tconstructor(config, baseUrl, headerTransformations = {}) {\n\t\tthis.config = { ...config };\n\t\tthis.headerTransformations = headerTransformations;\n\t\tthis.baseUrl = baseUrl;\n\t\tthis.client = createClient({ baseUrl: this.baseUrl });\n\t\tthis.setupMiddleware();\n\t}\n\t/**\n\t* Set up all middleware for the client\n\t*/\n\tsetupMiddleware() {\n\t\tif (this.config.timeout) {\n\t\t\tconst timeoutMiddleware = createTimeoutMiddleware(this.config.timeout);\n\t\t\tthis.client.use(timeoutMiddleware);\n\t\t}\n\t\tif (this.config.debug) {\n\t\t\tconst debugMiddleware = createDebugMiddleware(this.config.logger);\n\t\t\tthis.client.use(debugMiddleware);\n\t\t}\n\t}\n\t/**\n\t* Get the base URL of the API\n\t*\n\t* @returns The base URL of the API\n\t*/\n\tgetBaseUrl() {\n\t\treturn this.baseUrl;\n\t}\n\t/**\n\t* Execute a request and handle the response consistently\n\t* This provides unified error handling and response processing\n\t*\n\t* @param apiCall - Function that executes the API request\n\t* @returns Promise with the API response in standardized format\n\t*/\n\tasync executeRequest(apiCall) {\n\t\treturn executeRequest(apiCall);\n\t}\n\t/**\n\t* Merge default headers with method-level headers\n\t* Method-level headers take precedence over default headers\n\t* Automatically applies SDK-specific header transformations\n\t*\n\t* @param methodHeaders - Headers passed to the specific method call\n\t* @returns Merged headers object with proper HTTP header names\n\t*/\n\tmergeHeaders(methodHeaders) {\n\t\treturn mergeAndTransformHeaders(this.config.defaultHeaders, methodHeaders, this.headerTransformations);\n\t}\n\t/**\n\t* Set default headers for the client\n\t*\n\t* @param headers - Default headers to set\n\t*/\n\tsetDefaultHeaders(headers) {\n\t\tthis.config.defaultHeaders = headers;\n\t}\n\t/**\n\t* Get current default headers\n\t*\n\t* @returns Current default headers\n\t*/\n\tgetDefaultHeaders() {\n\t\treturn this.config.defaultHeaders;\n\t}\n};\n\n//#endregion\n//#region src/utils/url.ts\n/**\n* Generic URL utility functions for any SDK\n*/\n/**\n* Extract pathname from URL\n* Useful for middleware that needs to inspect request paths\n*/\nfunction getPathnameFromUrl(url) {\n\ttry {\n\t\treturn new URL(url).pathname;\n\t} catch {\n\t\treturn url.split(\"?\")[0] || url;\n\t}\n}\n\n//#endregion\nexport { BaseAPIClient, DebugLogger, ResponseUtils, createDebugMiddleware, createTimeoutMiddleware, executeRequest, extractRequestBody, getPathnameFromUrl, mergeAndTransformHeaders, mergeHeaders, transformHeaders };","/**\n * URL utility functions for the Storefront SDK\n */\n\n/**\n * Available API environments for Commerce Engine\n */\nexport enum Environment {\n /**\n * Staging environment\n */\n Staging = \"staging\",\n\n /**\n * Production environment\n */\n Production = \"production\",\n}\n\n/**\n * Commerce Engine specific SDK configuration\n */\nexport interface CommerceEngineConfig {\n /**\n * Store ID for the API requests\n */\n storeId: string;\n\n /**\n * Environment to use (staging or production)\n */\n environment?: Environment;\n\n /**\n * Custom base URL (overrides environment if provided)\n */\n baseUrl?: string;\n}\n\n/**\n * Build base URL for Storefront API\n */\nexport function buildStorefrontURL(config: CommerceEngineConfig): string {\n // If explicit baseUrl is provided, use it\n if (config.baseUrl) {\n return config.baseUrl;\n }\n\n // Otherwise construct URL based on environment and storeId\n const env = config.environment || Environment.Production;\n\n switch (env) {\n case Environment.Staging:\n return `https://staging.api.commercengine.io/api/v1/${config.storeId}/storefront`;\n case Environment.Production:\n default:\n return `https://prod.api.commercengine.io/api/v1/${config.storeId}/storefront`;\n }\n}\n","import { BaseAPIClient, type BaseSDKOptions } from \"@commercengine/sdk-core\";\nimport type { paths } from \"@/types/storefront\";\nimport { buildStorefrontURL } from \"@/lib/shared/url-utils\";\nimport type {\n PublicStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"@/lib/shared/sdk-types\";\n\nexport type StorefrontClientBaseConfig =\n BaseSDKOptions<SupportedDefaultHeaders> & {\n storeId: string;\n environment?: PublicStorefrontSDKOptions[\"environment\"];\n baseUrl?: string;\n apiKey?: string;\n};\n\n/**\n * Shared base class for Storefront API clients.\n *\n * This centralizes Storefront-specific URL construction, default header\n * transformations, and shared API key state while leaving auth middleware\n * decisions to the public and session-specific subclasses.\n */\nexport class StorefrontAPIClientBase extends BaseAPIClient<\n paths,\n SupportedDefaultHeaders\n> {\n protected apiKey?: string;\n\n constructor(config: StorefrontClientBaseConfig) {\n const baseUrl = buildStorefrontURL({\n storeId: config.storeId,\n environment: config.environment,\n baseUrl: config.baseUrl,\n });\n\n const headerTransformations = {\n customer_group_id: \"x-customer-group-id\",\n debug_mode: \"x-debug-mode\",\n } as Record<keyof SupportedDefaultHeaders, string>;\n\n super(\n {\n baseUrl,\n timeout: config.timeout,\n defaultHeaders: config.defaultHeaders,\n debug: config.debug,\n logger: config.logger,\n },\n baseUrl,\n headerTransformations\n );\n\n this.apiKey = config.apiKey;\n }\n\n public setApiKey(apiKey: string): void {\n this.apiKey = apiKey;\n }\n\n public clearApiKey(): void {\n this.apiKey = undefined;\n }\n\n public useMiddleware(\n middleware: Parameters<typeof this.client.use>[0]\n ): void {\n this.client.use(middleware);\n }\n}\n","import type { paths } from \"@/types/storefront\";\nimport { StorefrontSessionManager } from \"./manager\";\nimport type {\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"@/lib/shared/sdk-types\";\nimport {\n StorefrontAPIClientBase,\n type StorefrontClientBaseConfig,\n} from \"@/lib/shared/client\";\n\ntype SessionStorefrontClientConfig = StorefrontClientBaseConfig &\n SessionStorefrontSDKOptions & {\n sessionManager: StorefrontSessionManager;\n};\n\nexport function attachSessionAuth(\n client: StorefrontAPIClientBase,\n sessionManager: StorefrontSessionManager\n): void {\n client.useMiddleware(sessionManager.createAuthMiddleware());\n}\n\n/**\n * Storefront API client that extends the generic BaseAPIClient\n * Adds Commerce Engine specific authentication and token management\n */\nexport class SessionStorefrontAPIClient extends StorefrontAPIClientBase {\n protected config: SessionStorefrontClientConfig;\n\n /**\n * Create a new SessionStorefrontAPIClient\n *\n * @param config - Configuration for the API client\n */\n constructor(config: SessionStorefrontClientConfig) {\n super(config);\n\n // Store full config for Storefront-specific features\n this.config = { ...config };\n\n // Set up Storefront-specific auth middleware\n this.setupStorefrontAuth();\n }\n\n /**\n * Set up Storefront-specific authentication middleware\n */\n private setupStorefrontAuth(): void {\n attachSessionAuth(this, this.config.sessionManager);\n }\n\n /**\n * Get the authorization header value\n * without creating a new session.\n *\n * @returns The Authorization header value or empty string if no token is set\n */\n public async getAuthorizationHeader(): Promise<string> {\n return this.config.sessionManager.getAuthorizationHeader();\n }\n\n /**\n * Set authentication tokens\n *\n * @param accessToken - The access token (required)\n * @param refreshToken - The refresh token (optional)\n *\n * Behavior:\n * - If tokenStorage is provided: Stores tokens for automatic management\n * - If tokenStorage is not provided: Only stores access token for manual management\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n await this.config.sessionManager.setTokens(accessToken, refreshToken);\n }\n\n /**\n * Clear all authentication tokens\n *\n * Behavior:\n * - If tokenStorage is provided: Clears both access and refresh tokens from storage\n * - If tokenStorage is not provided: Clears the manual access token\n */\n public async clearTokens(): Promise<void> {\n await this.config.sessionManager.clearTokens();\n }\n\n /**\n * Set the X-Api-Key header\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n super.setApiKey(apiKey);\n this.config.apiKey = apiKey;\n this.config.sessionManager.setApiKey(apiKey);\n }\n\n /**\n * Clear the X-Api-Key header\n */\n public clearApiKey(): void {\n super.clearApiKey();\n this.config.apiKey = undefined;\n this.config.sessionManager.clearApiKey();\n }\n\n /**\n * Resolve the current user ID from explicit parameters or the active session.\n *\n * @param explicitUserId - Optional user ID supplied by the caller\n * @returns The resolved user ID\n * @throws When no user ID is available\n */\n protected async resolveCurrentUserId(explicitUserId?: string): Promise<string> {\n if (explicitUserId) return explicitUserId;\n return this.config.sessionManager.ensureUserId();\n }\n\n /**\n * Resolve path parameters that require `user_id`.\n *\n * @param pathParams - Path parameters with an optional `user_id`\n * @returns Path parameters with a guaranteed `user_id`\n */\n protected async resolveUserPathParams<T extends { user_id: string }>(\n pathParams: Omit<T, \"user_id\"> & { user_id?: string }\n ): Promise<T> {\n return {\n ...pathParams,\n user_id: await this.resolveCurrentUserId(pathParams.user_id),\n } as T;\n }\n\n /**\n * Resolve query parameters that require `user_id`.\n *\n * @param queryParams - Query parameters with an optional `user_id`\n * @returns Query parameters with a guaranteed `user_id`\n */\n protected async resolveUserQueryParams<T extends { user_id: string }>(\n queryParams: Omit<T, \"user_id\"> & { user_id?: string }\n ): Promise<T> {\n return {\n ...queryParams,\n user_id: await this.resolveCurrentUserId(queryParams.user_id),\n } as T;\n }\n\n /**\n * Resolve path parameters that require `customer_id`.\n *\n * @param pathParams - Path parameters with an optional `customer_id`\n * @returns Path parameters with a guaranteed `customer_id`\n * @throws When the user is anonymous or no session can be established\n */\n protected async resolveCustomerPathParams<T extends { customer_id: string }>(\n pathParams: Omit<T, \"customer_id\"> & { customer_id?: string }\n ): Promise<T> {\n return {\n ...pathParams,\n customer_id:\n pathParams.customer_id ??\n (await this.config.sessionManager.ensureCustomerId()),\n } as T;\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n GetProductDetailContent,\n GetProductDetailPathParams,\n GetProductDetailHeaderParams,\n GetProductDetailQuery,\n GetVariantDetailContent,\n GetVariantDetailPathParams,\n GetVariantDetailHeaderParams,\n GetVariantDetailQuery,\n ListProductsContent,\n ListProductsQuery,\n ListProductsHeaderParams,\n ListProductVariantsContent,\n ListProductVariantsQuery,\n ListProductVariantsPathParams,\n ListProductVariantsHeaderParams,\n ListCategoriesQuery,\n ListCategoriesContent,\n ListProductReviewsQuery,\n ListProductReviewsPathParams,\n ListProductReviewsContent,\n SearchProductsBody,\n SearchProductsContent,\n ListSkusQuery,\n ListSkusContent,\n ListSkusHeaderParams,\n ListCrosssellProductsContent,\n ListCrosssellProductsQuery,\n ListCrosssellProductsHeaderParams,\n ListUpsellProductsQuery,\n ListUpsellProductsContent,\n ListUpsellProductsHeaderParams,\n ListSimilarProductsQuery,\n ListSimilarProductsContent,\n ListSimilarProductsHeaderParams,\n SearchProductsHeaderParams,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class BaseCatalogClient extends StorefrontAPIClientBase {\n /**\n * List all products\n *\n * @param options - Optional query parameters\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with products and pagination info\n *\n * @example\n * ```typescript\n * // Basic product listing\n * const { data, error } = await sdk.catalog.listProducts();\n *\n * if (error) {\n * console.error(\"Failed to list products:\", error);\n * return;\n * }\n *\n * console.log(\"Products found:\", data.products?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With filtering and pagination\n * const { data: filteredData, error: filteredError } = await sdk.catalog.listProducts({\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" }),\n * category_slug: [\"electronics\", \"smartphones\"]\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listProducts(\n * {\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" }),\n * category_slug: [\"electronics\", \"smartphones\"]\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (filteredError) {\n * console.error(\"Failed to get filtered products:\", filteredError);\n * return;\n * }\n *\n * filteredData.products?.forEach(product => {\n * console.log(`Product: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * ```\n */\n public async listProducts(\n options?: ListProductsQuery,\n headers?: ListProductsHeaderParams\n ): Promise<ApiResult<ListProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all skus\n *\n * @param options - Optional query parameters\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with skus and pagination info\n *\n * @example\n * ```typescript\n * // Basic SKU listing\n * const { data, error } = await sdk.catalog.listSkus();\n *\n * if (error) {\n * console.error(\"Failed to list SKUs:\", error);\n * return;\n * }\n *\n * console.log(\"SKUs found:\", data.skus?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With pagination\n * const { data: skuData, error: skuError } = await sdk.catalog.listSkus({\n * page: 1,\n * limit: 50\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listSkus(\n * {\n * page: 1,\n * limit: 50\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (skuError) {\n * console.error(\"Failed to get SKUs:\", skuError);\n * return;\n * }\n *\n * skuData.skus?.forEach(sku => {\n * console.log(`SKU: ${sku.sku} - Price: ${sku.price}`);\n * });\n * ```\n */\n public async listSkus(\n options?: ListSkusQuery,\n headers?: ListSkusHeaderParams\n ): Promise<ApiResult<ListSkusContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/skus\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get details for a specific product\n *\n * @param pathParams - The path parameters. Accepts product ID or product slug.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with product details\n *\n * @example\n * ```typescript\n * // Get product by ID\n * const { data, error } = await sdk.catalog.getProductDetail(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get product details:\", error);\n * return;\n * }\n *\n * console.log(\"Product:\", data.product.name);\n * console.log(\"Price:\", data.product.pricing?.selling_price);\n * console.log(\"Description:\", data.product.short_description);\n *\n * // Get product by slug (also accepted in place of product_id)\n * const { data: slugData, error: slugError } = await sdk.catalog.getProductDetail({\n * product_id: \"detox-candy\"\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.getProductDetail(\n * { product_id: \"detox-candy\" },\n * undefined,\n * {\n * \"x-customer-group-id\": \"premium_customers\" // Override default SDK config\n * }\n * );\n *\n * if (slugError) {\n * console.error(\"Failed to get product by slug:\", slugError);\n * return;\n * }\n *\n * console.log(\"Product with custom pricing:\", slugData.product.pricing?.selling_price);\n * ```\n */\n public async getProductDetail(\n pathParams: GetProductDetailPathParams,\n options?: GetProductDetailQuery,\n headers?: GetProductDetailHeaderParams\n ): Promise<ApiResult<GetProductDetailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all variants for a specific product\n *\n * @param pathParams - The path parameters. Accepts product ID or product slug.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with product variants and pagination info\n *\n * @example\n * ```typescript\n * // By product ID\n * const { data, error } = await sdk.catalog.listProductVariants(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to list product variants:\", error);\n * return;\n * }\n *\n * console.log(\"Variants found:\", data.variants?.length || 0);\n *\n * data.variants?.forEach(variant => {\n * console.log(`Variant: ${variant.name} - SKU: ${variant.sku} - Price: ${variant.pricing?.selling_price}`);\n * });\n *\n * // By product slug (also accepted in place of product_id)\n * const { data: slugData, error: slugError } = await sdk.catalog.listProductVariants(\n * { product_id: \"detox-candy\" }\n * );\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listProductVariants(\n * { product_id: \"prod_123\" },\n * undefined,\n * {\n * \"x-customer-group-id\": \"wholesale_customers\" // Override default SDK config\n * }\n * );\n * ```\n */\n public async listProductVariants(\n pathParams: ListProductVariantsPathParams,\n options?: ListProductVariantsQuery,\n headers?: ListProductVariantsHeaderParams\n ): Promise<ApiResult<ListProductVariantsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/variants\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get details for a specific product variant\n *\n * @param pathParams - The path parameters. Accepts product ID or slug for product_id, and variant ID or slug for variant_id.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with variant details\n *\n * @example\n * ```typescript\n * // By product ID and variant ID\n * const { data, error } = await sdk.catalog.getVariantDetail(\n * {\n * product_id: \"prod_123\",\n * variant_id: \"var_456\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get variant details:\", error);\n * return;\n * }\n *\n * console.log(\"Variant:\", data.variant.name);\n * console.log(\"SKU:\", data.variant.sku);\n * console.log(\"Price:\", data.variant.pricing?.selling_price);\n * console.log(\"Stock available:\", data.variant.stock_available);\n *\n * // By product slug and variant slug (also accepted in place of IDs)\n * const { data: slugData, error: slugError } = await sdk.catalog.getVariantDetail(\n * {\n * product_id: \"detox-candy\",\n * variant_id: \"detox-candy-100g\"\n * }\n * );\n * ```\n */\n public async getVariantDetail(\n pathParams: GetVariantDetailPathParams,\n options?: GetVariantDetailQuery,\n headers?: GetVariantDetailHeaderParams\n ): Promise<ApiResult<GetVariantDetailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/variants/{variant_id}\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all product categories\n *\n * @param options - Optional query parameters\n * @returns Promise with categories and pagination info\n *\n * @example\n * ```typescript\n * // Basic category listing\n * const { data, error } = await sdk.catalog.listCategories();\n *\n * if (error) {\n * console.error(\"Failed to list categories:\", error);\n * return;\n * }\n *\n * console.log(\"Categories found:\", data.categories?.length || 0);\n *\n * data.categories?.forEach(category => {\n * console.log(`Category: ${category.name} - ${category.description}`);\n * });\n *\n * // With pagination\n * const { data: catData, error: catError } = await sdk.catalog.listCategories({\n * page: 1,\n * limit: 10\n * });\n * ```\n */\n public async listCategories(\n options?: ListCategoriesQuery\n ): Promise<ApiResult<ListCategoriesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/categories\", {\n params: {\n query: options,\n },\n })\n );\n }\n\n /**\n * List all reviews for a specific product\n *\n * @param pathParams - The path parameters (product ID)\n * @param queryParams - Optional query parameters\n * @returns Promise with product reviews and pagination info\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.catalog.listProductReviews(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to list product reviews:\", error);\n * return;\n * }\n *\n * console.log(\"Reviews found:\", data.reviews?.length || 0);\n *\n * data.reviews?.forEach(review => {\n * console.log(`Review by ${review.name}: ${review.rating}/5`);\n * console.log(\"Review text:\", review.review_text);\n * });\n *\n * // With pagination\n * const { data: reviewData, error: reviewError } = await sdk.catalog.listProductReviews(\n * { product_id: \"prod_123\" },\n * {\n * page: 1,\n * limit: 5\n * }\n * );\n * ```\n */\n public async listProductReviews(\n pathParams: ListProductReviewsPathParams,\n queryParams?: ListProductReviewsQuery\n ): Promise<ApiResult<ListProductReviewsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/reviews\", {\n params: {\n path: pathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Search for products\n *\n * @param searchData - The search query, filters, sort, and pagination options\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with search results including SKUs, facet distribution, facet stats, and pagination\n *\n * @example\n * ```typescript\n * // Basic search\n * const { data, error } = await sdk.catalog.searchProducts({\n * query: \"smartphone\",\n * page: 1,\n * limit: 20\n * });\n *\n * if (error) {\n * console.error(\"Failed to search products:\", error);\n * return;\n * }\n *\n * console.log(\"Search results:\", data.skus?.length || 0, \"products found\");\n * console.log(\"Facet distribution:\", data.facet_distribution);\n * console.log(\"Facet stats:\", data.facet_stats);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.skus?.forEach(sku => {\n * console.log(`Found: ${sku.product_name} - ${sku.pricing?.selling_price}`);\n * });\n *\n * // With filter (string expression — Meilisearch syntax)\n * const { data: filtered, error: filteredError } = await sdk.catalog.searchProducts({\n * query: \"laptop\",\n * filter: \"pricing.selling_price 500 TO 2000 AND product_type = physical\",\n * sort: [\"pricing.selling_price:asc\"],\n * facets: [\"product_type\", \"categories.name\", \"tags\"],\n * page: 1,\n * limit: 10\n * });\n *\n * // With filter (array of conditions — combined with AND)\n * const { data: arrayFiltered, error: arrayError } = await sdk.catalog.searchProducts({\n * query: \"shoes\",\n * filter: [\"product_type = physical\", \"rating >= 4\", \"stock_available > 0\"],\n * sort: [\"rating:desc\"],\n * facets: [\"*\"],\n * page: 1,\n * limit: 25\n * });\n *\n * // With filter (nested arrays — inner arrays use OR, outer uses AND)\n * const { data: nestedFiltered, error: nestedError } = await sdk.catalog.searchProducts({\n * query: \"headphones\",\n * filter: [\n * \"pricing.selling_price 50 TO 300\",\n * [\"product_type = physical\", \"product_type = bundle\"]\n * ],\n * page: 1,\n * limit: 25\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.searchProducts(\n * {\n * query: \"laptop\",\n * filter: \"categories.name = computers\",\n * page: 1,\n * limit: 20\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n * ```\n */\n public async searchProducts(\n searchData: SearchProductsBody,\n headers?: SearchProductsHeaderParams\n ): Promise<ApiResult<SearchProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/catalog/products/search\", {\n params: {\n header: mergedHeaders,\n },\n body: searchData,\n })\n );\n }\n\n /**\n * List cross-sell products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with cross-sell products\n * @example\n * ```typescript\n * // Basic usage - get cross-sell products for cart items\n * const { data, error } = await sdk.catalog.listCrossSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\", \"prod_01H9ABC67890FGHIJ\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listCrossSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 10,\n * sort_by: '{\"price\":\"asc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listCrossSellProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 10\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get cross-sell products:\", error.message);\n * } else {\n * console.log(\"Cross-sell products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Product: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listCrossSellProducts(\n options?: ListCrosssellProductsQuery,\n headers?: ListCrosssellProductsHeaderParams\n ): Promise<ApiResult<ListCrosssellProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/cross-sell\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List up-sell products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with up-sell products\n * @example\n * ```typescript\n * // Basic usage - get up-sell products for cart items\n * const { data, error } = await sdk.catalog.listUpSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listUpSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 15,\n * sort_by: '{\"relevance\":\"desc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listUpSellProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 15\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get up-sell products:\", error.message);\n * } else {\n * console.log(\"Up-sell products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Up-sell: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listUpSellProducts(\n options?: ListUpsellProductsQuery,\n headers?: ListUpsellProductsHeaderParams\n ): Promise<ApiResult<ListUpsellProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/up-sell\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List similar products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with similar products\n * @example\n * ```typescript\n * // Basic usage - get similar products for a specific product\n * const { data, error } = await sdk.catalog.listSimilarProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listSimilarProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 20,\n * sort_by: '{\"relevance\":\"desc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listSimilarProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 20\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get similar products:\", error.message);\n * } else {\n * console.log(\"Similar products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Similar: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listSimilarProducts(\n options?: ListSimilarProductsQuery,\n headers?: ListSimilarProductsHeaderParams\n ): Promise<ApiResult<ListSimilarProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/similar\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n}\n","import { BaseCatalogClient } from \"@/lib/shared/catalog\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class PublicCatalogClient extends BaseCatalogClient {}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CreateProductReviewFormData,\n CreateProductReviewPathParams,\n CreateProductReviewResponse,\n} from \"@/types/storefront-api-types\";\nimport { BaseCatalogClient } from \"@/lib/shared/catalog\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class CatalogClient extends BaseCatalogClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n\n /**\n * Create a product review\n *\n * @param pathParams - The path parameters (product ID)\n * @param formData - The review data including rating, comment, and optional images\n * @returns Promise with review creation response\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.catalog.createProductReview(\n * { product_id: \"prod_123\" },\n * {\n * user_id: \"user_123\",\n * order_number: \"ORD-001\",\n * rating: 5,\n * review_text: \"Excellent product! Highly recommended.\",\n * images: [\n * new File([\"image data\"], \"review1.jpg\", { type: \"image/jpeg\" }),\n * new File([\"image data\"], \"review2.jpg\", { type: \"image/jpeg\" })\n * ]\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to create review:\", error);\n * return;\n * }\n *\n * console.log(\"Review created successfully:\", data.message);\n * ```\n */\n public async createProductReview(\n pathParams: CreateProductReviewPathParams,\n formData: CreateProductReviewFormData\n ): Promise<ApiResult<CreateProductReviewResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/catalog/products/{product_id}/reviews\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n if (value instanceof File || value instanceof Blob) {\n fd.append(key, value);\n } else {\n fd.append(key, String(value));\n }\n }\n }\n return fd;\n },\n })\n );\n }\n}\n","import { SessionStorefrontAPIClient } from \"./session/client\";\nimport type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n AddToWishlistBody,\n AddToWishlistContent,\n AddToWishlistPathParams,\n ApplyCouponBody,\n ApplyCouponContent,\n ApplyCouponPathParams,\n CreateCartContent,\n CreateCartAddressBody,\n CreateCartAddressContent,\n CreateCartAddressPathParams,\n CreateCartBody,\n DeleteCartPathParams,\n DeleteCartResponse,\n DeleteFromWishlistBody,\n DeleteFromWishlistContent,\n DeleteFromWishlistPathParams,\n DeleteUserCartPathParams,\n DeleteUserCartResponse,\n GetCartContent,\n GetCartPathParams,\n GetUserCartContent,\n GetUserCartPathParams,\n GetWishlistContent,\n GetWishlistPathParams,\n RedeemCreditBalanceBody,\n RedeemCreditBalanceContent,\n RedeemCreditBalancePathParams,\n RedeemLoyaltyPointsBody,\n RedeemLoyaltyPointsContent,\n RedeemLoyaltyPointsPathParams,\n RemoveCouponContent,\n RemoveCouponPathParams,\n RemoveCreditBalanceContent,\n RemoveCreditBalancePathParams,\n RemoveLoyaltyPointsContent,\n RemoveLoyaltyPointsPathParams,\n UpdateCartBody,\n UpdateCartContent,\n UpdateCartPathParams,\n UpdateFulfillmentPreferenceContent,\n UpdateFulfillmentPreferencePathParams,\n UpdateFulfillmentPreferenceBody,\n ListCouponsContent,\n ListPromotionsContent,\n ListCouponsHeaderParams,\n ListPromotionsHeaderParams,\n EvaluatePromotionsPathParams,\n EvaluatePromotionsContent,\n EvaluateCouponsContent,\n EvaluateCouponsPathParams,\n CheckFulfillmentContent,\n CheckFulfillmentBody,\n GetFulfillmentOptionsBody,\n GetFulfillmentOptionsContent,\n GetWishlistQuery,\n} from \"@/types/storefront-api-types\";\n\n/**\n * Client for interacting with cart endpoints\n */\nexport class CartClient extends SessionStorefrontAPIClient {\n // ===============================\n // CART ENDPOINTS\n // ===============================\n\n /**\n * Create a new cart\n *\n * @param payload - Object containing the items to add to the cart\n * @returns Promise with the created cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.createCart({\n * items: [\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 2\n * },\n * {\n * product_id: \"01H9ABC67890FGHIJ\",\n * variant_id: \"01H9XYZ67890KLMNO\",\n * quantity: 1\n * }\n * ],\n * metadata: {\n * \"source\": \"web\",\n * \"campaign\": \"summer_sale\"\n * }\n * });\n *\n * if (error) {\n * console.error(\"Failed to create cart:\", error.message);\n * } else {\n * console.log(\"Cart created:\", data.cart.id);\n * }\n * ```\n */\n public async createCart(\n payload: CreateCartBody\n ): Promise<ApiResult<CreateCartContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts\", {\n body: payload,\n })\n );\n }\n\n /**\n * Get cart details - either by ID or using the stored cart ID\n *\n * @param cartId - The ID of the cart\n * @returns Promise with cart details\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getCart({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get cart:\", error.message);\n * } else {\n * const cart = data.cart;\n * console.log(\"Cart total:\", cart.grand_total);\n * console.log(\"Items count:\", cart.cart_items.length);\n * }\n * ```\n */\n public async getCart(\n cartId: GetCartPathParams\n ): Promise<ApiResult<GetCartContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Delete a cart - either by ID or using the stored cart ID\n *\n * @param cartId - The ID of the cart\n * @returns Promise that resolves when the cart is deleted\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.deleteCart({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete cart:\", error.message);\n * } else {\n * console.log(\"Cart deleted:\", data.message);\n * }\n * ```\n */\n public async deleteCart(\n cartId: DeleteCartPathParams\n ): Promise<ApiResult<DeleteCartResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Update cart items (add, update quantity, remove)\n *\n * @param cartId - The cart id\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // Add item to cart\n * const { data, error } = await sdk.cart.addDeleteCartItem(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 3\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update cart:\", error.message);\n * } else {\n * console.log(\"Cart updated:\", data.cart.cart_items.length);\n * }\n *\n * // Remove item from cart (set quantity to 0)\n * const { data: removeData, error: removeError } = await sdk.cart.addDeleteCartItem(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 0\n * }\n * );\n * ```\n */\n public async addDeleteCartItem(\n cartId: UpdateCartPathParams,\n body: UpdateCartBody\n ): Promise<ApiResult<UpdateCartContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/items\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Get cart details by user ID\n *\n * @param pathParams - Optional path parameters. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with cart details\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getUserCart();\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.getUserCart({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to get user cart:\", error.message);\n * } else {\n * console.log(\"User cart ID:\", data.cart.id);\n * console.log(\"Cart value:\", data.cart.subtotal);\n * }\n * ```\n */\n public async getUserCart(): Promise<ApiResult<GetUserCartContent>>;\n public async getUserCart(\n pathParams: { user_id: string }\n ): Promise<ApiResult<GetUserCartContent>>;\n public async getUserCart(\n pathParams: { user_id?: string } = {}\n ): Promise<ApiResult<GetUserCartContent>> {\n const resolvedPathParams =\n await this.resolveUserPathParams<GetUserCartPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/carts/users/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Delete a cart by user ID\n *\n * @param pathParams - Optional path parameters. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise that resolves when the cart is deleted\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.deleteUserCart();\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.deleteUserCart({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete user cart:\", error.message);\n * } else {\n * console.log(\"User cart cleared:\", data.message);\n * }\n * ```\n */\n public async deleteUserCart(): Promise<ApiResult<DeleteUserCartResponse>>;\n public async deleteUserCart(\n pathParams: { user_id: string }\n ): Promise<ApiResult<DeleteUserCartResponse>>;\n public async deleteUserCart(\n pathParams: { user_id?: string } = {}\n ): Promise<ApiResult<DeleteUserCartResponse>> {\n const resolvedPathParams =\n await this.resolveUserPathParams<DeleteUserCartPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/users/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // CART ADDRESS ENDPOINTS\n // ===============================\n\n /**\n * Update cart addresses\n *\n * @param cartId - The ID of the cart\n * @param addressData - The address data\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // For registered users with saved addresses\n * const { data, error } = await sdk.cart.updateCartAddress(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * billing_address_id: \"01H9ADDR12345BILL\",\n * shipping_address_id: \"01H9ADDR12345SHIP\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update cart address:\", error.message);\n * } else {\n * console.log(\"Addresses updated:\", data.cart);\n * }\n *\n * // For guest checkout with new addresses\n * const { data: guestData, error: guestError } = await sdk.cart.updateCartAddress(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * billing_address: {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * address_line1: \"123 Main Street\",\n * address_line2: \"Apt 4B\",\n * city: \"Mumbai\",\n * state: \"Maharashtra\",\n * pincode: \"400001\",\n * country: \"India\",\n * landmark: \"Near Station\",\n * tax_identification_number: null,\n * business_name: null\n * },\n * shipping_address: {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * address_line1: \"456 Oak Avenue\",\n * address_line2: null,\n * city: \"Pune\",\n * state: \"Maharashtra\",\n * pincode: \"411001\",\n * country: \"India\",\n * landmark: \"Near Mall\",\n * tax_identification_number: null,\n * business_name: null\n * }\n * }\n * );\n * ```\n */\n public async updateCartAddress(\n cartId: CreateCartAddressPathParams,\n addressData: CreateCartAddressBody\n ): Promise<ApiResult<CreateCartAddressContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/address\", {\n params: {\n path: cartId,\n },\n body: addressData,\n })\n );\n }\n\n // ===============================\n // COUPON & PROMOTION ENDPOINTS\n // ===============================\n\n /**\n * Apply a coupon to the cart\n *\n * @param cartId - The ID of the cart\n * @param couponCode - The coupon code\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.applyCoupon(\n * { id: \"01H9CART12345ABCDE\" },\n * { coupon_code: \"FLAT100OFF\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to apply coupon:\", error.message);\n * } else {\n * console.log(\"Coupon applied, new total:\", data.cart.grand_total);\n * console.log(\"Discount amount:\", data.cart.coupon_discount_amount);\n * }\n * ```\n */\n public async applyCoupon(\n cartId: ApplyCouponPathParams,\n couponCode: ApplyCouponBody\n ): Promise<ApiResult<ApplyCouponContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/coupon\", {\n params: {\n path: cartId,\n },\n body: couponCode,\n })\n );\n }\n\n /**\n * Remove a coupon from the cart\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeCoupon({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove coupon:\", error.message);\n * } else {\n * console.log(\"Coupon removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeCoupon(\n cartId: RemoveCouponPathParams\n ): Promise<ApiResult<RemoveCouponContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/coupon\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n /**\n * Get all available coupons\n *\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with all available coupons\n * @example\n * ```typescript\n * // Get all available coupons\n * const { data, error } = await sdk.cart.getAvailableCoupons();\n *\n * if (error) {\n * console.error(\"Failed to get available coupons:\", error.message);\n * } else {\n * const coupons = data.coupons || [];\n * console.log(\"Available coupons:\", coupons.length);\n * coupons.forEach(coupon => {\n * console.log(\"Coupon:\", coupon.coupon_code, \"Name:\", coupon.name);\n * });\n * }\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.cart.getAvailableCoupons({\n * \"x-customer-group-id\": \"01H9GROUP12345ABC\" // Override default SDK config\n * });\n * ```\n */\n public async getAvailableCoupons(\n headers?: ListCouponsHeaderParams\n ): Promise<ApiResult<ListCouponsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/carts/available-coupons\", {\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get all available promotions\n *\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with all available promotions\n * @example\n * ```typescript\n * // Get all available promotions\n * const { data, error } = await sdk.cart.getAvailablePromotions();\n *\n * if (error) {\n * console.error(\"Failed to get available promotions:\", error.message);\n * } else {\n * const promotions = data.promotions || [];\n * console.log(\"Available promotions:\", promotions.length);\n * promotions.forEach(promotion => {\n * console.log(\"Promotion:\", promotion.name, \"Type:\", promotion.promotion_type);\n * });\n * }\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.cart.getAvailablePromotions({\n * \"x-customer-group-id\": \"01H9GROUP12345ABC\" // Override default SDK config\n * });\n * ```\n */\n public async getAvailablePromotions(\n headers?: ListPromotionsHeaderParams\n ): Promise<ApiResult<ListPromotionsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/carts/available-promotions\", {\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Evaluate promotions\n *\n * @param cartId - The ID of the cart\n * @returns Promise with evaluated promotions\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.evaluatePromotions({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to evaluate promotions:\", error.message);\n * } else {\n * const applicable = data.applicable_promotions || [];\n * const inapplicable = data.inapplicable_promotions || [];\n *\n * console.log(\"Applicable promotions:\", applicable.length);\n * applicable.forEach(promo => {\n * console.log(`- ${promo.name}: ${promo.savings_message}`);\n * });\n *\n * console.log(\"Inapplicable promotions:\", inapplicable.length);\n * inapplicable.forEach(promo => {\n * console.log(`- ${promo.name}: ${promo.reason}`);\n * });\n * }\n * ```\n */\n public async evaluatePromotions(\n cartId: EvaluatePromotionsPathParams\n ): Promise<ApiResult<EvaluatePromotionsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}/evaluate-promotions\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Evaluate coupons\n *\n * @param cartId - The ID of the cart\n * @returns Promise with evaluated coupons\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.evaluateCoupons({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to evaluate coupons:\", error.message);\n * } else {\n * const applicable = data.applicable_coupons || [];\n * const inapplicable = data.inapplicable_coupons || [];\n *\n * console.log(\"Applicable coupons:\", applicable.length);\n * applicable.forEach(coupon => {\n * console.log(`- ${coupon.coupon_code?.join(\", \")}: Save $${coupon.estimated_discount}`);\n * });\n *\n * console.log(\"Inapplicable coupons:\", inapplicable.length);\n * inapplicable.forEach(coupon => {\n * console.log(`- ${coupon.coupon_code?.join(\", \")}: ${coupon.reason}`);\n * });\n * }\n * ```\n */\n public async evaluateCoupons(\n cartId: EvaluateCouponsPathParams\n ): Promise<ApiResult<EvaluateCouponsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}/evaluate-coupons\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n\n // ===============================\n // LOYALTY POINTS ENDPOINTS\n // ===============================\n\n /**\n * Redeem loyalty points\n *\n * @param cartId - The ID of the cart\n * @param points - The number of points to redeem\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.redeemLoyaltyPoints(\n * { id: \"01H9CART12345ABCDE\" },\n * { loyalty_point_redeemed: 500 }\n * );\n *\n * if (error) {\n * console.error(\"Failed to redeem loyalty points:\", error.message);\n * } else {\n * console.log(\"Points redeemed, new total:\", data.cart.grand_total);\n * console.log(\"Points redeemed:\", data.cart.loyalty_points_redeemed);\n * }\n * ```\n */\n public async redeemLoyaltyPoints(\n cartId: RedeemLoyaltyPointsPathParams,\n points: RedeemLoyaltyPointsBody\n ): Promise<ApiResult<RedeemLoyaltyPointsContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/loyalty-points\", {\n params: {\n path: cartId,\n },\n body: points,\n })\n );\n }\n\n /**\n * Remove loyalty points\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeLoyaltyPoints({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove loyalty points:\", error.message);\n * } else {\n * console.log(\"Loyalty points removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeLoyaltyPoints(\n cartId: RemoveLoyaltyPointsPathParams\n ): Promise<ApiResult<RemoveLoyaltyPointsContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/loyalty-points\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // FULFILLMENT ENDPOINTS\n // ===============================\n\n /**\n * Update fulfillment preference\n *\n * @param cartId - The ID of the cart\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // For delivery fulfillment with shipments\n * const { data, error } = await sdk.cart.updateFulfillmentPreference(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * fulfillment_type: \"delivery\",\n * shipments: [\n * {\n * id: \"01H9SHIP12345ABCDE\",\n * shipping_provider_id: \"01H9PROV12345FAST\",\n * courier_company_id: \"01H9COY12345FAST\" // Optional\n * }\n * ]\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update fulfillment preference:\", error.message);\n * } else {\n * console.log(\"Fulfillment preference updated:\", data.cart.fulfillment_preference?.fulfillment_type);\n * console.log(\"Shipping cost:\", data.cart.shipping_amount);\n * }\n *\n * // For collect-in-store fulfillment\n * const { data: collectData, error: collectError } = await sdk.cart.updateFulfillmentPreference(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * fulfillment_type: \"collect-in-store\",\n * pickup_location_id: \"01H9STORE12345ABC\"\n * }\n * );\n * ```\n */\n public async updateFulfillmentPreference(\n cartId: UpdateFulfillmentPreferencePathParams,\n body: UpdateFulfillmentPreferenceBody\n ): Promise<ApiResult<UpdateFulfillmentPreferenceContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/fulfillment-preference\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Check fulfillment serviceability\n *\n * Checks if fulfillment (delivery or collect-in-store) is available to the specified pincode\n * based on shipping zones and inventories.\n *\n * @param body - Fulfillment check body (cart-based or items-based)\n * @returns Promise with fulfillment serviceability result\n * @example\n * ```typescript\n * // Cart-based fulfillment check\n * const { data, error } = await sdk.cart.checkPincodeDeliverability({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * delivery_pincode: \"400001\",\n * fulfillment_type: \"delivery\" // optional: \"delivery\" | \"collect-in-store\"\n * });\n *\n * // Items-based fulfillment check\n * const { data, error } = await sdk.cart.checkPincodeDeliverability({\n * delivery_pincode: \"400001\",\n * items: [\n * { product_id: \"prod_123\", variant_id: \"var_456\" },\n * { product_id: \"prod_789\", variant_id: null }\n * ]\n * // fulfillment_type is optional\n * });\n *\n * if (error) {\n * console.error(\"Failed to check fulfillment serviceability:\", error.message);\n * } else {\n * console.log(\"Serviceable:\", data.is_serviceable);\n *\n * if (!data.is_serviceable && data.unserviceable_items) {\n * data.unserviceable_items.forEach(item => {\n * console.log(`Unserviceable: ${item.product_name}, max available: ${item.max_available_quantity}`);\n * });\n * }\n * }\n * ```\n */\n public async checkPincodeDeliverability(\n body: CheckFulfillmentBody\n ): Promise<ApiResult<CheckFulfillmentContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/fulfillment/serviceability\", {\n body: body,\n })\n );\n }\n\n /**\n * Get fulfillment options for an order\n *\n * @param body - Fulfillment options body containing cart_id and optional fulfillment_type\n * @returns Promise with fulfillment options including collect and delivery methods. The response contains:\n * - `summary`: Object with `collect_available`, `deliver_available`, `recommended_fulfillment_type`, and optional `recommended_store`\n * - `collect`: Optional array of `CollectInStore` objects for collect-in-store options\n * - `deliver`: Optional `DeliveryOption` object with `is_serviceable` and `shipments` array. Each shipment contains `id`, `items`, and `shipping_methods` array. Shipping methods may have optional `courier_companies` for auto shipping types.\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getFulfillmentOptions({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * fulfillment_type: \"delivery\" // optional: \"delivery\" | \"collect-in-store\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get fulfillment options:\", error.message);\n * } else {\n * // Check summary information\n * console.log(\"Collect available:\", data.summary.collect_available);\n * console.log(\"Deliver available:\", data.summary.deliver_available);\n * console.log(\"Recommended fulfillment type:\", data.summary.recommended_fulfillment_type);\n *\n * // Access collect options\n * if (data.collect && data.collect.length > 0) {\n * console.log(\"Available stores for collection:\");\n * data.collect.forEach(store => {\n * console.log(`${store.name} - ${store.distance_km}km away, ETA: ${store.collect_eta_minutes} minutes`);\n * });\n * }\n *\n * // Access delivery options (with shipments)\n * if (data.deliver && data.deliver.is_serviceable) {\n * console.log(\"Available shipments and shipping methods:\");\n * data.deliver.shipments.forEach(shipment => {\n * console.log(`Shipment ${shipment.id}:`);\n * console.log(` Items: ${shipment.items.length}`);\n * shipment.shipping_methods.forEach(method => {\n * console.log(` - ${method.name}: ${method.shipping_amount}, ${method.estimated_delivery_days} days`);\n * // Access courier companies for auto shipping methods\n * if (method.courier_companies) {\n * method.courier_companies.forEach(courier => {\n * console.log(` Courier: ${courier.name} - ${courier.shipping_amount}, ${courier.estimated_delivery_days} days`);\n * });\n * }\n * });\n * });\n * }\n * }\n * ```\n */\n public async getFulfillmentOptions(\n body: GetFulfillmentOptionsBody\n ): Promise<ApiResult<GetFulfillmentOptionsContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/fulfillment-options\", {\n body: body,\n })\n );\n }\n\n // ===============================\n // CREDIT BALANCE ENDPOINTS\n // ===============================\n\n /**\n * Use credit balance\n *\n * @param cartId - The ID of the cart\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.redeemCreditBalance(\n * { id: \"01H9CART12345ABCDE\" },\n * { credit_balance_used: 250.00 }\n * );\n *\n * if (error) {\n * console.error(\"Failed to redeem credit balance:\", error.message);\n * } else {\n * console.log(\"Credit applied, new total:\", data.cart.grand_total);\n * console.log(\"Credit used:\", data.cart.credit_balance_used);\n * }\n * ```\n */\n public async redeemCreditBalance(\n cartId: RedeemCreditBalancePathParams,\n body: RedeemCreditBalanceBody\n ): Promise<ApiResult<RedeemCreditBalanceContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/credit-balance\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Remove credit balance\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeCreditBalance({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove credit balance:\", error.message);\n * } else {\n * console.log(\"Credit balance removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeCreditBalance(\n cartId: RemoveCreditBalancePathParams\n ): Promise<ApiResult<RemoveCreditBalanceContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/credit-balance\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // WISHLIST ENDPOINTS\n // ===============================\n\n /**\n * Get wishlist items\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param options - Optional query parameters for filtering by seller_id (only for multi-seller marketplace stores)\n * @returns Promise with wishlist items\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getWishlist();\n *\n * // With query parameters\n * const { data: filtered } = await sdk.cart.getWishlist({\n * seller_id: \"seller_123\",\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.getWishlist({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to get wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Wishlist items:\", products.length);\n * products.forEach(product => {\n * console.log(\"Product:\", product.product_name, \"Price:\", product.pricing?.selling_price);\n * });\n * }\n * ```\n */\n public async getWishlist(): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n queryParams: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n pathParams: { user_id: string },\n queryParams?: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n pathParamsOrQuery?:\n | { user_id?: string }\n | GetWishlistQuery,\n options?: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>> {\n const hasPathParams =\n options !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"user_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { user_id?: string })\n : {};\n const queryParams = hasPathParams\n ? options\n : (pathParamsOrQuery as GetWishlistQuery | undefined);\n const resolvedPathParams =\n await this.resolveUserPathParams<GetWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Add item to wishlist\n *\n * @param pathParamsOrBody - Optional path parameters or the wishlist body.\n * @param maybeBody - The wishlist body when path parameters are provided.\n * @returns Promise with updated wishlist\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.addToWishlist({\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.addToWishlist(\n * { user_id: \"01H9USER12345ABCDE\" },\n * {\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to add to wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Item added to wishlist, total items:\", products.length);\n * }\n * ```\n */\n public async addToWishlist(\n body: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>>;\n public async addToWishlist(\n pathParams: { user_id: string },\n body: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>>;\n public async addToWishlist(\n pathParamsOrBody:\n | { user_id?: string }\n | AddToWishlistBody,\n maybeBody?: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { user_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as AddToWishlistBody);\n const resolvedPathParams =\n await this.resolveUserPathParams<AddToWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.POST(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Remove item from wishlist\n *\n * @param pathParamsOrBody - Optional path parameters or the wishlist body.\n * @param maybeBody - The wishlist body when path parameters are provided.\n * @returns Promise with updated wishlist\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeFromWishlist({\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.removeFromWishlist(\n * { user_id: \"01H9USER12345ABCDE\" },\n * {\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to remove from wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Item removed from wishlist, remaining items:\", products.length);\n * }\n * ```\n */\n public async removeFromWishlist(\n body: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>>;\n public async removeFromWishlist(\n pathParams: { user_id: string },\n body: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>>;\n public async removeFromWishlist(\n pathParamsOrBody:\n | { user_id?: string }\n | DeleteFromWishlistBody,\n maybeBody?: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { user_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as DeleteFromWishlistBody);\n const resolvedPathParams =\n await this.resolveUserPathParams<DeleteFromWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n\n}\n","import { SessionStorefrontAPIClient } from \"./session/client\";\nimport type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n AddProfileImageContent,\n AddProfileImageFormData,\n AddProfileImagePathParams,\n ChangePasswordBody,\n ChangePasswordContent,\n CheckVerificationStatusBody,\n CheckVerificationStatusContent,\n DeactivateUserPathParams,\n DeactivateUserResponse,\n DeleteUserPathParams,\n DeleteUserResponse,\n ForgotPasswordBody,\n ForgotPasswordContent,\n ForgotPasswordHeaderParams,\n GenerateOtpHeaderParams,\n GenerateOtpBody,\n GenerateOtpContent,\n GetAnonymousTokenContent,\n GetProfileImageContent,\n GetProfileImagePathParams,\n GetUserDetailContent,\n GetUserDetailPathParams,\n LoginWithEmailHeaderParams,\n LoginWithEmailBody,\n LoginWithEmailContent,\n LoginWithPasswordBody,\n LoginWithPasswordContent,\n LoginWithPhoneHeaderParams,\n LoginWithPhoneBody,\n LoginWithPhoneContent,\n LoginWithWhatsappHeaderParams,\n LoginWithWhatsappBody,\n LoginWithWhatsappContent,\n LogoutContent,\n RefreshTokenBody,\n RefreshTokenContent,\n RegisterWithEmailBody,\n RegisterWithEmailContent,\n RegisterWithEmailHeaderParams,\n RegisterWithPasswordBody,\n RegisterWithPasswordContent,\n RegisterWithPasswordHeaderParams,\n RegisterWithPhoneBody,\n RegisterWithPhoneContent,\n RegisterWithPhoneHeaderParams,\n RegisterWithWhatsappBody,\n RegisterWithWhatsappContent,\n RegisterWithWhatsappHeaderParams,\n RemoveProfileImagePathParams,\n RemoveProfileImageResponse,\n ResetPasswordBody,\n ResetPasswordContent,\n UpdateProfileImageContent,\n UpdateProfileImageFormData,\n UpdateProfileImagePathParams,\n UpdateUserBody,\n UpdateUserContent,\n UpdateUserPathParams,\n VerifyOtpBody,\n VerifyOtpContent,\n} from \"@/types/storefront-api-types\";\n\n/**\n * Client for interacting with authentication endpoints\n */\nexport class AuthClient extends SessionStorefrontAPIClient {\n /**\n * Get anonymous token for guest users\n *\n * @example\n * ```typescript\n * // Get token for guest browsing\n * const { data, error } = await sdk.auth.getAnonymousToken();\n *\n * if (error) {\n * console.error(\"Failed to get anonymous token:\", error.message);\n * } else {\n * console.log(\"Anonymous token:\", data.access_token);\n * // Store token or proceed with guest operations\n * }\n * ```\n */\n public async getAnonymousToken(): Promise<\n ApiResult<GetAnonymousTokenContent>\n > {\n return this.executeRequest(() => this.client.POST(\"/auth/anonymous\"));\n }\n\n /**\n * Login with phone number\n *\n * @param body - Login request body containing phone number and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with phone number\n * const { data, error } = await sdk.auth.loginWithPhone({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"Login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * // Redirect user to OTP verification screen\n * }\n * ```\n */\n public async loginWithPhone(\n body: LoginWithPhoneBody,\n headers?: LoginWithPhoneHeaderParams\n ): Promise<ApiResult<LoginWithPhoneContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/phone\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with WhatsApp\n *\n * @param body - Login request body containing phone number and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with WhatsApp number\n * const { data, error } = await sdk.auth.loginWithWhatsApp({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"WhatsApp login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent to WhatsApp. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * }\n * ```\n */\n public async loginWithWhatsApp(\n body: LoginWithWhatsappBody,\n headers?: LoginWithWhatsappHeaderParams\n ): Promise<ApiResult<LoginWithWhatsappContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/whatsapp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with email\n *\n * @param body - Login request body containing email and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with email address\n * const { data, error } = await sdk.auth.loginWithEmail({\n * email: \"customer@example.com\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"Email login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent to email. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * // Show OTP input form\n * }\n * ```\n */\n public async loginWithEmail(\n body: LoginWithEmailBody,\n headers?: LoginWithEmailHeaderParams\n ): Promise<ApiResult<LoginWithEmailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/email\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with password\n *\n * @param body - Login credentials containing email/phone and password\n * @returns Promise with user info and tokens\n * @example\n * ```typescript\n * // Login with email and password\n * const { data, error } = await sdk.auth.loginWithPassword({\n * email: \"customer@example.com\",\n * password: \"securePassword123\"\n * });\n *\n * if (error) {\n * console.error(\"Password login failed:\", error.message);\n * } else {\n * console.log(\"Login successful:\", data.user.email);\n * console.log(\"Access token:\", data.access_token);\n * }\n * ```\n */\n public async loginWithPassword(\n body: LoginWithPasswordBody\n ): Promise<ApiResult<LoginWithPasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/password\", {\n body: body,\n })\n );\n }\n\n /**\n * Start forgot-password OTP flow\n *\n * @param body - Request body containing email or phone details\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for the reset flow\n * @example\n * ```typescript\n * // Send password reset OTP\n * const { data, error } = await sdk.auth.forgotPassword({\n * email: \"customer@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"Password reset failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async forgotPassword(\n body: ForgotPasswordBody,\n headers?: ForgotPasswordHeaderParams\n ): Promise<ApiResult<ForgotPasswordContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/forgot-password\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Reset password\n *\n * @param body - Reset password request body containing new password and OTP token\n * @returns Promise with new access and refresh tokens\n * @example\n * ```typescript\n * // Reset password with OTP token from forgot password flow\n * const { data, error } = await sdk.auth.resetPassword({\n * new_password: \"newSecurePassword123\",\n * confirm_password: \"newSecurePassword123\",\n * otp_token: \"abc123otptoken\"\n * });\n *\n * if (error) {\n * console.error(\"Password reset failed:\", error.message);\n * } else {\n * console.log(\"Password reset successful\");\n * console.log(\"New access token:\", data.access_token);\n * }\n * ```\n */\n public async resetPassword(\n body: ResetPasswordBody\n ): Promise<ApiResult<ResetPasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/reset-password\", {\n body: body,\n })\n );\n }\n\n /**\n * Change password\n *\n * @param body - Change password request body containing old and new passwords\n * @returns Promise with new access and refresh tokens\n * @example\n * ```typescript\n * // Change user's password\n * const { data, error } = await sdk.auth.changePassword({\n * old_password: \"currentPassword123\",\n * new_password: \"newSecurePassword456\",\n * confirm_password: \"newSecurePassword456\"\n * });\n *\n * if (error) {\n * console.error(\"Password change failed:\", error.message);\n * } else {\n * console.log(\"Password changed successfully\");\n * console.log(\"New access token:\", data.access_token);\n * }\n * ```\n */\n public async changePassword(\n body: ChangePasswordBody\n ): Promise<ApiResult<ChangePasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/change-password\", {\n body: body,\n })\n );\n }\n\n /**\n * Verify OTP\n *\n * @param body - OTP verification data including code and tokens\n * @returns Promise with user info and tokens\n * @example\n * ```typescript\n * // Verify OTP after login attempt\n * const { data, error } = await sdk.auth.verifyOtp({\n * otp: \"1234\",\n * otp_token: \"56895455\",\n * otp_action: \"login\" // or \"register\"\n * });\n *\n * if (error) {\n * console.error(\"OTP verification failed:\", error.message);\n * // Show error message, allow retry\n * } else {\n * console.log(\"Login successful:\", data.user.email);\n * console.log(\"User ID:\", data.user.id);\n * }\n * ```\n */\n public async verifyOtp(\n body: VerifyOtpBody\n ): Promise<ApiResult<VerifyOtpContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/verify-otp\", {\n body: body,\n })\n );\n }\n\n /**\n * Register with phone\n *\n * @param body - Registration details including phone number and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with phone number\n * const { data, error } = await sdk.auth.registerWithPhone({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"Phone registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithPhone(\n body: RegisterWithPhoneBody,\n headers?: RegisterWithPhoneHeaderParams\n ): Promise<ApiResult<RegisterWithPhoneContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/phone\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with email\n *\n * @param body - Registration details including email and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with email address\n * const { data, error } = await sdk.auth.registerWithEmail({\n * email: \"jane.smith@example.com\",\n * first_name: \"Jane\",\n * last_name: \"Smith\",\n * phone: \"9876543210\"\n * });\n *\n * if (error) {\n * console.error(\"Email registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithEmail(\n body: RegisterWithEmailBody,\n headers?: RegisterWithEmailHeaderParams\n ): Promise<ApiResult<RegisterWithEmailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/email\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with WhatsApp\n *\n * @param body - Registration details including WhatsApp number and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with WhatsApp number\n * const { data, error } = await sdk.auth.registerWithWhatsapp({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"WhatsApp registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithWhatsapp(\n body: RegisterWithWhatsappBody,\n headers?: RegisterWithWhatsappHeaderParams\n ): Promise<ApiResult<RegisterWithWhatsappContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/whatsapp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with password\n *\n * @param body - Registration details including email or phone and password\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * const { data, error } = await sdk.auth.registerWithPassword({\n * email: \"jane.smith@example.com\",\n * password: \"securePassword123\",\n * confirm_password: \"securePassword123\",\n * });\n *\n * if (error) {\n * console.error(\"Password registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithPassword(\n body: RegisterWithPasswordBody,\n headers?: RegisterWithPasswordHeaderParams\n ): Promise<ApiResult<RegisterWithPasswordContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/password\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Refresh the access token using a refresh token\n * @param body - Request body containing the refresh token\n * @returns Promise with the new access token and refresh token\n * @example\n * ```typescript\n * // Refresh access token when it expires\n * const { data, error } = await sdk.auth.refreshToken({\n * refresh_token: \"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...\"\n * });\n *\n * if (error) {\n * console.error(\"Token refresh failed:\", error.message);\n * // Redirect to login\n * } else {\n * console.log(\"Token refreshed successfully\");\n * console.log(\"New access token:\", data.access_token);\n * console.log(\"New refresh token:\", data.refresh_token);\n * }\n * ```\n */\n public async refreshToken(\n body: RefreshTokenBody\n ): Promise<ApiResult<RefreshTokenContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/refresh-token\", {\n body: body,\n })\n );\n }\n\n /**\n * Logout\n *\n * @returns Promise that resolves when logout is complete\n * @example\n * ```typescript\n * // Logout current user\n * const { data, error } = await sdk.auth.logout();\n *\n * if (error) {\n * console.error(\"Logout failed:\", error.message);\n * } else {\n * console.log(\"Logout successful\");\n * console.log(\"Session ended for user:\", data.user.email);\n * }\n * ```\n */\n public async logout(): Promise<ApiResult<LogoutContent>> {\n return this.executeRequest(() => this.client.POST(\"/auth/logout\"));\n }\n\n /**\n * Get user details\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with user details\n * @example\n * ```typescript\n * // Get details for a specific user\n * const { data, error } = await sdk.auth.getUserDetails({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get user details:\", error.message);\n * } else {\n * console.log(\"User details:\", data.user);\n * console.log(\"Email:\", data.user.email);\n * console.log(\"Phone:\", data.user.phone);\n * console.log(\"Created:\", data.user.created_at);\n * }\n * ```\n */\n public async getUserDetails(\n pathParams: GetUserDetailPathParams\n ): Promise<ApiResult<GetUserDetailContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Update user details\n *\n * @param pathParams - Path parameters containing user ID\n * @param body - Updated user information\n * @returns Promise with updated user details\n * @example\n * ```typescript\n * // Update user profile information\n * const { data, error } = await sdk.auth.updateUserDetails(\n * { id: \"01H9XYZ12345USERID\" },\n * {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update user:\", error.message);\n * } else {\n * console.log(\"User updated successfully:\", data.user.first_name);\n * }\n * ```\n */\n public async updateUserDetails(\n pathParams: UpdateUserPathParams,\n body: UpdateUserBody\n ): Promise<ApiResult<UpdateUserContent>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n\n /**\n * Delete user account\n *\n * @description Deletes a user account. If the user is a primary user, deletes the associated\n * customer and all linked users. If the user is a normal user, deletes only that user without\n * affecting the customer or other users.\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deletion confirmation\n * @example\n * ```typescript\n * // Delete a user account\n * const { data, error } = await sdk.auth.deleteUser({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete user:\", error.message);\n * } else {\n * console.log(\"User deleted successfully\");\n * console.log(\"Success:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async deleteUser(\n pathParams: DeleteUserPathParams\n ): Promise<ApiResult<DeleteUserResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Add profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @param formData - Form data containing the image file\n * @returns Promise with profile image URL\n * @example\n * ```typescript\n * // Add profile image for a user\n * const imageFile = document.getElementById('file-input').files[0];\n * const { data, error } = await sdk.auth.addProfileImage(\n * { id: \"01H9XYZ12345USERID\" },\n * { image: imageFile }\n * );\n *\n * if (error) {\n * console.error(\"Failed to add profile image:\", error.message);\n * } else {\n * console.log(\"Profile image added successfully\");\n * console.log(\"Image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async addProfileImage(\n pathParams: AddProfileImagePathParams,\n formData: AddProfileImageFormData\n ): Promise<ApiResult<AddProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n fd.append(key, value);\n }\n }\n return fd;\n },\n })\n );\n }\n\n /**\n * Update profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @param formData - Form data containing the new image file\n * @returns Promise with updated profile image URL\n * @example\n * ```typescript\n * // Update existing profile image\n * const newImageFile = document.getElementById('file-input').files[0];\n * const { data, error } = await sdk.auth.updateProfileImage(\n * { id: \"01H9XYZ12345USERID\" },\n * { image: newImageFile }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update profile image:\", error.message);\n * } else {\n * console.log(\"Profile image updated successfully\");\n * console.log(\"New image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async updateProfileImage(\n pathParams: UpdateProfileImagePathParams,\n formData: UpdateProfileImageFormData\n ): Promise<ApiResult<UpdateProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n fd.append(key, value);\n }\n }\n return fd;\n },\n })\n );\n }\n\n /**\n * Delete profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deletion confirmation\n * @example\n * ```typescript\n * // Delete user's profile image\n * const { data, error } = await sdk.auth.deleteProfileImage({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete profile image:\", error.message);\n * } else {\n * console.log(\"Profile image deleted successfully\");\n * console.log(\"Success:\", data.success);\n * }\n * ```\n */\n public async deleteProfileImage(\n pathParams: RemoveProfileImagePathParams\n ): Promise<ApiResult<RemoveProfileImageResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Get profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with profile image URL\n * @example\n * ```typescript\n * // Get user's profile image URL\n * const { data, error } = await sdk.auth.getProfileImage({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get profile image:\", error.message);\n * } else {\n * console.log(\"Profile image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async getProfileImage(\n pathParams: GetProfileImagePathParams\n ): Promise<ApiResult<GetProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Deactivate user account\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deactivation confirmation\n * @example\n * ```typescript\n * // Deactivate a user account\n * const { data, error } = await sdk.auth.deactivateUserAccount({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to deactivate account:\", error.message);\n * } else {\n * console.log(\"Account deactivated successfully\");\n * console.log(\"Success:\", data.success);\n * }\n * ```\n */\n public async deactivateUserAccount(\n pathParams: DeactivateUserPathParams\n ): Promise<ApiResult<DeactivateUserResponse>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}/deactivate\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Generate OTP\n *\n * @param body - OTP generation body (phone or email)\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Generate OTP for phone number\n * const { data, error } = await sdk.auth.generateOtp({\n * phone: \"9876543210\",\n * country_code: \"+91\"\n * });\n *\n * if (error) {\n * console.error(\"OTP generation failed:\", error.message);\n * } else {\n * console.log(\"OTP sent successfully\");\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async generateOtp(\n body: GenerateOtpBody,\n headers?: GenerateOtpHeaderParams\n ): Promise<ApiResult<GenerateOtpContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/generate-otp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Check whether email or phone is already verified\n *\n * @param body - Request body containing phone numbers or email addresses to verify\n * @returns Promise with verification status for provided contacts\n * @example\n * ```typescript\n * // Check verification status for multiple contacts\n * const { data, error } = await sdk.auth.checkEmailOrPhoneIsVerified({\n * phone: [\"9876543210\", \"9123456789\"],\n * email: [\"user1@example.com\", \"user2@example.com\"]\n * });\n *\n * if (error) {\n * console.error(\"Verification check failed:\", error.message);\n * } else {\n * console.log(\"Verified phones:\", data.verified_phone);\n * console.log(\"Verified emails:\", data.verified_email);\n * }\n * ```\n */\n public async checkEmailOrPhoneIsVerified(\n body: CheckVerificationStatusBody\n ): Promise<ApiResult<CheckVerificationStatusContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/verified-email-phone\", {\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CancelOrderBody,\n CancelOrderContent,\n CancelOrderPathParams,\n CancelPaymentRequestPathParams,\n CancelPaymentRequestResponse,\n CreateOrderBody,\n CreateOrderContent,\n GetOrderDetailContent,\n GetOrderDetailPathParams,\n GetPaymentStatusContent,\n ListOrderPaymentsContent,\n ListOrderPaymentsPathParams,\n ListOrderRefundsContent,\n ListOrderRefundsPathParams,\n ListOrdersContent,\n ListOrderShipmentsContent,\n ListOrderShipmentsPathParams,\n ListOrdersQuery,\n RetryOrderPaymentBody,\n RetryOrderPaymentContent,\n RetryOrderPaymentPathParams,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with order endpoints\n */\nexport class OrderClient extends SessionStorefrontAPIClient {\n /**\n * Get order details\n *\n * @param orderNumber - Order number\n * @returns Promise with order details\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.getOrderDetails({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order details:\", error.message);\n * } else {\n * console.log(\"Order details:\", data.order);\n * console.log(\"Order status:\", data.order.status);\n * console.log(\"Total amount:\", data.order.grand_total);\n * }\n * ```\n */\n public async getOrderDetails(\n pathParams: GetOrderDetailPathParams\n ): Promise<ApiResult<GetOrderDetailContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Create order\n *\n * @param body - Order creation request body\n * @returns Promise with order details\n * @example\n * ```typescript\n * // Juspay Hyper Checkout - Redirects to hosted payment page\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"hyper-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * action: \"paymentPage\"\n * }\n * });\n *\n * // Juspay Express Checkout - New Card\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"CARD\",\n * payment_method: \"VISA\",\n * auth_type: \"OTP\",\n * save_to_locker: true,\n * card_number: \"4111111111111111\",\n * card_exp_month: \"12\",\n * card_exp_year: \"2025\",\n * name_on_card: \"John Doe\",\n * card_security_code: \"123\"\n * }\n * });\n *\n * // Juspay Express Checkout - Saved Card Token\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * get_client_auth_token: true,\n * payment_method_type: \"CARD\",\n * payment_method: \"VISA\",\n * auth_type: \"OTP\",\n * save_to_locker: false,\n * card_token: \"token_abc123\",\n * card_security_code: \"123\"\n * }\n * });\n *\n * // Juspay Express Checkout - UPI Collect\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"UPI\",\n * payment_method: \"UPI_COLLECT\",\n * upi_vpa: \"user@upi\"\n * }\n * });\n *\n * // Juspay Express Checkout - Net Banking\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"NB\",\n * payment_method: \"NB_HDFC\"\n * }\n * });\n *\n * if (error) {\n * console.error(\"Failed to create order:\", error.message);\n * } else {\n * console.log(\"Order created:\", data.order.id);\n * console.log(\"Payment required:\", data.payment_required);\n * console.log(\"Payment info:\", data.payment_info);\n *\n * // For hyper-checkout, redirect to payment page\n * if (\"payment_links\" in data.payment_info) {\n * window.location.href = data.payment_info.payment_links?.web;\n * }\n *\n * // For express-checkout with OTP authentication\n * if (\"payment\" in data.payment_info && data.payment_info.payment?.authentication?.params) {\n * const { id: txn_id, challenge_id } = data.payment_info.payment.authentication.params;\n * // Use txn_id and challenge_id with sdk.payments.authenticateDirectOtp()\n * }\n * }\n * ```\n */\n public async createOrder(\n body: CreateOrderBody\n ): Promise<ApiResult<CreateOrderContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders\", {\n body: body,\n })\n );\n }\n\n /**\n * List all orders\n *\n * @param queryParams - Optional query parameters for filtering and pagination. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with order list\n * @example\n * ```typescript\n * // Basic usage\n * const { data, error } = await sdk.order.listOrders();\n *\n * // Advanced usage with optional parameters\n * const { data, error } = await sdk.order.listOrders({\n * page: 1,\n * limit: 20,\n * sort_by: '{\"created_at\":\"desc\"}',\n * status: [\"confirmed\", \"shipped\", \"delivered\"]\n * });\n *\n * if (error) {\n * console.error(\"Failed to list orders:\", error.message);\n * } else {\n * console.log(\"Orders found:\", data.orders?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.orders?.forEach(order => {\n * console.log(`Order ${order.order_number}: ${order.status}`);\n * });\n * }\n * ```\n */\n public async listOrders(): Promise<ApiResult<ListOrdersContent>>;\n public async listOrders(\n queryParams: Partial<ListOrdersQuery>\n ): Promise<ApiResult<ListOrdersContent>>;\n public async listOrders(\n queryParams: Partial<ListOrdersQuery> = {}\n ): Promise<ApiResult<ListOrdersContent>> {\n const resolvedQueryParams =\n await this.resolveUserQueryParams<ListOrdersQuery>(queryParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/orders\", {\n params: {\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * Get payment status for an order\n *\n * @param orderNumber - Order number\n * @returns Promise with payment status\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.getPaymentStatus(\"ORD-2024-001\");\n *\n * if (error) {\n * console.error(\"Failed to get payment status:\", error.message);\n * } else {\n * console.log(\"Payment status:\", data.status);\n * console.log(\"Amount paid:\", data.amount_paid);\n * console.log(\"Amount unpaid:\", data.amount_unpaid);\n * console.log(\"Retry available:\", data.is_retry_available);\n * }\n * ```\n */\n public async getPaymentStatus(\n orderNumber: string\n ): Promise<ApiResult<GetPaymentStatusContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/payment-status\", {\n params: {\n path: { order_number: orderNumber },\n },\n })\n );\n }\n\n /**\n * Get all shipments for an order\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with shipments\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderShipments({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order shipments:\", error.message);\n * } else {\n * console.log(\"Shipments found:\", data.shipments?.length || 0);\n *\n * data.shipments?.forEach(shipment => {\n * console.log(`Shipment ${shipment.reference_number}: ${shipment.status}`);\n * console.log(\"AWB:\", shipment.awb_no);\n * console.log(\"Courier:\", shipment.courier_company_name);\n * });\n * }\n * ```\n */\n public async listOrderShipments(\n pathParams: ListOrderShipmentsPathParams\n ): Promise<ApiResult<ListOrderShipmentsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/shipments\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * List order payments\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with payments\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderPayments({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order payments:\", error.message);\n * } else {\n * console.log(\"Payments found:\", data.payments?.length || 0);\n *\n * data.payments?.forEach(payment => {\n * console.log(`Payment ${payment.request_number}: ${payment.payment_status}`);\n * console.log(\"Amount:\", payment.amount);\n * console.log(\"Reference:\", payment.payment_reference_number);\n * });\n * }\n * ```\n */\n public async listOrderPayments(\n pathParams: ListOrderPaymentsPathParams\n ): Promise<ApiResult<ListOrderPaymentsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/payments\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * List order refunds\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with refunds\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderRefunds({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order refunds:\", error.message);\n * } else {\n * console.log(\"Refunds found:\", data.refunds?.length || 0);\n *\n * data.refunds?.forEach(refund => {\n * console.log(`Refund ${refund.request_number}: ${refund.status}`);\n * console.log(\"Amount:\", refund.refund_amount);\n * console.log(\"Reason:\", refund.refund_remarks);\n * console.log(\"Processed at:\", refund.refund_date);\n * });\n * }\n * ```\n */\n public async listOrderRefunds(\n pathParams: ListOrderRefundsPathParams\n ): Promise<ApiResult<ListOrderRefundsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/refunds\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Cancel an order\n *\n * @param pathParams - Order number path parameters\n * @param body - Cancellation request body\n * @returns Promise with order details\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.cancelOrder(\n * { order_number: \"ORD-2024-001\" },\n * {\n * cancellation_reason: \"Customer requested cancellation\",\n * refund_mode: \"original_payment_mode\",\n * feedback: \"Customer changed their mind about the purchase\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to cancel order:\", error.message);\n * } else {\n * console.log(\"Order cancelled successfully\");\n * console.log(\"Updated order status:\", data.order?.status);\n * console.log(\"Cancellation reason:\", data.order?.cancellation_reason);\n * }\n * ```\n */\n public async cancelOrder(\n pathParams: CancelOrderPathParams,\n body: CancelOrderBody\n ): Promise<ApiResult<CancelOrderContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/cancel\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n\n /**\n * Cancel a payment request for an order\n *\n * @description Use when the express checkout payment flow is used and the user wants to switch\n * payment methods (e.g. started with UPI, then chose another). Without this call, the user must\n * wait until the payment-status API returns `status: failed` and `is_retry_available: true`\n * (typically ~3 minutes). Calling this endpoint cancels the existing payment request so the user\n * can retry payment immediately.\n *\n * @param pathParams - Path parameters containing the order number\n * @returns Promise with cancellation confirmation\n * @example\n * ```typescript\n * // Cancel an in-progress payment request to switch payment methods\n * const { data, error } = await sdk.order.cancelPaymentRequest({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to cancel payment request:\", error.message);\n * } else {\n * console.log(\"Payment request cancelled:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async cancelPaymentRequest(\n pathParams: CancelPaymentRequestPathParams\n ): Promise<ApiResult<CancelPaymentRequestResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/cancel-payment-request\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Retry payment for an order\n *\n * @param pathParams - Order number path parameters\n * @param body - Payment retry request body\n * @returns Promise with payment information\n * @example\n * ```typescript\n * // Juspay Hyper Checkout - Redirects to hosted payment page\n * const { data, error } = await sdk.order.retryOrderPayment(\n * { order_number: \"ORD-2024-001\" },\n * {\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"hyper-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * action: \"paymentPage\"\n * }\n * }\n * );\n *\n * // Juspay Express Checkout - UPI Collect\n * const { data, error } = await sdk.order.retryOrderPayment(\n * { order_number: \"ORD-2024-001\" },\n * {\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"UPI\",\n * payment_method: \"UPI_COLLECT\",\n * upi_vpa: \"user@upi\"\n * }\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to retry payment:\", error.message);\n * } else {\n * console.log(\"Payment retry initiated\");\n * console.log(\"Payment info:\", data.payment_info);\n *\n * // For hyper-checkout, redirect to payment page\n * if (\"payment_links\" in data.payment_info) {\n * window.location.href = data.payment_info.payment_links?.web;\n * }\n * }\n * ```\n */\n public async retryOrderPayment(\n pathParams: RetryOrderPaymentPathParams,\n body: RetryOrderPaymentBody\n ): Promise<ApiResult<RetryOrderPaymentContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/retry-payment\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n ListPaymentMethodsContent,\n ListPaymentMethodsQuery,\n VerifyVpaContent,\n VerifyVpaQuery,\n AuthenticateDirectOtpBody,\n AuthenticateDirectOtpResponse,\n ResendDirectOtpBody,\n ResendDirectOtpContent,\n GetCardInfoContent,\n GetCardInfoQuery,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with payment endpoints\n */\nexport class PaymentsClient extends SessionStorefrontAPIClient {\n /**\n * List all available payment methods\n *\n * @param queryParams - Query parameters containing the payment method type and payment provider slug\n * @returns Promise with list of payment methods\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.listPaymentMethods({\n * payment_method_type: \"card\",\n * payment_provider_slug: \"payu\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list payment methods:\", error.message);\n * } else {\n * console.log(\"Payment methods:\", data.payment_methods);\n *\n * data.payment_methods?.forEach(method => {\n * console.log(\"Payment method:\", method.name);\n * console.log(\"Gateway:\", method.payment_gateway);\n * });\n * }\n * ```\n */\n public async listPaymentMethods(\n queryParams?: ListPaymentMethodsQuery\n ): Promise<\n ApiResult<ListPaymentMethodsContent>\n > {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/payment-methods\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Verify a UPI Virtual Payment Address (VPA)\n *\n * @description The Virtual Payment Address or VPA is a unique ID given to an individual\n * using the Unified Payment Interface (UPI) service to send or receive money.\n * Validating the VPA helps reduce payment failure rates due to incorrect VPA.\n *\n * @param queryParams - Query parameters containing the VPA to verify\n * @returns Promise with VPA verification result\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.verifyVpa({\n * vpa: \"user@upi\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to verify VPA:\", error.message);\n * } else {\n * console.log(\"VPA:\", data.vpa);\n * console.log(\"Status:\", data.status);\n *\n * if (data.status === \"valid\") {\n * console.log(\"VPA is valid and can be used for UPI payments\");\n * } else {\n * console.log(\"VPA is invalid, please check and try again\");\n * }\n * }\n * ```\n */\n public async verifyVpa(\n queryParams?: VerifyVpaQuery\n ): Promise<ApiResult<VerifyVpaContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/verify-vpa\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Get card information\n *\n * Retrieves card information based on the initial 9 digits (card BIN) of the card number.\n *\n * @param queryParams - Query parameters containing the card BIN\n * @returns Promise with card information\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.getCardInfo({\n * cardbin: \"411111111\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get card information:\", error.message);\n * } else {\n * console.log(\"Card information:\", data.card_info);\n * }\n * ```\n */\n public async getCardInfo(\n queryParams: GetCardInfoQuery\n ): Promise<ApiResult<GetCardInfoContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/card-info\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n \n /**\n * Authenticate a direct OTP for payment verification\n *\n * @description Used to authenticate OTP during payment flows that require 2FA verification.\n * The txn_id and challenge_id can be obtained from the create order API response\n * under the payment_info.authentication.params object.\n *\n * @param body - OTP authentication request body\n * @returns Promise with authentication result\n * @example\n * ```typescript\n * // After creating an order, if OTP authentication is required:\n * const { data, error } = await sdk.payments.authenticateDirectOtp({\n * txn_id: \"txn_01H9XYZ12345ABCDE\",\n * challenge_id: \"challenge_01H9XYZ12345ABCDE\",\n * otp: \"123456\"\n * });\n *\n * if (error) {\n * console.error(\"OTP authentication failed:\", error.message);\n * } else {\n * console.log(\"Authentication success:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async authenticateDirectOtp(\n body: AuthenticateDirectOtpBody\n ): Promise<ApiResult<AuthenticateDirectOtpResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/payments/authenticate-direct-otp\", {\n body: body,\n })\n );\n }\n\n /**\n * Resend a direct OTP for payment verification\n *\n * @description Used to resend OTP during payment flows that require 2FA verification.\n * The txn_id and challenge_id can be obtained from the create order API response\n * under the payment_info.authentication.params object.\n *\n * @param body - OTP resend request body\n * @returns Promise with new payment info containing updated OTP challenge\n * @example\n * ```typescript\n * // If user didn't receive OTP or it expired:\n * const { data, error } = await sdk.payments.resendDirectOtp({\n * txn_id: \"txn_01H9XYZ12345ABCDE\",\n * challenge_id: \"challenge_01H9XYZ12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to resend OTP:\", error.message);\n * } else {\n * console.log(\"OTP resent successfully\");\n * console.log(\"New payment info:\", data.payment_info);\n * }\n * ```\n */\n public async resendDirectOtp(\n body: ResendDirectOtpBody\n ): Promise<ApiResult<ResendDirectOtpContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/payments/resend-direct-otp\", {\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n ListCountriesContent,\n ListCountryPincodesContent,\n ListCountryPincodesPathParams,\n ListCountryPincodesQuery,\n ListCountryStatesContent,\n ListCountryStatesPathParams,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class BaseHelpersClient extends StorefrontAPIClientBase {\n /**\n * Get a list of countries\n *\n * @returns Promise with countries\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountries();\n *\n * if (error) {\n * console.error(\"Failed to get countries:\", error);\n * return;\n * }\n *\n * console.log(\"Countries found:\", data.countries?.length || 0);\n *\n * data.countries?.forEach(country => {\n * console.log(`Country: ${country.country_name} (${country.country_iso_code})`);\n * console.log(\"Currency:\", country.currency_code);\n * });\n * ```\n */\n public async listCountries(): Promise<ApiResult<ListCountriesContent>> {\n return this.executeRequest(() => this.client.GET(\"/common/countries\", {}));\n }\n\n /**\n * Get a list of states for a country\n *\n * @param pathParams - Path parameters\n * @returns Promise with states\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountryStates({\n * country_iso_code: \"IN\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get states:\", error);\n * return;\n * }\n *\n * console.log(\"States found:\", data.states?.length || 0);\n *\n * data.states?.forEach(state => {\n * console.log(`State: ${state.name} (${state.iso_code})`);\n * });\n *\n * // Get states for different country\n * const { data: usStates, error: usError } = await sdk.helpers.listCountryStates({\n * country_iso_code: \"US\"\n * });\n *\n * if (usError) {\n * console.error(\"Failed to get US states:\", usError);\n * return;\n * }\n *\n * console.log(\"US States:\", usStates.states?.map(s => s.name).join(\", \"));\n * ```\n */\n public async listCountryStates(\n pathParams: ListCountryStatesPathParams\n ): Promise<ApiResult<ListCountryStatesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/common/countries/{country_iso_code}/states\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Get pincodes for a country\n *\n * @param pathParams - Path parameters\n * @returns Promise with pincodes\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountryPincodes({\n * country_iso_code: \"IN\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get pincodes:\", error);\n * return;\n * }\n *\n * console.log(\"Pincodes found:\", data.pincodes?.length || 0);\n *\n * data.pincodes?.forEach(pincode => {\n * console.log(`Pincode: ${pincode.pincode} - ${pincode.city}, ${pincode.state_name}`);\n * });\n *\n * // Get pincodes for different country\n * const { data: usPincodes, error: usError } = await sdk.helpers.listCountryPincodes({\n * country_iso_code: \"US\"\n * });\n *\n * if (usError) {\n * console.error(\"Failed to get US pincodes:\", usError);\n * return;\n * }\n *\n * console.log(\"US Pincodes:\", usPincodes.pincodes?.map(p => p.pincode).join(\", \"));\n * ```\n */\n public async listCountryPincodes(\n pathParams: ListCountryPincodesPathParams,\n queryParams?: ListCountryPincodesQuery\n ): Promise<ApiResult<ListCountryPincodesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/common/countries/{country_iso_code}/pincodes\", {\n params: {\n path: pathParams,\n query: queryParams,\n },\n })\n );\n }\n}\n","import { BaseHelpersClient } from \"@/lib/shared/helper\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class PublicHelpersClient extends BaseHelpersClient {}\n","import { BaseHelpersClient } from \"@/lib/shared/helper\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class HelpersClient extends BaseHelpersClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CreateAddressBody,\n CreateAddressContent,\n CreateAddressPathParams,\n DeleteAddressPathParams,\n DeleteAddressResponse,\n GetAddressDetailContent,\n GetAddressDetailPathParams,\n GetLoyaltyDetailsContent,\n GetLoyaltyDetailsPathParams,\n ListAddressesContent,\n ListAddressesPathParams,\n ListAddressesQuery,\n ListCustomerReviewsContent,\n ListCustomerReviewsPathParams,\n ListLoyaltyActivitiesContent,\n ListLoyaltyActivitiesPathParams,\n ListLoyaltyActivitiesQuery,\n UpdateAddressDetailBody,\n UpdateAddressDetailContent,\n UpdateAddressDetailPathParams,\n ListSavedPaymentMethodsContent,\n ListSavedPaymentMethodsPathParams,\n ListCustomerCardsContent,\n ListCustomerCardsPathParams,\n ListSavedPaymentMethodsQuery,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with customer endpoints\n */\nexport class CustomerClient extends SessionStorefrontAPIClient {\n\n /**\n * Get all saved addresses for a customer\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param queryParams - Optional query parameters when path params are provided.\n * @returns Promise with addresses\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listAddresses();\n *\n * if (error) {\n * console.error(\"Failed to list addresses:\", error);\n * return;\n * }\n *\n * console.log(\"Addresses:\", data.addresses);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With pagination\n * const { data: page2, error: page2Error } = await sdk.customer.listAddresses({\n * page: 2,\n * limit: 10\n * });\n * ```\n */\n public async listAddresses(): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n queryParams: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n pathParams: { customer_id: string },\n queryParams?: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n pathParamsOrQuery?:\n | { customer_id?: string }\n | ListAddressesQuery,\n queryParams?: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>> {\n const hasPathParams =\n queryParams !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"customer_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { customer_id?: string })\n : {};\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListAddressesPathParams>(pathParams);\n const resolvedQueryParams = hasPathParams\n ? queryParams\n : (pathParamsOrQuery as ListAddressesQuery | undefined);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/addresses\", {\n params: {\n path: resolvedPathParams,\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * Create a new address for a customer\n *\n * @param pathParamsOrBody - Optional path parameters or the address body.\n * @param maybeBody - Address body when path params are provided.\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.createAddress({\n * address_line1: \"123 Main Street\",\n * address_line2: \"Apt 4B\",\n * city: \"New York\",\n * state: \"NY\",\n * country: \"US\",\n * pincode: \"10001\",\n * is_default_billing: true,\n * is_default_shipping: false\n * });\n *\n * if (error) {\n * console.error(\"Failed to create address:\", error);\n * return;\n * }\n *\n * console.log(\"Address created:\", data.address);\n * ```\n */\n public async createAddress(\n body: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>>;\n public async createAddress(\n pathParams: { customer_id: string },\n body: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>>;\n public async createAddress(\n pathParamsOrBody:\n | { customer_id?: string }\n | CreateAddressBody,\n maybeBody?: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { customer_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as CreateAddressBody);\n const resolvedPathParams =\n await this.resolveCustomerPathParams<CreateAddressPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.POST(\"/customers/{customer_id}/addresses\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Get an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.getAddress({\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get address:\", error);\n * return;\n * }\n *\n * console.log(\"Address details:\", data.address);\n * ```\n */\n public async getAddress(\n pathParams: { address_id: string }\n ): Promise<ApiResult<GetAddressDetailContent>>;\n public async getAddress(\n pathParams: { address_id: string; customer_id: string }\n ): Promise<ApiResult<GetAddressDetailContent>>;\n public async getAddress(\n pathParams: { address_id: string; customer_id?: string }\n ): Promise<ApiResult<GetAddressDetailContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<GetAddressDetailPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Update an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @param body - Address update body\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.updateAddress(\n * {\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * },\n * {\n * address_line1: \"456 Oak Avenue\",\n * city: \"Los Angeles\",\n * state: \"CA\",\n * pincode: \"90210\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update address:\", error);\n * return;\n * }\n *\n * console.log(\"Address updated:\", data.address);\n * ```\n */\n public async updateAddress(\n pathParams: { address_id: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>>;\n public async updateAddress(\n pathParams: { address_id: string; customer_id: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>>;\n public async updateAddress(\n pathParams: { address_id: string; customer_id?: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<UpdateAddressDetailPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.PUT(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Delete an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @returns Promise with deletion response\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.deleteAddress({\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete address:\", error);\n * return;\n * }\n *\n * console.log(\"Address deleted:\", data.message);\n * ```\n */\n public async deleteAddress(\n pathParams: { address_id: string }\n ): Promise<ApiResult<DeleteAddressResponse>>;\n public async deleteAddress(\n pathParams: { address_id: string; customer_id: string }\n ): Promise<ApiResult<DeleteAddressResponse>>;\n public async deleteAddress(\n pathParams: { address_id: string; customer_id?: string }\n ): Promise<ApiResult<DeleteAddressResponse>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<DeleteAddressPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Get customer loyalty details\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with loyalty details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.getLoyaltyDetails();\n *\n * if (error) {\n * console.error(\"Failed to get loyalty details:\", error);\n * return;\n * }\n *\n * console.log(\"Loyalty info:\", data.loyalty);\n * console.log(\"Points balance:\", data.loyalty_point_balance);\n * ```\n */\n public async getLoyaltyDetails(): Promise<ApiResult<GetLoyaltyDetailsContent>>;\n public async getLoyaltyDetails(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<GetLoyaltyDetailsContent>>;\n public async getLoyaltyDetails(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<GetLoyaltyDetailsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<GetLoyaltyDetailsPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/loyalty\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * List all loyalty points activity for a customer\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param queryParams - Optional query parameters when path params are provided.\n * @returns Promise with loyalty points activity\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listLoyaltyPointsActivity();\n *\n * if (error) {\n * console.error(\"Failed to get loyalty activity:\", error);\n * return;\n * }\n *\n * console.log(\"Loyalty activity:\", data.loyalty_points_activity);\n *\n * // With pagination and sorting\n * const { data: sortedData, error: sortedError } = await sdk.customer.listLoyaltyPointsActivity({\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" })\n * });\n * ```\n */\n public async listLoyaltyPointsActivity(): Promise<\n ApiResult<ListLoyaltyActivitiesContent>\n >;\n public async listLoyaltyPointsActivity(\n queryParams: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>>;\n public async listLoyaltyPointsActivity(\n pathParams: { customer_id: string },\n queryParams?: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>>;\n public async listLoyaltyPointsActivity(\n pathParamsOrQuery?:\n | { customer_id?: string }\n | ListLoyaltyActivitiesQuery,\n queryParams?: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>> {\n const hasPathParams =\n queryParams !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"customer_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { customer_id?: string })\n : {};\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListLoyaltyActivitiesPathParams>(\n pathParams\n );\n const resolvedQueryParams = hasPathParams\n ? queryParams\n : (pathParamsOrQuery as ListLoyaltyActivitiesQuery | undefined);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/loyalty-points-activity\", {\n params: {\n path: resolvedPathParams,\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * List all reviews left by a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with reviews\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listCustomerReviews();\n *\n * if (error) {\n * console.error(\"Failed to get customer reviews:\", error);\n * return;\n * }\n *\n * console.log(\"Customer reviews:\", data.reviews);\n * console.log(\"Ready for review:\", data.ready_for_review);\n * ```\n */\n public async listCustomerReviews(): Promise<ApiResult<ListCustomerReviewsContent>>;\n public async listCustomerReviews(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<ListCustomerReviewsContent>>;\n public async listCustomerReviews(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<ListCustomerReviewsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListCustomerReviewsPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/reviews\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * List all saved payment methods for a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @param queryParams - Optional query parameters for filtering.\n * @returns Promise with payment methods\n *\n * @example\n * ```typescript\n * // Uses customer_id from active session\n * const { data, error } = await sdk.customer.listSavedPaymentMethods();\n *\n * // With explicit customer_id\n * const { data: explicit } = await sdk.customer.listSavedPaymentMethods({\n * customer_id: \"customer_123\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list saved payment methods:\", error);\n * return;\n * }\n *\n * console.log(\"Saved payment methods:\", data.saved_payment_methods);\n * ```\n */\n public async listSavedPaymentMethods(): Promise<\n ApiResult<ListSavedPaymentMethodsContent>\n >;\n public async listSavedPaymentMethods(\n pathParams: { customer_id: string },\n queryParams?: ListSavedPaymentMethodsQuery\n ): Promise<ApiResult<ListSavedPaymentMethodsContent>>;\n public async listSavedPaymentMethods(\n pathParams: { customer_id?: string } = {},\n queryParams?: ListSavedPaymentMethodsQuery\n ): Promise<ApiResult<ListSavedPaymentMethodsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListSavedPaymentMethodsPathParams>(\n pathParams\n );\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/payment-methods\", {\n params: {\n path: resolvedPathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * List all saved cards for a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with cards\n *\n * @example\n * ```typescript\n * // Uses customer_id from active session\n * const { data, error } = await sdk.customer.listCustomerCards();\n *\n * // With explicit customer_id\n * const { data: explicit } = await sdk.customer.listCustomerCards({\n * customer_id: \"customer_123\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list customer cards:\", error);\n * return;\n * }\n *\n * console.log(\"Customer cards:\", data.cards);\n * ```\n */\n public async listCustomerCards(): Promise<ApiResult<ListCustomerCardsContent>>;\n public async listCustomerCards(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<ListCustomerCardsContent>>;\n public async listCustomerCards(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<ListCustomerCardsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListCustomerCardsPathParams>(\n pathParams\n );\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/cards\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CheckStoreResponse,\n GetConfigContent,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class BaseStoreConfigClient extends StorefrontAPIClientBase {\n /**\n * Check store existence\n *\n * @description Checks whether a store with the configured store ID exists.\n * Returns `success: true` if the store exists, `false` otherwise.\n *\n * @returns Promise with store existence check result\n * @example\n * ```typescript\n * const { data, error } = await sdk.store.checkStore();\n *\n * if (error) {\n * console.error(\"Failed to check store:\", error.message);\n * } else {\n * console.log(\"Store exists:\", data.success);\n * }\n * ```\n */\n public async checkStore(): Promise<ApiResult<CheckStoreResponse>> {\n return this.executeRequest(() => this.client.GET(\"/store/check\"));\n }\n\n /**\n * Get store config\n *\n * @returns Promise with store configuration data\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.store.getStoreConfig();\n *\n * if (error) {\n * console.error('Failed to get store config:', error.message);\n * return;\n * }\n *\n * // Access store configuration data\n * const storeConfig = data.store_config;\n * console.log('Store brand:', storeConfig.brand.name);\n * console.log('Currency:', storeConfig.currency.code);\n * console.log('KYC enabled:', storeConfig.is_kyc_enabled);\n * console.log('Customer groups enabled:', storeConfig.is_customer_group_enabled);\n * ```\n */\n public async getStoreConfig(): Promise<ApiResult<GetConfigContent>> {\n return this.executeRequest(() => this.client.GET(\"/store/config\"));\n }\n}\n","import { BaseStoreConfigClient } from \"@/lib/shared/store-config\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class PublicStoreConfigClient extends BaseStoreConfigClient {}\n","import { BaseStoreConfigClient } from \"@/lib/shared/store-config\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class StoreConfigClient extends BaseStoreConfigClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n}\n","/**\n * Token storage interface for the auth middleware\n */\nexport interface TokenStorage {\n getAccessToken(): Promise<string | null>;\n setAccessToken(token: string): Promise<void>;\n getRefreshToken(): Promise<string | null>;\n setRefreshToken(token: string): Promise<void>;\n clearTokens(): Promise<void>;\n}\n\n/**\n * Simple in-memory token storage implementation\n */\nexport class MemoryTokenStorage implements TokenStorage {\n private accessToken: string | null = null;\n private refreshToken: string | null = null;\n\n async getAccessToken(): Promise<string | null> {\n return this.accessToken;\n }\n\n async setAccessToken(token: string): Promise<void> {\n this.accessToken = token;\n }\n\n async getRefreshToken(): Promise<string | null> {\n return this.refreshToken;\n }\n\n async setRefreshToken(token: string): Promise<void> {\n this.refreshToken = token;\n }\n\n async clearTokens(): Promise<void> {\n this.accessToken = null;\n this.refreshToken = null;\n }\n}\n\n/**\n * Browser localStorage token storage implementation\n */\nexport class BrowserTokenStorage implements TokenStorage {\n private accessTokenKey: string;\n private refreshTokenKey: string;\n\n constructor(prefix: string = \"storefront_\") {\n this.accessTokenKey = `${prefix}access_token`;\n this.refreshTokenKey = `${prefix}refresh_token`;\n }\n\n async getAccessToken(): Promise<string | null> {\n if (typeof localStorage === \"undefined\") return null;\n return localStorage.getItem(this.accessTokenKey);\n }\n\n async setAccessToken(token: string): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.setItem(this.accessTokenKey, token);\n }\n }\n\n async getRefreshToken(): Promise<string | null> {\n if (typeof localStorage === \"undefined\") return null;\n return localStorage.getItem(this.refreshTokenKey);\n }\n\n async setRefreshToken(token: string): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.setItem(this.refreshTokenKey, token);\n }\n }\n\n async clearTokens(): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.removeItem(this.accessTokenKey);\n localStorage.removeItem(this.refreshTokenKey);\n }\n }\n}\n\n/**\n * Cookie-based token storage implementation\n */\nexport class CookieTokenStorage implements TokenStorage {\n private accessTokenKey: string;\n private refreshTokenKey: string;\n private options: CookieOptions;\n\n constructor(options: CookieTokenStorageOptions = {}) {\n const prefix = options.prefix || \"storefront_\";\n this.accessTokenKey = `${prefix}access_token`;\n this.refreshTokenKey = `${prefix}refresh_token`;\n\n this.options = {\n maxAge: options.maxAge || 7 * 24 * 60 * 60, // 7 days default\n path: options.path || \"/\",\n domain: options.domain,\n secure:\n options.secure ??\n (typeof window !== \"undefined\" &&\n window.location?.protocol === \"https:\"),\n sameSite: options.sameSite || \"Lax\",\n httpOnly: false, // Must be false for client-side access\n };\n }\n\n async getAccessToken(): Promise<string | null> {\n return this.getCookie(this.accessTokenKey);\n }\n\n async setAccessToken(token: string): Promise<void> {\n this.setCookie(this.accessTokenKey, token);\n }\n\n async getRefreshToken(): Promise<string | null> {\n return this.getCookie(this.refreshTokenKey);\n }\n\n async setRefreshToken(token: string): Promise<void> {\n this.setCookie(this.refreshTokenKey, token);\n }\n\n async clearTokens(): Promise<void> {\n this.deleteCookie(this.accessTokenKey);\n this.deleteCookie(this.refreshTokenKey);\n }\n\n private getCookie(name: string): string | null {\n if (typeof document === \"undefined\") return null;\n\n const value = `; ${document.cookie}`;\n const parts = value.split(`; ${name}=`);\n\n if (parts.length === 2) {\n const cookieValue = parts.pop()?.split(\";\").shift();\n return cookieValue ? decodeURIComponent(cookieValue) : null;\n }\n\n return null;\n }\n\n private setCookie(name: string, value: string): void {\n if (typeof document === \"undefined\") return;\n\n const encodedValue = encodeURIComponent(value);\n let cookieString = `${name}=${encodedValue}`;\n\n if (this.options.maxAge) {\n cookieString += `; Max-Age=${this.options.maxAge}`;\n }\n\n if (this.options.path) {\n cookieString += `; Path=${this.options.path}`;\n }\n\n if (this.options.domain) {\n cookieString += `; Domain=${this.options.domain}`;\n }\n\n if (this.options.secure) {\n cookieString += `; Secure`;\n }\n\n if (this.options.sameSite) {\n cookieString += `; SameSite=${this.options.sameSite}`;\n }\n\n document.cookie = cookieString;\n }\n\n private deleteCookie(name: string): void {\n if (typeof document === \"undefined\") return;\n\n let cookieString = `${name}=; Max-Age=0`;\n\n if (this.options.path) {\n cookieString += `; Path=${this.options.path}`;\n }\n\n if (this.options.domain) {\n cookieString += `; Domain=${this.options.domain}`;\n }\n\n document.cookie = cookieString;\n }\n}\n\n/**\n * Configuration options for CookieTokenStorage\n */\nexport interface CookieTokenStorageOptions {\n /**\n * Prefix for cookie names (default: \"storefront_\")\n */\n prefix?: string;\n\n /**\n * Maximum age of cookies in seconds (default: 7 days)\n */\n maxAge?: number;\n\n /**\n * Cookie path (default: \"/\")\n */\n path?: string;\n\n /**\n * Cookie domain (default: current domain)\n */\n domain?: string;\n\n /**\n * Whether cookies should be secure (default: auto-detect based on protocol)\n */\n secure?: boolean;\n\n /**\n * SameSite cookie attribute (default: \"Lax\")\n */\n sameSite?: \"Strict\" | \"Lax\" | \"None\";\n}\n\n/**\n * Internal cookie options interface\n */\ninterface CookieOptions {\n maxAge?: number;\n path?: string;\n domain?: string;\n secure?: boolean;\n sameSite?: \"Strict\" | \"Lax\" | \"None\";\n httpOnly?: boolean;\n}\n","/**\n * Decode a JWT token payload without signature verification.\n * This is a lightweight replacement for jose's decodeJwt.\n *\n * @param token - The JWT token to decode\n * @returns The decoded payload\n * @throws Error if the token is malformed\n */\nfunction decodeJwt<T = Record<string, unknown>>(token: string): T {\n if (typeof token !== \"string\") {\n throw new Error(\"Invalid token: must be a string\");\n }\n\n const parts = token.split(\".\");\n if (parts.length !== 3) {\n throw new Error(\"Invalid token: must have 3 parts\");\n }\n\n const base64Url = parts[1];\n if (!base64Url) throw new Error(\"Invalid token: missing payload\");\n\n let base64 = base64Url.replace(/-/g, \"+\").replace(/_/g, \"/\");\n const padding = base64.length % 4;\n if (padding) base64 += \"=\".repeat(4 - padding);\n\n // UTF-8 safe decoding\n const binaryStr = atob(base64);\n const bytes = new Uint8Array(binaryStr.length);\n for (let i = 0; i < binaryStr.length; i++) {\n bytes[i] = binaryStr.charCodeAt(i);\n }\n\n const payload = JSON.parse(new TextDecoder().decode(bytes));\n if (typeof payload !== \"object\" || payload === null) {\n throw new Error(\"Invalid token: payload must be an object\");\n }\n\n return payload;\n}\n\n/**\n * Channel information from JWT token\n */\nexport interface Channel {\n id: string;\n name: string;\n type: string;\n}\n\n/**\n * JWT payload structure for storefront tokens\n */\nexport interface JwtPayload {\n token_type: string;\n exp: number;\n iat: number;\n jti: string;\n ulid: string;\n email: string | null;\n phone: string | null;\n username: string;\n first_name: string | null;\n last_name: string | null;\n store_id: string;\n is_logged_in: boolean;\n customer_id: string | null;\n customer_group_id: string | null;\n anonymous_id: string;\n is_anonymous: boolean;\n channel: Channel;\n}\n\n/**\n * User information extracted from JWT token\n */\nexport interface UserInfo {\n id: string;\n email: string | null;\n phone: string | null;\n username: string;\n firstName: string | null;\n lastName: string | null;\n storeId: string;\n isLoggedIn: boolean;\n isAnonymous: boolean;\n customerId: string | null;\n customerGroupId: string | null;\n anonymousId: string;\n channel: Channel;\n tokenExpiry: Date;\n tokenIssuedAt: Date;\n}\n\n/**\n * Decode and extract user information from a JWT token\n * \n * @param token - The JWT token to decode\n * @returns User information or null if token is invalid\n */\nexport function extractUserInfoFromToken(token: string): UserInfo | null {\n try {\n const payload = decodeJwt(token) as JwtPayload;\n \n return {\n id: payload.ulid,\n email: payload.email,\n phone: payload.phone,\n username: payload.username,\n firstName: payload.first_name,\n lastName: payload.last_name,\n storeId: payload.store_id,\n isLoggedIn: payload.is_logged_in,\n isAnonymous: payload.is_anonymous,\n customerId: payload.customer_id,\n customerGroupId: payload.customer_group_id,\n anonymousId: payload.anonymous_id,\n channel: payload.channel,\n tokenExpiry: new Date(payload.exp * 1000),\n tokenIssuedAt: new Date(payload.iat * 1000),\n };\n } catch (error) {\n console.warn(\"Failed to decode JWT token:\", error);\n return null;\n }\n}\n\n/**\n * Check if a JWT token is expired\n * \n * @param token - The JWT token to check\n * @param bufferSeconds - Buffer time in seconds (default: 30)\n * @returns True if token is expired or will expire within buffer time\n */\nexport function isTokenExpired(token: string, bufferSeconds: number = 30): boolean {\n try {\n const payload = decodeJwt<{ exp?: number }>(token);\n if (!payload.exp) return true;\n\n const currentTime = Math.floor(Date.now() / 1000);\n const expiryTime = payload.exp;\n \n // Consider token expired if it expires within the buffer time\n return currentTime >= (expiryTime - bufferSeconds);\n } catch (error) {\n console.warn(\"Failed to decode JWT token:\", error);\n return true; // Treat invalid tokens as expired\n }\n}\n\n/**\n * Get the user ID from a JWT token\n * \n * @param token - The JWT token\n * @returns User ID (ulid) or null if token is invalid\n */\nexport function getUserIdFromToken(token: string): string | null {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.id || null;\n}\n\n/**\n * Check if user is logged in based on JWT token\n * \n * @param token - The JWT token\n * @returns True if user is logged in, false otherwise\n */\nexport function isUserLoggedIn(token: string): boolean {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.isLoggedIn || false;\n}\n\n/**\n * Check if user is anonymous based on JWT token\n * \n * @param token - The JWT token\n * @returns True if user is anonymous, false otherwise\n */\nexport function isUserAnonymous(token: string): boolean {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.isAnonymous ?? true;\n} \n","// Auto-generated auth operation metadata from the OpenAPI spec\n// Do not edit manually - regenerate using generate-auth-operation-metadata.py\n\nexport type StorefrontHttpMethod = \"GET\" | \"POST\" | \"PUT\" | \"DELETE\" | \"PATCH\" | \"HEAD\" | \"OPTIONS\";\n\nexport type StorefrontAuthOperation = {\n method: StorefrontHttpMethod;\n path: string;\n};\n\nexport const API_KEY_ONLY_OPERATIONS = [\n { method: \"POST\", path: \"/auth/anonymous\" },\n { method: \"GET\", path: \"/common/countries\" },\n { method: \"GET\", path: \"/common/countries/{country_iso_code}/pincodes\" },\n { method: \"GET\", path: \"/common/countries/{country_iso_code}/states\" },\n { method: \"GET\", path: \"/store/check\" },\n { method: \"GET\", path: \"/store/config\" },\n { method: \"GET\", path: \"/store/kyc-document\" },\n { method: \"GET\", path: \"/store/sellers/{id}\" },\n { method: \"GET\", path: \"/store/sellers/{id}/reviews\" },\n] as const;\n\nexport const DUAL_AUTH_OPERATIONS = [\n { method: \"GET\", path: \"/catalog/categories\" },\n { method: \"GET\", path: \"/catalog/products\" },\n { method: \"GET\", path: \"/catalog/products/cross-sell\" },\n { method: \"POST\", path: \"/catalog/products/search\" },\n { method: \"GET\", path: \"/catalog/products/similar\" },\n { method: \"GET\", path: \"/catalog/products/up-sell\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/variants\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/variants/{variant_id}\" },\n { method: \"GET\", path: \"/catalog/skus\" },\n] as const;\n\nexport const SESSION_ONLY_OPERATIONS = [\n { method: \"POST\", path: \"/analytics/track\" },\n { method: \"POST\", path: \"/auth/change-password\" },\n { method: \"POST\", path: \"/auth/forgot-password\" },\n { method: \"POST\", path: \"/auth/generate-otp\" },\n { method: \"POST\", path: \"/auth/login/email\" },\n { method: \"POST\", path: \"/auth/login/password\" },\n { method: \"POST\", path: \"/auth/login/phone\" },\n { method: \"POST\", path: \"/auth/login/whatsapp\" },\n { method: \"POST\", path: \"/auth/logout\" },\n { method: \"POST\", path: \"/auth/refresh-token\" },\n { method: \"POST\", path: \"/auth/register/email\" },\n { method: \"POST\", path: \"/auth/register/password\" },\n { method: \"POST\", path: \"/auth/register/phone\" },\n { method: \"POST\", path: \"/auth/register/whatsapp\" },\n { method: \"POST\", path: \"/auth/reset-password\" },\n { method: \"DELETE\", path: \"/auth/user/{id}\" },\n { method: \"GET\", path: \"/auth/user/{id}\" },\n { method: \"PUT\", path: \"/auth/user/{id}\" },\n { method: \"PUT\", path: \"/auth/user/{id}/deactivate\" },\n { method: \"DELETE\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"GET\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"POST\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"PUT\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"POST\", path: \"/auth/verified-email-phone\" },\n { method: \"POST\", path: \"/auth/verify-otp\" },\n { method: \"POST\", path: \"/campaigns/newsletter-subscribe\" },\n { method: \"POST\", path: \"/carts\" },\n { method: \"GET\", path: \"/carts/available-coupons\" },\n { method: \"GET\", path: \"/carts/available-promotions\" },\n { method: \"POST\", path: \"/carts/fulfillment-options\" },\n { method: \"DELETE\", path: \"/carts/users/{user_id}\" },\n { method: \"GET\", path: \"/carts/users/{user_id}\" },\n { method: \"DELETE\", path: \"/carts/{id}\" },\n { method: \"GET\", path: \"/carts/{id}\" },\n { method: \"POST\", path: \"/carts/{id}/address\" },\n { method: \"DELETE\", path: \"/carts/{id}/coupon\" },\n { method: \"POST\", path: \"/carts/{id}/coupon\" },\n { method: \"DELETE\", path: \"/carts/{id}/credit-balance\" },\n { method: \"POST\", path: \"/carts/{id}/credit-balance\" },\n { method: \"GET\", path: \"/carts/{id}/evaluate-coupons\" },\n { method: \"GET\", path: \"/carts/{id}/evaluate-promotions\" },\n { method: \"POST\", path: \"/carts/{id}/fulfillment-preference\" },\n { method: \"POST\", path: \"/carts/{id}/items\" },\n { method: \"DELETE\", path: \"/carts/{id}/loyalty-points\" },\n { method: \"POST\", path: \"/carts/{id}/loyalty-points\" },\n { method: \"GET\", path: \"/catalog/marketplace/categories\" },\n { method: \"GET\", path: \"/catalog/marketplace/products\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/cross-sell\" },\n { method: \"POST\", path: \"/catalog/marketplace/products/search\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/similar\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/up-sell\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/reviews\" },\n { method: \"POST\", path: \"/catalog/marketplace/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/variants\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/variants/{variant_id}\" },\n { method: \"GET\", path: \"/catalog/marketplace/skus\" },\n { method: \"POST\", path: \"/catalog/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/customers/{customer_id}/addresses\" },\n { method: \"POST\", path: \"/customers/{customer_id}/addresses\" },\n { method: \"DELETE\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"PUT\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/cards\" },\n { method: \"GET\", path: \"/customers/{customer_id}/documents\" },\n { method: \"POST\", path: \"/customers/{customer_id}/documents\" },\n { method: \"POST\", path: \"/customers/{customer_id}/documents/verify\" },\n { method: \"DELETE\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"PUT\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/loyalty\" },\n { method: \"GET\", path: \"/customers/{customer_id}/loyalty-points-activity\" },\n { method: \"GET\", path: \"/customers/{customer_id}/payment-methods\" },\n { method: \"GET\", path: \"/customers/{customer_id}/reviews\" },\n { method: \"POST\", path: \"/fulfillment/serviceability\" },\n { method: \"GET\", path: \"/orders\" },\n { method: \"POST\", path: \"/orders\" },\n { method: \"GET\", path: \"/orders/returns\" },\n { method: \"GET\", path: \"/orders/{order_number}\" },\n { method: \"POST\", path: \"/orders/{order_number}/cancel\" },\n { method: \"POST\", path: \"/orders/{order_number}/cancel-payment-request\" },\n { method: \"GET\", path: \"/orders/{order_number}/payment-status\" },\n { method: \"GET\", path: \"/orders/{order_number}/payments\" },\n { method: \"GET\", path: \"/orders/{order_number}/refunds\" },\n { method: \"POST\", path: \"/orders/{order_number}/retry-payment\" },\n { method: \"POST\", path: \"/orders/{order_number}/return\" },\n { method: \"GET\", path: \"/orders/{order_number}/return/{return_id}\" },\n { method: \"GET\", path: \"/orders/{order_number}/shipments\" },\n { method: \"POST\", path: \"/payments/authenticate-direct-otp\" },\n { method: \"GET\", path: \"/payments/card-info\" },\n { method: \"POST\", path: \"/payments/generate-hash\" },\n { method: \"POST\", path: \"/payments/juspay/create-order\" },\n { method: \"POST\", path: \"/payments/juspay/customers\" },\n { method: \"GET\", path: \"/payments/juspay/customers/{user_id}\" },\n { method: \"GET\", path: \"/payments/payment-methods\" },\n { method: \"POST\", path: \"/payments/resend-direct-otp\" },\n { method: \"GET\", path: \"/payments/verify-vpa\" },\n { method: \"GET\", path: \"/subscriptions\" },\n { method: \"POST\", path: \"/subscriptions\" },\n { method: \"GET\", path: \"/subscriptions/{id}\" },\n { method: \"PUT\", path: \"/subscriptions/{id}\" },\n { method: \"DELETE\", path: \"/wishlist/{user_id}\" },\n { method: \"GET\", path: \"/wishlist/{user_id}\" },\n { method: \"POST\", path: \"/wishlist/{user_id}\" },\n] as const;\n","import {\n API_KEY_ONLY_OPERATIONS,\n DUAL_AUTH_OPERATIONS,\n type StorefrontAuthOperation,\n} from \"@/types/auth-operation-metadata\";\n\nconst TOKEN_RETURNING_OPERATIONS = [\n { method: \"POST\", path: \"/auth/change-password\" },\n { method: \"POST\", path: \"/auth/login/password\" },\n { method: \"POST\", path: \"/auth/reset-password\" },\n { method: \"POST\", path: \"/auth/verify-otp\" },\n { method: \"POST\", path: \"/auth/refresh-token\" },\n { method: \"POST\", path: \"/auth/logout\" },\n] as const satisfies readonly StorefrontAuthOperation[];\n\nconst ANONYMOUS_AUTH_OPERATION = {\n method: \"POST\",\n path: \"/auth/anonymous\",\n} as const satisfies StorefrontAuthOperation;\n\nfunction normalizeMethod(method: string): string {\n return method.toUpperCase();\n}\n\nfunction normalizePathname(pathname: string): string {\n let normalizedPathname = pathname;\n\n const storefrontMarker = \"/storefront\";\n const storefrontMarkerIndex = normalizedPathname.indexOf(storefrontMarker);\n\n // Requests in middleware carry the full API pathname\n // (`/api/v1/{storeId}/storefront/...`), while generated auth metadata is\n // keyed by storefront-relative operation paths (`/auth/anonymous`). Strip\n // the API prefix so method+path matching stays aligned with the spec.\n if (storefrontMarkerIndex !== -1) {\n normalizedPathname =\n normalizedPathname.slice(storefrontMarkerIndex + storefrontMarker.length) ||\n \"/\";\n }\n\n if (normalizedPathname.length > 1 && normalizedPathname.endsWith(\"/\")) {\n return normalizedPathname.slice(0, -1);\n }\n\n return normalizedPathname;\n}\n\nfunction matchesPathTemplate(pathTemplate: string, pathname: string): boolean {\n const normalizedTemplate = normalizePathname(pathTemplate);\n const normalizedPathname = normalizePathname(pathname);\n\n const templateSegments = normalizedTemplate.split(\"/\").filter(Boolean);\n const pathSegments = normalizedPathname.split(\"/\").filter(Boolean);\n\n if (templateSegments.length !== pathSegments.length) {\n return false;\n }\n\n return templateSegments.every((templateSegment, index) => {\n if (\n templateSegment.startsWith(\"{\") &&\n templateSegment.endsWith(\"}\")\n ) {\n return true;\n }\n\n return templateSegment === pathSegments[index];\n });\n}\n\nfunction matchesOperation(\n method: string,\n pathname: string,\n operation: StorefrontAuthOperation\n): boolean {\n return (\n normalizeMethod(method) === operation.method &&\n matchesPathTemplate(operation.path, pathname)\n );\n}\n\nfunction matchesOperationList(\n method: string,\n pathname: string,\n operations: readonly StorefrontAuthOperation[]\n): boolean {\n return operations.some((operation) => matchesOperation(method, pathname, operation));\n}\n\n/**\n * Check if a method+path pair is the anonymous auth operation.\n */\nexport function isAnonymousAuthOperation(method: string, pathname: string): boolean {\n return matchesOperation(method, pathname, ANONYMOUS_AUTH_OPERATION);\n}\n\n/**\n * Check if a method+path pair requires API key only authentication.\n */\nexport function isApiKeyOnlyOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, API_KEY_ONLY_OPERATIONS);\n}\n\n/**\n * Check if a method+path pair supports both bearer and API key authentication.\n */\nexport function isDualAuthOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, DUAL_AUTH_OPERATIONS);\n}\n\n/**\n * Check if a method+path pair returns tokens in a successful response.\n */\nexport function isTokenReturningOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, TOKEN_RETURNING_OPERATIONS);\n}\n","import { getPathnameFromUrl } from \"@commercengine/sdk-core\";\nimport type { Middleware } from \"openapi-fetch\";\nimport {\n isAnonymousAuthOperation,\n isApiKeyOnlyOperation,\n isTokenReturningOperation,\n} from \"./auth-utils\";\nimport type { TokenStorage } from \"@/lib/storage/token-storage\";\nimport {\n extractUserInfoFromToken,\n getUserIdFromToken,\n isTokenExpired,\n isUserLoggedIn,\n type UserInfo,\n} from \"./jwt-utils\";\n\n/**\n * Public session helpers exposed as `sdk.session`.\n *\n * These methods are split into two groups:\n * - `peek*`: passive lookups that never create or refresh tokens\n * - `ensure*`: active helpers that may create or refresh tokens when automatic\n * token management is enabled. They throw when no session can be established.\n */\nexport interface StorefrontSession {\n /**\n * Read the current access token without creating a new session.\n *\n * @returns The current access token, or `null` when no token is available\n */\n peekAccessToken(): Promise<string | null>;\n\n /**\n * Read the current refresh token without creating a new session.\n *\n * @returns The current refresh token, or `null` when no token is available\n */\n peekRefreshToken(): Promise<string | null>;\n\n /**\n * Read user information from the current token without creating a new session.\n *\n * @returns Decoded user information, or `null` when no token is available\n */\n peekUserInfo(): Promise<UserInfo | null>;\n\n /**\n * Read the current user ID without creating a new session.\n *\n * @returns The current user ID, or `null` when no token is available\n */\n peekUserId(): Promise<string | null>;\n\n /**\n * Read the current customer ID without creating a new session.\n *\n * @returns The current customer ID, or `null` when no token is available\n */\n peekCustomerId(): Promise<string | null>;\n\n /**\n * Read the current customer group ID without creating a new session.\n *\n * @returns The current customer group ID, or `null` when no token is available\n */\n peekCustomerGroupId(): Promise<string | null>;\n\n /**\n * Ensure an access token is available for the current session.\n *\n * In managed mode, this may create an anonymous session or refresh an expired\n * token. In manual mode, it only returns the currently configured token.\n *\n * @returns A usable access token\n * @throws When no session can be established\n */\n ensureAccessToken(): Promise<string>;\n\n /**\n * Ensure user information is available for the current session.\n *\n * @returns Decoded user information\n * @throws When no session can be established\n */\n ensureUserInfo(): Promise<UserInfo>;\n\n /**\n * Ensure a user ID is available for the current session.\n *\n * @returns The current user ID\n * @throws When no session can be established\n */\n ensureUserId(): Promise<string>;\n\n /**\n * Ensure a customer ID is available for the current session.\n *\n * @returns The current customer ID\n * @throws When the user is anonymous or no session can be established\n */\n ensureCustomerId(): Promise<string>;\n\n /**\n * Clear all known session tokens.\n */\n clear(): Promise<void>;\n}\n\ninterface SessionManagerOptions {\n accessToken?: string;\n apiKey?: string;\n baseUrl: string;\n onTokensCleared?: () => void;\n onTokensUpdated?: (accessToken: string, refreshToken: string) => void;\n refreshToken?: string;\n tokenStorage?: TokenStorage;\n\n /**\n * Custom function to refresh tokens.\n * When provided, this is used instead of the default fetch to `/auth/refresh-token`.\n */\n refreshTokenFn?: (refreshToken: string) => Promise<{\n access_token: string;\n refresh_token: string;\n }>;\n}\n\ntype TokenPair = {\n access_token: string;\n refresh_token: string;\n};\n\n/**\n * Snapshot of the current access and refresh tokens, used by\n * {@link StorefrontSessionManager.notifyTokensUpdatedIfChanged} to detect\n * whether `setTokens()` actually changed anything before firing the callback.\n */\ntype SessionTokenState = {\n accessToken: string | null;\n refreshToken: string | null;\n};\n\n/**\n * Internal per-SDK session controller.\n *\n * A single instance is shared by all API clients created from the same\n * `SessionStorefrontSDK`. This keeps refresh locks, token assessment, and session\n * bootstrap logic coordinated in one place while preserving optional manual\n * token management when `tokenStorage` is not provided.\n */\nexport class StorefrontSessionManager implements StorefrontSession {\n private readonly tokenStorage?: TokenStorage;\n private readonly onTokensUpdated?: (accessToken: string, refreshToken: string) => void;\n private readonly onTokensCleared?: () => void;\n private readonly baseUrl: string;\n private readonly refreshTokenFn?: (refreshToken: string) => Promise<TokenPair>;\n private apiKey?: string;\n private accessToken: string | null;\n private refreshToken: string | null;\n private initializationPromise: Promise<void> | null = null;\n private refreshPromise: Promise<void> | null = null;\n private bootstrapPromise: Promise<string | null> | null = null;\n private hasAssessedTokens = false;\n\n constructor(options: SessionManagerOptions) {\n this.tokenStorage = options.tokenStorage;\n this.baseUrl = options.baseUrl;\n this.apiKey = options.apiKey;\n this.onTokensUpdated = options.onTokensUpdated;\n this.onTokensCleared = options.onTokensCleared;\n this.accessToken = options.accessToken ?? null;\n this.refreshToken = options.refreshToken ?? null;\n this.refreshTokenFn = options.refreshTokenFn;\n\n if (this.tokenStorage && this.accessToken) {\n this.initializationPromise = this.initializeManagedTokens(\n this.accessToken,\n this.refreshToken\n );\n }\n }\n\n /**\n * Update the API key used by session bootstrap and refresh flows.\n */\n public setApiKey(apiKey: string): void {\n this.apiKey = apiKey;\n }\n\n /**\n * Remove the API key used by session bootstrap and refresh flows.\n */\n public clearApiKey(): void {\n this.apiKey = undefined;\n }\n\n /**\n * Create the auth middleware used by each API client.\n *\n * The returned middleware shares the same session state and refresh locking\n * across all clients attached to a single `SessionStorefrontSDK` instance.\n */\n public createAuthMiddleware(): Middleware {\n return {\n onRequest: async ({ request }) => this.handleRequest(request),\n onResponse: async ({ request, response }) =>\n this.handleResponse(request, response),\n };\n }\n\n /**\n * Read the current authorization header without creating a new session.\n *\n * @returns A `Bearer` header value, or an empty string when no token exists\n */\n public async getAuthorizationHeader(): Promise<string> {\n const token = await this.peekAccessToken();\n return token ? `Bearer ${token}` : \"\";\n }\n\n /**\n * Persist new session tokens.\n *\n * In managed mode, tokens are written to the configured token storage. In\n * manual mode, they are stored in memory for header injection and session\n * inspection.\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n const previousTokens = await this.getCurrentTokenState();\n\n if (this.tokenStorage) {\n await this.awaitInitialization();\n await this.storeManagedTokens(accessToken, refreshToken ?? null);\n } else {\n this.accessToken = accessToken;\n\n if (refreshToken) {\n this.refreshToken = refreshToken;\n console.warn(\n \"Refresh token provided but automatic refresh is disabled because tokenStorage is not configured.\"\n );\n }\n }\n\n const nextTokens = await this.getCurrentTokenState();\n this.notifyTokensUpdatedIfChanged(previousTokens, nextTokens);\n }\n\n /**\n * Clear all session tokens managed by this controller.\n */\n public async clearTokens(): Promise<void> {\n if (this.tokenStorage) {\n await this.awaitInitialization();\n await this.tokenStorage.clearTokens();\n } else {\n this.accessToken = null;\n this.refreshToken = null;\n }\n this.onTokensCleared?.();\n }\n\n /**\n * Clear all session tokens through the public session interface.\n */\n public async clear(): Promise<void> {\n await this.clearTokens();\n }\n\n // ---------------------------------------------------------------------------\n // Passive peek methods — never create or refresh tokens\n // ---------------------------------------------------------------------------\n\n public async peekAccessToken(): Promise<string | null> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return this.tokenStorage.getAccessToken();\n }\n\n return this.accessToken;\n }\n\n public async peekRefreshToken(): Promise<string | null> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return this.tokenStorage.getRefreshToken();\n }\n\n return this.refreshToken;\n }\n\n public async peekUserInfo(): Promise<UserInfo | null> {\n const token = await this.peekAccessToken();\n if (!token) return null;\n return extractUserInfoFromToken(token);\n }\n\n public async peekUserId(): Promise<string | null> {\n const token = await this.peekAccessToken();\n if (!token) return null;\n return getUserIdFromToken(token);\n }\n\n public async peekCustomerId(): Promise<string | null> {\n const userInfo = await this.peekUserInfo();\n return userInfo?.customerId ?? null;\n }\n\n public async peekCustomerGroupId(): Promise<string | null> {\n const userInfo = await this.peekUserInfo();\n return userInfo?.customerGroupId ?? null;\n }\n\n // ---------------------------------------------------------------------------\n // Active ensure methods — may create/refresh tokens, throw on failure\n // ---------------------------------------------------------------------------\n\n public async ensureAccessToken(): Promise<string> {\n const token = await this.getOrCreateAccessToken();\n if (!token) {\n throw new Error(\n \"No session available. Configure tokenStorage + apiKey for automatic session management, or call setTokens() to set tokens manually.\"\n );\n }\n return token;\n }\n\n public async ensureUserInfo(): Promise<UserInfo> {\n const token = await this.ensureAccessToken();\n const userInfo = extractUserInfoFromToken(token);\n if (!userInfo) {\n throw new Error(\"Failed to extract user information from access token.\");\n }\n return userInfo;\n }\n\n public async ensureUserId(): Promise<string> {\n const token = await this.ensureAccessToken();\n const userId = getUserIdFromToken(token);\n if (!userId) {\n throw new Error(\"Failed to extract user ID from access token.\");\n }\n return userId;\n }\n\n public async ensureCustomerId(): Promise<string> {\n const userInfo = await this.ensureUserInfo();\n if (!userInfo.customerId) {\n throw new Error(\n \"No customer_id available. User must be logged in (not anonymous) for this operation. Pass customer_id explicitly or log in first.\"\n );\n }\n return userInfo.customerId;\n }\n\n // ---------------------------------------------------------------------------\n // Middleware handlers\n // ---------------------------------------------------------------------------\n\n private async handleRequest(request: Request): Promise<Request | Response> {\n const method = request.method;\n const pathname = getPathnameFromUrl(request.url);\n\n if (this.tokenStorage) {\n await this.assessTokenStateOnce();\n }\n\n if (isAnonymousAuthOperation(method, pathname)) {\n return this.prepareAnonymousAuthRequest(request);\n }\n\n if (isApiKeyOnlyOperation(method, pathname)) {\n this.applyApiKeyHeader(request);\n return request;\n }\n\n // Middleware uses the non-throwing variant so requests degrade\n // gracefully (server returns 401) rather than throwing before send.\n const accessToken = await this.getOrCreateAccessToken();\n if (accessToken) {\n request.headers.set(\"Authorization\", `Bearer ${accessToken}`);\n }\n\n return request;\n }\n\n private async handleResponse(\n request: Request,\n response: Response\n ): Promise<Response> {\n if (!this.tokenStorage) {\n return response;\n }\n\n const method = request.method;\n const pathname = getPathnameFromUrl(request.url);\n\n if (response.ok) {\n await this.captureTokensFromResponse(method, pathname, response);\n return response;\n }\n\n if (\n response.status === 401 &&\n !isAnonymousAuthOperation(method, pathname) &&\n !isApiKeyOnlyOperation(method, pathname)\n ) {\n const currentToken = await this.peekAccessToken();\n\n if (currentToken && isTokenExpired(currentToken, 0)) {\n try {\n await this.refreshTokens();\n\n const refreshedToken = await this.peekAccessToken();\n if (refreshedToken) {\n const retryRequest = request.clone();\n retryRequest.headers.set(\"Authorization\", `Bearer ${refreshedToken}`);\n return fetch(retryRequest);\n }\n } catch (error) {\n console.warn(\"Token refresh failed on 401 response:\", error);\n }\n }\n }\n\n return response;\n }\n\n private async prepareAnonymousAuthRequest(\n request: Request\n ): Promise<Request | Response> {\n this.applyApiKeyHeader(request);\n\n const existingToken = await this.peekAccessToken();\n\n if (\n this.tokenStorage &&\n existingToken &&\n !isTokenExpired(existingToken) &&\n isUserLoggedIn(existingToken)\n ) {\n return new Response(\n JSON.stringify({\n message: \"Cannot create anonymous session while authenticated\",\n success: false,\n code: \"USER_ALREADY_AUTHENTICATED\",\n }),\n {\n status: 400,\n headers: { \"Content-Type\": \"application/json\" },\n }\n );\n }\n\n if (existingToken) {\n request.headers.set(\"Authorization\", `Bearer ${existingToken}`);\n }\n\n return request;\n }\n\n // ---------------------------------------------------------------------------\n // Internal helpers\n // ---------------------------------------------------------------------------\n\n private applyApiKeyHeader(request: Request): void {\n if (this.apiKey) {\n request.headers.set(\"X-Api-Key\", this.apiKey);\n }\n }\n\n /**\n * Snapshot the effective token pair from storage (managed mode) or\n * in-memory fields (manual mode). Used before and after `setTokens()` to\n * detect whether the tokens actually changed.\n */\n private async getCurrentTokenState(): Promise<SessionTokenState> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return {\n accessToken: await this.tokenStorage.getAccessToken(),\n refreshToken: await this.tokenStorage.getRefreshToken(),\n };\n }\n\n return {\n accessToken: this.accessToken,\n refreshToken: this.refreshToken,\n };\n }\n\n /**\n * Fire `onTokensUpdated` only when the effective token pair differs from\n * the previous snapshot. This prevents duplicate notifications when\n * `setTokens()` is called with the same values already in storage.\n */\n private notifyTokensUpdatedIfChanged(\n previousTokens: SessionTokenState,\n nextTokens: SessionTokenState\n ): void {\n if (!this.onTokensUpdated || !nextTokens.accessToken) {\n return;\n }\n\n if (\n previousTokens.accessToken === nextTokens.accessToken &&\n previousTokens.refreshToken === nextTokens.refreshToken\n ) {\n return;\n }\n\n this.onTokensUpdated(\n nextTokens.accessToken,\n nextTokens.refreshToken ?? \"\"\n );\n }\n\n /**\n * Internal token acquisition — returns null on failure instead of throwing.\n * Used by middleware so requests degrade gracefully.\n */\n private async getOrCreateAccessToken(): Promise<string | null> {\n if (!this.tokenStorage) {\n return this.peekAccessToken();\n }\n\n await this.awaitInitialization();\n await this.assessTokenStateOnce();\n\n let accessToken = await this.tokenStorage.getAccessToken();\n\n if (!accessToken) {\n accessToken = await this.bootstrapAnonymousSession();\n }\n\n if (accessToken && isTokenExpired(accessToken)) {\n try {\n await this.refreshTokens();\n accessToken = await this.tokenStorage.getAccessToken();\n } catch {\n accessToken = await this.tokenStorage.getAccessToken();\n }\n }\n\n return accessToken;\n }\n\n private async initializeManagedTokens(\n accessToken: string,\n refreshToken: string | null\n ): Promise<void> {\n try {\n await this.storeManagedTokens(accessToken, refreshToken);\n } catch (error) {\n console.warn(\"Failed to initialize tokens in storage:\", error);\n } finally {\n this.accessToken = null;\n this.refreshToken = null;\n }\n }\n\n private async awaitInitialization(): Promise<void> {\n if (this.initializationPromise) {\n await this.initializationPromise;\n this.initializationPromise = null;\n }\n }\n\n private async assessTokenStateOnce(): Promise<void> {\n if (!this.tokenStorage || this.hasAssessedTokens) {\n return;\n }\n\n this.hasAssessedTokens = true;\n\n try {\n const accessToken = await this.tokenStorage.getAccessToken();\n const refreshToken = await this.tokenStorage.getRefreshToken();\n\n if (!accessToken && refreshToken) {\n await this.tokenStorage.clearTokens();\n console.info(\"Cleaned up orphaned refresh token\");\n }\n } catch (error) {\n console.warn(\"Token state assessment failed:\", error);\n }\n }\n\n private async bootstrapAnonymousSession(): Promise<string | null> {\n if (!this.tokenStorage) {\n return null;\n }\n\n if (this.bootstrapPromise) {\n return this.bootstrapPromise;\n }\n\n this.bootstrapPromise = (async () => {\n try {\n const response = await fetch(`${this.baseUrl}/auth/anonymous`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(this.apiKey && { \"X-Api-Key\": this.apiKey }),\n },\n });\n\n if (!response.ok) {\n return null;\n }\n\n const data = await response.json();\n const tokens = data.content;\n\n if (tokens?.access_token && tokens?.refresh_token) {\n await this.storeManagedTokens(\n tokens.access_token,\n tokens.refresh_token\n );\n this.onTokensUpdated?.(tokens.access_token, tokens.refresh_token);\n console.info(\n \"Automatically created anonymous session for first API request\"\n );\n return tokens.access_token as string;\n }\n\n return null;\n } catch (error) {\n console.warn(\"Failed to automatically create anonymous tokens:\", error);\n return null;\n } finally {\n this.bootstrapPromise = null;\n }\n })();\n\n return this.bootstrapPromise;\n }\n\n private async refreshTokens(): Promise<void> {\n if (!this.tokenStorage) {\n return;\n }\n const tokenStorage = this.tokenStorage;\n\n if (this.refreshPromise) {\n return this.refreshPromise;\n }\n\n this.refreshPromise = (async () => {\n try {\n const refreshToken = await tokenStorage.getRefreshToken();\n let newTokens: TokenPair;\n\n if (refreshToken && !isTokenExpired(refreshToken)) {\n if (this.refreshTokenFn) {\n newTokens = await this.refreshTokenFn(refreshToken);\n } else {\n const response = await fetch(`${this.baseUrl}/auth/refresh-token`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n\n if (!response.ok) {\n throw new Error(`Token refresh failed: ${response.status}`);\n }\n\n const data = await response.json();\n newTokens = data.content;\n }\n } else {\n const currentAccessToken = await tokenStorage.getAccessToken();\n\n if (!currentAccessToken) {\n throw new Error(\"No tokens available for refresh\");\n }\n\n const reason = refreshToken\n ? \"refresh token expired\"\n : \"no refresh token available\";\n\n const response = await fetch(`${this.baseUrl}/auth/anonymous`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(this.apiKey && { \"X-Api-Key\": this.apiKey }),\n Authorization: `Bearer ${currentAccessToken}`,\n },\n });\n\n if (!response.ok) {\n throw new Error(\n `Anonymous token fallback failed: ${response.status}`\n );\n }\n\n const data = await response.json();\n newTokens = data.content;\n\n console.info(\n `Token refreshed via anonymous fallback (${reason}) - user may need to re-authenticate for privileged operations`\n );\n }\n\n await this.storeManagedTokens(\n newTokens.access_token,\n newTokens.refresh_token\n );\n this.onTokensUpdated?.(\n newTokens.access_token,\n newTokens.refresh_token\n );\n } catch (error) {\n console.error(\"Token refresh failed:\", error);\n await this.clearTokens();\n throw error;\n } finally {\n this.refreshPromise = null;\n }\n })();\n\n return this.refreshPromise;\n }\n\n private async captureTokensFromResponse(\n method: string,\n pathname: string,\n response: Response\n ): Promise<void> {\n if (\n !this.tokenStorage ||\n !(\n isTokenReturningOperation(method, pathname) ||\n isAnonymousAuthOperation(method, pathname)\n )\n ) {\n return;\n }\n\n try {\n const data = await response.clone().json();\n const content = data.content;\n\n if (content?.access_token && content?.refresh_token) {\n await this.storeManagedTokens(content.access_token, content.refresh_token);\n this.onTokensUpdated?.(content.access_token, content.refresh_token);\n }\n } catch (error) {\n console.warn(\"Failed to extract tokens from response:\", error);\n }\n }\n\n private async storeManagedTokens(\n accessToken: string,\n refreshToken: string | null\n ): Promise<void> {\n if (!this.tokenStorage) {\n return;\n }\n\n await this.tokenStorage.setAccessToken(accessToken);\n\n if (refreshToken) {\n await this.tokenStorage.setRefreshToken(refreshToken);\n }\n }\n}\n","import {\n StorefrontAPIClientBase,\n type StorefrontClientBaseConfig,\n} from \"@/lib/shared/client\";\n\n/**\n * Storefront API client that always authenticates with `X-Api-Key`.\n *\n * This client is used by the public storefront surface where no session or\n * token lifecycle should be involved.\n */\nexport class PublicStorefrontAPIClient extends StorefrontAPIClientBase {\n constructor(config: StorefrontClientBaseConfig) {\n super(config);\n this.setupPublicAuth();\n }\n\n private setupPublicAuth(): void {\n this.client.use({\n onRequest: async ({ request }) => {\n if (this.apiKey) {\n request.headers.set(\"X-Api-Key\", this.apiKey);\n }\n\n return request;\n },\n });\n }\n}\n","import { SessionStorefrontAPIClient } from \"./lib/session/client\";\nimport { Environment } from \"./lib/shared/url-utils\";\nimport { PublicCatalogClient } from \"./lib/public/catalog\";\nimport { CatalogClient } from \"./lib/catalog\";\nimport { CartClient } from \"./lib/cart\";\nimport { AuthClient } from \"./lib/auth\";\nimport { OrderClient } from \"./lib/order\";\nimport { PaymentsClient } from \"./lib/payments\";\nimport { PublicHelpersClient } from \"./lib/public/helper\";\nimport { HelpersClient } from \"./lib/helper\";\nimport { CustomerClient } from \"./lib/customer\";\nimport { PublicStoreConfigClient } from \"./lib/public/store-config\";\nimport { StoreConfigClient } from \"./lib/store-config\";\nimport {\n type TokenStorage,\n MemoryTokenStorage,\n BrowserTokenStorage,\n CookieTokenStorage,\n} from \"./lib/storage/token-storage\";\nimport {\n isUserLoggedIn,\n isUserAnonymous,\n type UserInfo,\n} from \"./lib/session/jwt-utils\";\nimport {\n StorefrontSessionManager,\n type StorefrontSession,\n} from \"./lib/session/manager\";\nimport { ResponseUtils } from \"@commercengine/sdk-core\";\nimport { buildStorefrontURL } from \"./lib/shared/url-utils\";\nimport { PublicStorefrontAPIClient } from \"./lib/public/client\";\nimport type {\n PublicStorefrontSDKOptions,\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"./lib/shared/sdk-types\";\n\n/**\n * Public SDK class for the Storefront API.\n *\n * This surface is intentionally limited to API-key-backed, public read\n * operations so it can be used safely during build and prerender flows.\n */\nexport class PublicStorefrontSDK {\n /**\n * Client for catalog-related read-only endpoints\n */\n public readonly catalog: PublicCatalogClient;\n\n /**\n * Client for helper-related endpoints\n */\n public readonly helpers: PublicHelpersClient;\n\n /**\n * Client for store config-related endpoints\n */\n public readonly store: PublicStoreConfigClient;\n\n /**\n * Centrally stored default headers for consistency\n */\n private defaultHeaders?: SupportedDefaultHeaders;\n\n constructor(options: PublicStorefrontSDKOptions) {\n this.defaultHeaders = options.defaultHeaders;\n\n const config = {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n apiKey: options.apiKey,\n timeout: options.timeout,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n };\n\n this.catalog = new PublicCatalogClient(config);\n this.helpers = new PublicHelpersClient(config);\n this.store = new PublicStoreConfigClient(config);\n }\n\n /**\n * Set the API key for all public clients\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n this.catalog.setApiKey(apiKey);\n this.helpers.setApiKey(apiKey);\n this.store.setApiKey(apiKey);\n }\n\n /**\n * Clear the API key from all public clients\n */\n public clearApiKey(): void {\n this.catalog.clearApiKey();\n this.helpers.clearApiKey();\n this.store.clearApiKey();\n }\n\n /**\n * Set default headers for all public clients\n *\n * @param headers - Default headers to set (only supported headers allowed)\n */\n public setDefaultHeaders(headers: SupportedDefaultHeaders): void {\n this.defaultHeaders = headers;\n this.catalog.setDefaultHeaders(headers);\n this.helpers.setDefaultHeaders(headers);\n this.store.setDefaultHeaders(headers);\n }\n\n /**\n * Get current default headers\n *\n * @returns Current default headers from central storage (always consistent)\n */\n public getDefaultHeaders(): SupportedDefaultHeaders | undefined {\n return this.defaultHeaders;\n }\n}\n\n/**\n * Main session-aware SDK class for the Storefront API\n */\nexport class SessionStorefrontSDK {\n /**\n * Client for catalog-related endpoints (products, categories, etc.)\n */\n public readonly catalog: CatalogClient;\n\n /**\n * Client for cart-related endpoints\n */\n public readonly cart: CartClient;\n\n /**\n * Client for authentication-related endpoints\n */\n public readonly auth: AuthClient;\n\n /**\n * Client for customer-related endpoints\n */\n public readonly customer: CustomerClient;\n\n /**\n * Client for helper-related endpoints\n */\n public readonly helpers: HelpersClient;\n\n /**\n * Client for order-related endpoints\n */\n public readonly order: OrderClient;\n\n /**\n * Client for payment-related endpoints\n */\n public readonly payments: PaymentsClient;\n\n /**\n * Client for store config-related endpoints\n */\n public readonly store: StoreConfigClient;\n\n /**\n * Centrally stored default headers for consistency\n */\n private defaultHeaders?: SupportedDefaultHeaders;\n\n /**\n * Shared session helper and coordinator for all API clients in this SDK instance.\n */\n public readonly session: StorefrontSession;\n private readonly sessionManager: StorefrontSessionManager;\n\n /**\n * Create a new SessionStorefrontSDK instance\n *\n * @param options - Configuration options for the SDK\n */\n constructor(options: SessionStorefrontSDKOptions) {\n // Store default headers centrally for consistency\n this.defaultHeaders = options.defaultHeaders;\n\n const sessionManager = new StorefrontSessionManager({\n accessToken: options.accessToken,\n apiKey: options.apiKey,\n baseUrl: buildStorefrontURL({\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n }),\n onTokensCleared: options.onTokensCleared,\n onTokensUpdated: options.onTokensUpdated,\n refreshToken: options.refreshToken,\n refreshTokenFn: options.refreshTokenFn,\n tokenStorage: options.tokenStorage,\n });\n\n this.sessionManager = sessionManager;\n this.session = sessionManager;\n\n // Convert options to internal config format\n const config = {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n accessToken: options.accessToken,\n refreshToken: options.refreshToken,\n apiKey: options.apiKey,\n timeout: options.timeout,\n tokenStorage: options.tokenStorage,\n onTokensUpdated: options.onTokensUpdated,\n onTokensCleared: options.onTokensCleared,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n sessionManager,\n };\n\n this.catalog = new CatalogClient(config);\n this.cart = new CartClient(config);\n this.auth = new AuthClient(config);\n this.customer = new CustomerClient(config);\n this.helpers = new HelpersClient(config);\n this.order = new OrderClient(config);\n this.payments = new PaymentsClient(config);\n this.store = new StoreConfigClient(config);\n }\n\n /**\n * Set authentication tokens for all clients\n *\n * @param accessToken - The access token (required)\n * @param refreshToken - The refresh token (optional)\n *\n * Behavior:\n * - If tokenStorage is provided: Stores tokens for automatic management\n * - If tokenStorage is not provided: Only stores access token for manual management\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n await this.sessionManager.setTokens(accessToken, refreshToken);\n }\n\n /**\n * Clear all authentication tokens from all clients\n *\n * Behavior:\n * - If tokenStorage is provided: Clears both access and refresh tokens from storage\n * - If tokenStorage is not provided: Clears the manual access token\n */\n public async clearTokens(): Promise<void> {\n await this.sessionManager.clearTokens();\n }\n\n /**\n * Set the API key for all clients\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n this.sessionManager.setApiKey(apiKey);\n }\n\n /**\n * Clear the API key from all clients\n */\n public clearApiKey(): void {\n this.sessionManager.clearApiKey();\n }\n\n /**\n * Get the current access token if using token storage\n *\n * This is a passive lookup. It will not create or refresh a session.\n */\n public async getAccessToken(): Promise<string | null> {\n return this.session.peekAccessToken();\n }\n\n /**\n * Ensure an access token is available for the current session.\n *\n * This may create or refresh a managed session when automatic token\n * management is configured.\n *\n * @returns A usable access token\n */\n public async ensureAccessToken(): Promise<string> {\n return this.session.ensureAccessToken();\n }\n\n /**\n * Get user information from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns User information extracted from JWT token, or null if no token or invalid token\n */\n public async getUserInfo(): Promise<UserInfo | null> {\n return this.session.peekUserInfo();\n }\n\n /**\n * Get the current user ID from the access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns User ID (ulid) or null if no token or invalid token\n */\n public async getUserId(): Promise<string | null> {\n return this.session.peekUserId();\n }\n\n /**\n * Check if the current user is logged in (not anonymous)\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns True if user is logged in, false if anonymous or no token\n */\n public async isLoggedIn(): Promise<boolean> {\n const token = await this.getAccessToken();\n if (!token) return false;\n return isUserLoggedIn(token);\n }\n\n /**\n * Check if the current user is anonymous\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns True if user is anonymous or no token, false if logged in\n */\n public async isAnonymous(): Promise<boolean> {\n const token = await this.getAccessToken();\n if (!token) return true;\n return isUserAnonymous(token);\n }\n\n /**\n * Get the customer ID from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns Customer ID or null if no token, invalid token, or user has no customer ID\n */\n public async getCustomerId(): Promise<string | null> {\n return this.session.peekCustomerId();\n }\n\n /**\n * Get the customer group ID from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns Customer group ID or null if no token, invalid token, or user has no customer group\n */\n public async getCustomerGroupId(): Promise<string | null> {\n return this.session.peekCustomerGroupId();\n }\n\n /**\n * Set default headers for all clients\n *\n * @param headers - Default headers to set (only supported headers allowed)\n */\n public setDefaultHeaders(headers: SupportedDefaultHeaders): void {\n // Update central storage first\n this.defaultHeaders = headers;\n\n // Sync to all clients using their inherited setDefaultHeaders method\n this.catalog.setDefaultHeaders(headers);\n this.cart.setDefaultHeaders(headers);\n this.auth.setDefaultHeaders(headers);\n this.customer.setDefaultHeaders(headers);\n this.helpers.setDefaultHeaders(headers);\n this.order.setDefaultHeaders(headers);\n this.payments.setDefaultHeaders(headers);\n this.store.setDefaultHeaders(headers);\n }\n\n /**\n * Get current default headers\n *\n * @returns Current default headers from central storage (always consistent)\n */\n public getDefaultHeaders(): SupportedDefaultHeaders | undefined {\n // Return from central storage for guaranteed consistency\n return this.defaultHeaders;\n }\n}\n\nexport type SessionStorefrontConfig = Omit<\n SessionStorefrontSDKOptions,\n keyof PublicStorefrontSDKOptions\n>;\n\nexport interface CreateStorefrontOptions extends PublicStorefrontSDKOptions {\n /**\n * Optional default configuration for the cached session-aware SDK returned by\n * `storefront.session()`.\n */\n session?: SessionStorefrontConfig;\n}\n\nexport interface StorefrontFactory {\n /**\n * Get the cached public storefront SDK.\n *\n * This instance is safe for public reads and never participates in session\n * bootstrap, refresh, or token persistence.\n */\n public(): PublicStorefrontSDK;\n\n /**\n * Get the cached default session-aware SDK.\n *\n * Use this when your app should operate with a stable managed or manual\n * session configuration.\n */\n session(): SessionStorefrontSDK;\n\n /**\n * Create a one-off session-aware SDK with per-call overrides.\n *\n * This is useful for stateless/token-seeded requests that should not reuse\n * the cached session client from `storefront.session()`.\n *\n * @param overrides - Per-instance session configuration overrides\n */\n session(overrides: Partial<SessionStorefrontConfig>): SessionStorefrontSDK;\n}\n\nfunction buildPublicStorefrontOptions(\n options: PublicStorefrontSDKOptions\n): PublicStorefrontSDKOptions {\n return {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n apiKey: options.apiKey,\n timeout: options.timeout,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n };\n}\n\nfunction buildSessionStorefrontOptions(\n options: CreateStorefrontOptions,\n overrides?: Partial<SessionStorefrontConfig>\n): SessionStorefrontSDKOptions {\n return {\n ...buildPublicStorefrontOptions(options),\n ...options.session,\n ...overrides,\n };\n}\n\n/**\n * Create a configured storefront factory with explicit public and session\n * access patterns.\n *\n * @example\n * ```typescript\n * import {\n * BrowserTokenStorage,\n * createStorefront,\n * Environment,\n * } from \"@commercengine/storefront-sdk\";\n *\n * export const storefront = createStorefront({\n * storeId: \"your-store-id\",\n * apiKey: \"your-api-key\",\n * environment: Environment.Staging,\n * session: {\n * tokenStorage: new BrowserTokenStorage(\"myapp_\"),\n * },\n * });\n *\n * const { data: products } = await storefront.public().catalog.listProducts();\n * const { data: cart } = await storefront.session().cart.getCart();\n * ```\n *\n * @param options - Shared public config plus optional default session config\n * @returns A storefront factory with explicit `public()` and `session()` accessors\n */\nexport function createStorefront(\n options: CreateStorefrontOptions\n): StorefrontFactory {\n const publicOptions = buildPublicStorefrontOptions(options);\n let publicSDK: PublicStorefrontSDK | null = null;\n let sessionSDK: SessionStorefrontSDK | null = null;\n\n const session = (\n overrides?: Partial<SessionStorefrontConfig>\n ): SessionStorefrontSDK => {\n if (overrides && Object.keys(overrides).length > 0) {\n return new SessionStorefrontSDK(\n buildSessionStorefrontOptions(options, overrides)\n );\n }\n\n if (!sessionSDK) {\n sessionSDK = new SessionStorefrontSDK(\n buildSessionStorefrontOptions(options)\n );\n }\n\n return sessionSDK;\n };\n\n return {\n public: () => {\n if (!publicSDK) {\n publicSDK = new PublicStorefrontSDK(publicOptions);\n }\n\n return publicSDK;\n },\n session: session as StorefrontFactory[\"session\"],\n };\n}\n\n// Export individual clients for advanced usage\nexport {\n PublicStorefrontAPIClient,\n SessionStorefrontAPIClient,\n PublicCatalogClient,\n AuthClient,\n CartClient,\n CatalogClient,\n CustomerClient,\n PublicHelpersClient,\n HelpersClient,\n OrderClient,\n PaymentsClient,\n PublicStoreConfigClient,\n StoreConfigClient,\n ResponseUtils,\n};\n// Export environment enum\nexport { Environment } from \"./lib/shared/url-utils\";\n// Export token storage types\nexport type { TokenStorage };\nexport { MemoryTokenStorage, BrowserTokenStorage, CookieTokenStorage };\nexport type { StorefrontSession };\nexport type {\n PublicStorefrontSDKOptions,\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"./lib/shared/sdk-types\";\n\n// Export token storage options\nexport type { CookieTokenStorageOptions } from \"./lib/storage/token-storage\";\n\n// Export JWT types that are used in public API\nexport type { UserInfo, Channel } from \"./lib/session/jwt-utils\";\n\n// Export ALL types from sdk-core\nexport type * from \"@commercengine/sdk-core\";\n\n// Export API types for consumer usage\nexport type { components, operations, paths } from \"./types/storefront\";\n\nexport type * from \"./types/storefront-api-types\";\n"],"x_google_ignoreList":[0],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.iife.js","names":[],"sources":["../../../node_modules/.pnpm/openapi-fetch@0.17.0/node_modules/openapi-fetch/dist/index.mjs","../../sdk-core/dist/index.mjs","../src/lib/shared/url-utils.ts","../src/lib/shared/client.ts","../src/lib/session/client.ts","../src/lib/shared/catalog.ts","../src/lib/public/client.ts","../src/lib/public/catalog.ts","../src/lib/catalog.ts","../src/lib/cart.ts","../src/lib/auth.ts","../src/lib/order.ts","../src/lib/payments.ts","../src/lib/shared/helper.ts","../src/lib/public/helper.ts","../src/lib/helper.ts","../src/lib/customer.ts","../src/lib/shared/store-config.ts","../src/lib/public/store-config.ts","../src/lib/store-config.ts","../src/lib/storage/token-storage.ts","../src/lib/session/jwt-utils.ts","../src/types/auth-operation-metadata.ts","../src/lib/session/auth-utils.ts","../src/lib/session/manager.ts","../src/index.ts"],"sourcesContent":["const PATH_PARAM_RE = /\\{[^{}]+\\}/g;\nconst supportsRequestInitExt = () => {\n return typeof process === \"object\" && Number.parseInt(process?.versions?.node?.substring(0, 2)) >= 18 && process.versions.undici;\n};\nfunction randomID() {\n return Math.random().toString(36).slice(2, 11);\n}\nfunction createClient(clientOptions) {\n let {\n baseUrl = \"\",\n Request: CustomRequest = globalThis.Request,\n fetch: baseFetch = globalThis.fetch,\n querySerializer: globalQuerySerializer,\n bodySerializer: globalBodySerializer,\n pathSerializer: globalPathSerializer,\n headers: baseHeaders,\n requestInitExt = void 0,\n ...baseOptions\n } = { ...clientOptions };\n requestInitExt = supportsRequestInitExt() ? requestInitExt : void 0;\n baseUrl = removeTrailingSlash(baseUrl);\n const globalMiddlewares = [];\n async function coreFetch(schemaPath, fetchOptions) {\n const {\n baseUrl: localBaseUrl,\n fetch = baseFetch,\n Request = CustomRequest,\n headers,\n params = {},\n parseAs = \"json\",\n querySerializer: requestQuerySerializer,\n bodySerializer = globalBodySerializer ?? defaultBodySerializer,\n pathSerializer: requestPathSerializer,\n body,\n middleware: requestMiddlewares = [],\n ...init\n } = fetchOptions || {};\n let finalBaseUrl = baseUrl;\n if (localBaseUrl) {\n finalBaseUrl = removeTrailingSlash(localBaseUrl) ?? baseUrl;\n }\n let querySerializer = typeof globalQuerySerializer === \"function\" ? globalQuerySerializer : createQuerySerializer(globalQuerySerializer);\n if (requestQuerySerializer) {\n querySerializer = typeof requestQuerySerializer === \"function\" ? requestQuerySerializer : createQuerySerializer({\n ...typeof globalQuerySerializer === \"object\" ? globalQuerySerializer : {},\n ...requestQuerySerializer\n });\n }\n const pathSerializer = requestPathSerializer || globalPathSerializer || defaultPathSerializer;\n const serializedBody = body === void 0 ? void 0 : bodySerializer(\n body,\n // Note: we declare mergeHeaders() both here and below because it’s a bit of a chicken-or-egg situation:\n // bodySerializer() needs all headers so we aren’t dropping ones set by the user, however,\n // the result of this ALSO sets the lowest-priority content-type header. So we re-merge below,\n // setting the content-type at the very beginning to be overwritten.\n // Lastly, based on the way headers work, it’s not a simple “present-or-not” check becauase null intentionally un-sets headers.\n mergeHeaders(baseHeaders, headers, params.header)\n );\n const finalHeaders = mergeHeaders(\n // with no body, we should not to set Content-Type\n serializedBody === void 0 || // if serialized body is FormData; browser will correctly set Content-Type & boundary expression\n serializedBody instanceof FormData ? {} : {\n \"Content-Type\": \"application/json\"\n },\n baseHeaders,\n headers,\n params.header\n );\n const finalMiddlewares = [...globalMiddlewares, ...requestMiddlewares];\n const requestInit = {\n redirect: \"follow\",\n ...baseOptions,\n ...init,\n body: serializedBody,\n headers: finalHeaders\n };\n let id;\n let options;\n let request = new Request(\n createFinalURL(schemaPath, { baseUrl: finalBaseUrl, params, querySerializer, pathSerializer }),\n requestInit\n );\n let response;\n for (const key in init) {\n if (!(key in request)) {\n request[key] = init[key];\n }\n }\n if (finalMiddlewares.length) {\n id = randomID();\n options = Object.freeze({\n baseUrl: finalBaseUrl,\n fetch,\n parseAs,\n querySerializer,\n bodySerializer,\n pathSerializer\n });\n for (const m of finalMiddlewares) {\n if (m && typeof m === \"object\" && typeof m.onRequest === \"function\") {\n const result = await m.onRequest({\n request,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (result instanceof Request) {\n request = result;\n } else if (result instanceof Response) {\n response = result;\n break;\n } else {\n throw new Error(\"onRequest: must return new Request() or Response() when modifying the request\");\n }\n }\n }\n }\n }\n if (!response) {\n try {\n response = await fetch(request, requestInitExt);\n } catch (error2) {\n let errorAfterMiddleware = error2;\n if (finalMiddlewares.length) {\n for (let i = finalMiddlewares.length - 1; i >= 0; i--) {\n const m = finalMiddlewares[i];\n if (m && typeof m === \"object\" && typeof m.onError === \"function\") {\n const result = await m.onError({\n request,\n error: errorAfterMiddleware,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (result instanceof Response) {\n errorAfterMiddleware = void 0;\n response = result;\n break;\n }\n if (result instanceof Error) {\n errorAfterMiddleware = result;\n continue;\n }\n throw new Error(\"onError: must return new Response() or instance of Error\");\n }\n }\n }\n }\n if (errorAfterMiddleware) {\n throw errorAfterMiddleware;\n }\n }\n if (finalMiddlewares.length) {\n for (let i = finalMiddlewares.length - 1; i >= 0; i--) {\n const m = finalMiddlewares[i];\n if (m && typeof m === \"object\" && typeof m.onResponse === \"function\") {\n const result = await m.onResponse({\n request,\n response,\n schemaPath,\n params,\n options,\n id\n });\n if (result) {\n if (!(result instanceof Response)) {\n throw new Error(\"onResponse: must return new Response() when modifying the response\");\n }\n response = result;\n }\n }\n }\n }\n }\n const contentLength = response.headers.get(\"Content-Length\");\n if (response.status === 204 || request.method === \"HEAD\" || contentLength === \"0\" && !response.headers.get(\"Transfer-Encoding\")?.includes(\"chunked\")) {\n return response.ok ? { data: void 0, response } : { error: void 0, response };\n }\n if (response.ok) {\n const getResponseData = async () => {\n if (parseAs === \"stream\") {\n return response.body;\n }\n if (parseAs === \"json\" && !contentLength) {\n const raw = await response.text();\n return raw ? JSON.parse(raw) : void 0;\n }\n return await response[parseAs]();\n };\n return { data: await getResponseData(), response };\n }\n let error = await response.text();\n try {\n error = JSON.parse(error);\n } catch {\n }\n return { error, response };\n }\n return {\n request(method, url, init) {\n return coreFetch(url, { ...init, method: method.toUpperCase() });\n },\n /** Call a GET endpoint */\n GET(url, init) {\n return coreFetch(url, { ...init, method: \"GET\" });\n },\n /** Call a PUT endpoint */\n PUT(url, init) {\n return coreFetch(url, { ...init, method: \"PUT\" });\n },\n /** Call a POST endpoint */\n POST(url, init) {\n return coreFetch(url, { ...init, method: \"POST\" });\n },\n /** Call a DELETE endpoint */\n DELETE(url, init) {\n return coreFetch(url, { ...init, method: \"DELETE\" });\n },\n /** Call a OPTIONS endpoint */\n OPTIONS(url, init) {\n return coreFetch(url, { ...init, method: \"OPTIONS\" });\n },\n /** Call a HEAD endpoint */\n HEAD(url, init) {\n return coreFetch(url, { ...init, method: \"HEAD\" });\n },\n /** Call a PATCH endpoint */\n PATCH(url, init) {\n return coreFetch(url, { ...init, method: \"PATCH\" });\n },\n /** Call a TRACE endpoint */\n TRACE(url, init) {\n return coreFetch(url, { ...init, method: \"TRACE\" });\n },\n /** Register middleware */\n use(...middleware) {\n for (const m of middleware) {\n if (!m) {\n continue;\n }\n if (typeof m !== \"object\" || !(\"onRequest\" in m || \"onResponse\" in m || \"onError\" in m)) {\n throw new Error(\"Middleware must be an object with one of `onRequest()`, `onResponse() or `onError()`\");\n }\n globalMiddlewares.push(m);\n }\n },\n /** Unregister middleware */\n eject(...middleware) {\n for (const m of middleware) {\n const i = globalMiddlewares.indexOf(m);\n if (i !== -1) {\n globalMiddlewares.splice(i, 1);\n }\n }\n }\n };\n}\nclass PathCallForwarder {\n constructor(client, url) {\n this.client = client;\n this.url = url;\n }\n GET = (init) => {\n return this.client.GET(this.url, init);\n };\n PUT = (init) => {\n return this.client.PUT(this.url, init);\n };\n POST = (init) => {\n return this.client.POST(this.url, init);\n };\n DELETE = (init) => {\n return this.client.DELETE(this.url, init);\n };\n OPTIONS = (init) => {\n return this.client.OPTIONS(this.url, init);\n };\n HEAD = (init) => {\n return this.client.HEAD(this.url, init);\n };\n PATCH = (init) => {\n return this.client.PATCH(this.url, init);\n };\n TRACE = (init) => {\n return this.client.TRACE(this.url, init);\n };\n}\nclass PathClientProxyHandler {\n constructor() {\n this.client = null;\n }\n // Assume the property is an URL.\n get(coreClient, url) {\n const forwarder = new PathCallForwarder(coreClient, url);\n this.client[url] = forwarder;\n return forwarder;\n }\n}\nfunction wrapAsPathBasedClient(coreClient) {\n const handler = new PathClientProxyHandler();\n const proxy = new Proxy(coreClient, handler);\n function Client() {\n }\n Client.prototype = proxy;\n const client = new Client();\n handler.client = client;\n return client;\n}\nfunction createPathBasedClient(clientOptions) {\n return wrapAsPathBasedClient(createClient(clientOptions));\n}\nfunction serializePrimitiveParam(name, value, options) {\n if (value === void 0 || value === null) {\n return \"\";\n }\n if (typeof value === \"object\") {\n throw new Error(\n \"Deeply-nested arrays/objects aren\\u2019t supported. Provide your own `querySerializer()` to handle these.\"\n );\n }\n return `${name}=${options?.allowReserved === true ? value : encodeURIComponent(value)}`;\n}\nfunction serializeObjectParam(name, value, options) {\n if (!value || typeof value !== \"object\") {\n return \"\";\n }\n const values = [];\n const joiner = {\n simple: \",\",\n label: \".\",\n matrix: \";\"\n }[options.style] || \"&\";\n if (options.style !== \"deepObject\" && options.explode === false) {\n for (const k in value) {\n values.push(k, options.allowReserved === true ? value[k] : encodeURIComponent(value[k]));\n }\n const final2 = values.join(\",\");\n switch (options.style) {\n case \"form\": {\n return `${name}=${final2}`;\n }\n case \"label\": {\n return `.${final2}`;\n }\n case \"matrix\": {\n return `;${name}=${final2}`;\n }\n default: {\n return final2;\n }\n }\n }\n for (const k in value) {\n const finalName = options.style === \"deepObject\" ? `${name}[${k}]` : k;\n values.push(serializePrimitiveParam(finalName, value[k], options));\n }\n const final = values.join(joiner);\n return options.style === \"label\" || options.style === \"matrix\" ? `${joiner}${final}` : final;\n}\nfunction serializeArrayParam(name, value, options) {\n if (!Array.isArray(value)) {\n return \"\";\n }\n if (options.explode === false) {\n const joiner2 = { form: \",\", spaceDelimited: \"%20\", pipeDelimited: \"|\" }[options.style] || \",\";\n const final = (options.allowReserved === true ? value : value.map((v) => encodeURIComponent(v))).join(joiner2);\n switch (options.style) {\n case \"simple\": {\n return final;\n }\n case \"label\": {\n return `.${final}`;\n }\n case \"matrix\": {\n return `;${name}=${final}`;\n }\n // case \"spaceDelimited\":\n // case \"pipeDelimited\":\n default: {\n return `${name}=${final}`;\n }\n }\n }\n const joiner = { simple: \",\", label: \".\", matrix: \";\" }[options.style] || \"&\";\n const values = [];\n for (const v of value) {\n if (options.style === \"simple\" || options.style === \"label\") {\n values.push(options.allowReserved === true ? v : encodeURIComponent(v));\n } else {\n values.push(serializePrimitiveParam(name, v, options));\n }\n }\n return options.style === \"label\" || options.style === \"matrix\" ? `${joiner}${values.join(joiner)}` : values.join(joiner);\n}\nfunction createQuerySerializer(options) {\n return function querySerializer(queryParams) {\n const search = [];\n if (queryParams && typeof queryParams === \"object\") {\n for (const name in queryParams) {\n const value = queryParams[name];\n if (value === void 0 || value === null) {\n continue;\n }\n if (Array.isArray(value)) {\n if (value.length === 0) {\n continue;\n }\n search.push(\n serializeArrayParam(name, value, {\n style: \"form\",\n explode: true,\n ...options?.array,\n allowReserved: options?.allowReserved || false\n })\n );\n continue;\n }\n if (typeof value === \"object\") {\n search.push(\n serializeObjectParam(name, value, {\n style: \"deepObject\",\n explode: true,\n ...options?.object,\n allowReserved: options?.allowReserved || false\n })\n );\n continue;\n }\n search.push(serializePrimitiveParam(name, value, options));\n }\n }\n return search.join(\"&\");\n };\n}\nfunction defaultPathSerializer(pathname, pathParams) {\n let nextURL = pathname;\n for (const match of pathname.match(PATH_PARAM_RE) ?? []) {\n let name = match.substring(1, match.length - 1);\n let explode = false;\n let style = \"simple\";\n if (name.endsWith(\"*\")) {\n explode = true;\n name = name.substring(0, name.length - 1);\n }\n if (name.startsWith(\".\")) {\n style = \"label\";\n name = name.substring(1);\n } else if (name.startsWith(\";\")) {\n style = \"matrix\";\n name = name.substring(1);\n }\n if (!pathParams || pathParams[name] === void 0 || pathParams[name] === null) {\n continue;\n }\n const value = pathParams[name];\n if (Array.isArray(value)) {\n nextURL = nextURL.replace(match, serializeArrayParam(name, value, { style, explode }));\n continue;\n }\n if (typeof value === \"object\") {\n nextURL = nextURL.replace(match, serializeObjectParam(name, value, { style, explode }));\n continue;\n }\n if (style === \"matrix\") {\n nextURL = nextURL.replace(match, `;${serializePrimitiveParam(name, value)}`);\n continue;\n }\n nextURL = nextURL.replace(match, style === \"label\" ? `.${encodeURIComponent(value)}` : encodeURIComponent(value));\n }\n return nextURL;\n}\nfunction defaultBodySerializer(body, headers) {\n if (body instanceof FormData) {\n return body;\n }\n if (headers) {\n const contentType = headers.get instanceof Function ? headers.get(\"Content-Type\") ?? headers.get(\"content-type\") : headers[\"Content-Type\"] ?? headers[\"content-type\"];\n if (contentType === \"application/x-www-form-urlencoded\") {\n return new URLSearchParams(body).toString();\n }\n }\n return JSON.stringify(body);\n}\nfunction createFinalURL(pathname, options) {\n let finalURL = `${options.baseUrl}${pathname}`;\n if (options.params?.path) {\n finalURL = options.pathSerializer(finalURL, options.params.path);\n }\n let search = options.querySerializer(options.params.query ?? {});\n if (search.startsWith(\"?\")) {\n search = search.substring(1);\n }\n if (search) {\n finalURL += `?${search}`;\n }\n return finalURL;\n}\nfunction mergeHeaders(...allHeaders) {\n const finalHeaders = new Headers();\n for (const h of allHeaders) {\n if (!h || typeof h !== \"object\") {\n continue;\n }\n const iterator = h instanceof Headers ? h.entries() : Object.entries(h);\n for (const [k, v] of iterator) {\n if (v === null) {\n finalHeaders.delete(k);\n } else if (Array.isArray(v)) {\n for (const v2 of v) {\n finalHeaders.append(k, v2);\n }\n } else if (v !== void 0) {\n finalHeaders.set(k, v);\n }\n }\n }\n return finalHeaders;\n}\nfunction removeTrailingSlash(url) {\n if (url.endsWith(\"/\")) {\n return url.substring(0, url.length - 1);\n }\n return url;\n}\n\nexport { createFinalURL, createPathBasedClient, createQuerySerializer, createClient as default, defaultBodySerializer, defaultPathSerializer, mergeHeaders, randomID, removeTrailingSlash, serializeArrayParam, serializeObjectParam, serializePrimitiveParam, wrapAsPathBasedClient };\n//# sourceMappingURL=index.mjs.map\n","import createClient from \"openapi-fetch\";\n\n//#region src/middleware/debug.ts\n/**\n* Response utilities for debugging and working with Response objects\n*/\nvar ResponseUtils = class {\n\t/**\n\t* Get response headers as a plain object\n\t*/\n\tstatic getHeaders(response) {\n\t\treturn Object.fromEntries(response.headers.entries());\n\t}\n\t/**\n\t* Get specific header value\n\t*/\n\tstatic getHeader(response, name) {\n\t\treturn response.headers.get(name);\n\t}\n\t/**\n\t* Check if response was successful\n\t*/\n\tstatic isSuccess(response) {\n\t\treturn response.ok;\n\t}\n\t/**\n\t* Get response metadata\n\t*/\n\tstatic getMetadata(response) {\n\t\treturn {\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\tok: response.ok,\n\t\t\turl: response.url,\n\t\t\tredirected: response.redirected,\n\t\t\ttype: response.type,\n\t\t\theaders: Object.fromEntries(response.headers.entries())\n\t\t};\n\t}\n\t/**\n\t* Clone and read response as text (useful for debugging)\n\t* Note: This can only be called once per response\n\t*/\n\tstatic async getText(response) {\n\t\treturn await response.clone().text();\n\t}\n\t/**\n\t* Clone and read response as JSON (useful for debugging)\n\t* Note: This can only be called once per response\n\t*/\n\tstatic async getJSON(response) {\n\t\treturn await response.clone().json();\n\t}\n\t/**\n\t* Format response information for debugging\n\t*/\n\tstatic format(response) {\n\t\tconst metadata = this.getMetadata(response);\n\t\treturn `${metadata.status} ${metadata.statusText} - ${metadata.url}`;\n\t}\n\t/**\n\t* Format response for logging purposes (enhanced version)\n\t*/\n\tstatic formatResponse(response) {\n\t\treturn {\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\turl: response.url,\n\t\t\tok: response.ok\n\t\t};\n\t}\n};\n/**\n* Debug logging utilities\n*/\nvar DebugLogger = class {\n\tlogger;\n\tconstructor(logger) {\n\t\tthis.logger = logger || ((level, message, data) => {\n\t\t\tconsole.log(`[${level.toUpperCase()}]`, message);\n\t\t\tif (data) console.log(data);\n\t\t});\n\t}\n\t/**\n\t* Log debug information about API request\n\t*/\n\tlogRequest(request, requestBody) {\n\t\tthis.logger(\"info\", \"API Request Debug Info\", {\n\t\t\tmethod: request.method,\n\t\t\turl: request.url,\n\t\t\theaders: Object.fromEntries(request.headers.entries()),\n\t\t\tbody: requestBody,\n\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t});\n\t}\n\t/**\n\t* Log debug information about API response\n\t*/\n\tasync logResponse(response, responseBody) {\n\t\tthis.logger(\"info\", \"API Response Debug Info\", {\n\t\t\turl: response.url,\n\t\t\tstatus: response.status,\n\t\t\tstatusText: response.statusText,\n\t\t\tok: response.ok,\n\t\t\theaders: Object.fromEntries(response.headers.entries()),\n\t\t\tredirected: response.redirected,\n\t\t\ttype: response.type,\n\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t});\n\t\tif (responseBody) this.logger(\"info\", \"API Response Data\", {\n\t\t\tdata: responseBody,\n\t\t\tcontentType: response.headers.get(\"content-type\"),\n\t\t\tcontentLength: response.headers.get(\"content-length\")\n\t\t});\n\t}\n\t/**\n\t* Log error information\n\t*/\n\tlogError(message, error) {\n\t\tthis.logger(\"error\", message, error);\n\t}\n\t/**\n\t* Compatibility shim retained for older internal callers.\n\t* Response bodies are no longer cached by the debug logger.\n\t*/\n\tgetCachedResponseText(_url) {\n\t\treturn null;\n\t}\n\t/**\n\t* Compatibility shim retained for older internal callers.\n\t* Response bodies are no longer cached by the debug logger.\n\t*/\n\tclearCache() {}\n\tinfo(message, data) {\n\t\tthis.logger(\"info\", message, data);\n\t}\n\twarn(message, data) {\n\t\tthis.logger(\"warn\", message, data);\n\t}\n\terror(message, data) {\n\t\tthis.logger(\"error\", message, data);\n\t}\n};\n/**\n* Extract request body for logging\n*/\nasync function extractRequestBody(request) {\n\tif (request.method === \"GET\" || request.method === \"HEAD\") return null;\n\ttry {\n\t\tconst clonedRequest = request.clone();\n\t\tconst contentType = request.headers.get(\"content-type\")?.toLowerCase();\n\t\tif (contentType?.startsWith(\"application/json\")) return await clonedRequest.json();\n\t\telse if (contentType?.startsWith(\"multipart/form-data\")) return \"[FormData - cannot display]\";\n\t\telse if (contentType?.startsWith(\"text/\")) return await clonedRequest.text();\n\t\treturn \"[Request body - unknown format]\";\n\t} catch (error) {\n\t\treturn \"[Request body unavailable]\";\n\t}\n}\n/**\n* Create debug middleware for openapi-fetch (internal use)\n* Enhanced version that combines original functionality with duration tracking\n*/\nfunction createDebugMiddleware(logger) {\n\tconst debugLogger = new DebugLogger(logger);\n\treturn {\n\t\tasync onRequest({ request }) {\n\t\t\trequest.__debugStartTime = Date.now();\n\t\t\tconst requestBody = await extractRequestBody(request);\n\t\t\tdebugLogger.logRequest(request, requestBody);\n\t\t\treturn request;\n\t\t},\n\t\tasync onResponse({ request, response }) {\n\t\t\tconst startTime = request.__debugStartTime;\n\t\t\tconst duration = startTime ? Date.now() - startTime : 0;\n\t\t\tconst cloned = response.clone();\n\t\t\tlet responseBody = null;\n\t\t\ttry {\n\t\t\t\tconst contentType = response.headers.get(\"content-type\")?.toLowerCase();\n\t\t\t\tif (contentType?.startsWith(\"application/json\")) responseBody = await cloned.json();\n\t\t\t\telse if (contentType?.startsWith(\"text/\")) responseBody = await cloned.text();\n\t\t\t} catch (error) {}\n\t\t\tawait debugLogger.logResponse(response, responseBody);\n\t\t\tif (duration > 0) debugLogger.info(`Request completed in ${duration}ms`, {\n\t\t\t\turl: request.url,\n\t\t\t\tmethod: request.method\n\t\t\t});\n\t\t\treturn response;\n\t\t},\n\t\tasync onError({ error, request }) {\n\t\t\tdebugLogger.logError(\"API Request Failed\", {\n\t\t\t\terror: {\n\t\t\t\t\tname: error instanceof Error ? error.name : \"Unknown\",\n\t\t\t\t\tmessage: error instanceof Error ? error.message : String(error),\n\t\t\t\t\tstack: error instanceof Error ? error.stack : void 0\n\t\t\t\t},\n\t\t\t\trequest: {\n\t\t\t\t\tmethod: request.method,\n\t\t\t\t\turl: request.url,\n\t\t\t\t\theaders: Object.fromEntries(request.headers.entries())\n\t\t\t\t},\n\t\t\t\ttimestamp: (/* @__PURE__ */ new Date()).toISOString()\n\t\t\t});\n\t\t\tthrow error;\n\t\t}\n\t};\n}\n\n//#endregion\n//#region src/middleware/timeout.ts\n/**\n* Timeout middleware for Commerce Engine SDKs\n*/\n/**\n* Create timeout middleware for openapi-fetch\n* Adds configurable request timeout functionality\n* \n* @param timeoutMs - Timeout duration in milliseconds\n* @returns Middleware object with onRequest handler\n*/\nfunction createTimeoutMiddleware(timeoutMs) {\n\tconst timeouts = /* @__PURE__ */ new WeakMap();\n\tconst clearRequestTimeout = (signal) => {\n\t\tconst timeoutId = timeouts.get(signal);\n\t\tif (timeoutId) {\n\t\t\tclearTimeout(timeoutId);\n\t\t\ttimeouts.delete(signal);\n\t\t}\n\t};\n\treturn {\n\t\tonRequest: async ({ request }) => {\n\t\t\tconst controller = new AbortController();\n\t\t\tconst timeoutId = setTimeout(() => controller.abort(), timeoutMs);\n\t\t\tif (request.signal) request.signal.addEventListener(\"abort\", () => controller.abort(), { once: true });\n\t\t\tconst newRequest = new Request(request, { signal: controller.signal });\n\t\t\ttimeouts.set(newRequest.signal, timeoutId);\n\t\t\tcontroller.signal.addEventListener(\"abort\", () => clearRequestTimeout(newRequest.signal), { once: true });\n\t\t\treturn newRequest;\n\t\t},\n\t\tonResponse: async ({ request, response }) => {\n\t\t\tclearRequestTimeout(request.signal);\n\t\t\treturn response;\n\t\t},\n\t\tonError: async ({ request, error }) => {\n\t\t\tclearRequestTimeout(request.signal);\n\t\t\tthrow error;\n\t\t}\n\t};\n}\n\n//#endregion\n//#region src/middleware/headers.ts\n/**\n* Header transformation and merging utilities for Commerce Engine SDKs\n*/\n/**\n* Merge two header objects\n* Method-level headers take precedence over default headers\n*\n* @param defaultHeaders - Default headers from SDK configuration\n* @param methodHeaders - Headers passed to the specific method call\n* @returns Merged headers object\n*/\nfunction mergeHeaders(defaultHeaders, methodHeaders) {\n\tconst merged = {};\n\tif (defaultHeaders) Object.assign(merged, defaultHeaders);\n\tif (methodHeaders) Object.assign(merged, methodHeaders);\n\tObject.keys(merged).forEach((key) => {\n\t\tif (merged[key] === void 0) delete merged[key];\n\t});\n\treturn merged;\n}\n/**\n* Transform headers using a transformation mapping\n* Headers not in the transformation map are passed through unchanged\n*\n* @param headers - Headers object with original names\n* @param transformations - Mapping of original names to transformed names\n* @returns Headers object with transformed names\n*/\nfunction transformHeaders(headers, transformations) {\n\tconst transformed = {};\n\tfor (const [key, value] of Object.entries(headers)) if (value !== void 0) {\n\t\tconst headerName = transformations[key] || key;\n\t\ttransformed[headerName] = value;\n\t}\n\treturn transformed;\n}\n/**\n* Merge headers with transformation support\n* Transforms default headers, then merges with method headers\n*\n* @param defaultHeaders - Default headers from SDK configuration\n* @param methodHeaders - Headers passed to the specific method call\n* @param transformations - Mapping for header name transformations\n* @returns Merged headers object with transformations applied\n*/\nfunction mergeAndTransformHeaders(defaultHeaders, methodHeaders, transformations) {\n\tconst merged = {};\n\tif (defaultHeaders && transformations) {\n\t\tconst transformedDefaults = transformHeaders(defaultHeaders, transformations);\n\t\tObject.assign(merged, transformedDefaults);\n\t} else if (defaultHeaders) Object.assign(merged, defaultHeaders);\n\tif (methodHeaders) Object.assign(merged, methodHeaders);\n\tObject.keys(merged).forEach((key) => {\n\t\tif (merged[key] === void 0) delete merged[key];\n\t});\n\treturn merged;\n}\n\n//#endregion\n//#region src/utils/response.ts\n/**\n* Execute a request and handle the response consistently\n* This provides unified error handling and response processing across all SDKs\n*\n* @param apiCall - Function that executes the API request\n* @returns Promise with the API response in standardized format\n*/\nasync function executeRequest(apiCall) {\n\ttry {\n\t\tconst { data, error, response } = await apiCall();\n\t\tif (error) return {\n\t\t\tdata: null,\n\t\t\terror,\n\t\t\tresponse\n\t\t};\n\t\tif (data && data.content !== void 0) return {\n\t\t\tdata: data.content,\n\t\t\terror: null,\n\t\t\tresponse\n\t\t};\n\t\treturn {\n\t\t\tdata,\n\t\t\terror: null,\n\t\t\tresponse\n\t\t};\n\t} catch (err) {\n\t\tconst mockResponse = new Response(null, {\n\t\t\tstatus: 503,\n\t\t\tstatusText: \"Service Unavailable\"\n\t\t});\n\t\treturn {\n\t\t\tdata: null,\n\t\t\terror: {\n\t\t\t\tsuccess: false,\n\t\t\t\tcode: \"NETWORK_ERROR\",\n\t\t\t\tmessage: \"Network error occurred\",\n\t\t\t\terror: err\n\t\t\t},\n\t\t\tresponse: mockResponse\n\t\t};\n\t}\n}\n\n//#endregion\n//#region src/base-client.ts\n/**\n* Base API client for Commerce Engine SDKs\n* Provides common functionality without token management\n*/\n/**\n* Generic base API client that all Commerce Engine SDKs can extend\n* Handles common functionality like middleware setup, request execution, and header management\n* Does NOT include token management - that's SDK-specific\n* \n* @template TPaths - OpenAPI paths type\n* @template THeaders - Supported default headers type\n*/\nvar BaseAPIClient = class {\n\tclient;\n\tconfig;\n\tbaseUrl;\n\theaderTransformations;\n\t/**\n\t* Create a new BaseAPIClient\n\t*\n\t* @param config - Configuration for the API client\n\t* @param baseUrl - The base URL for the API (must be provided by subclass)\n\t* @param headerTransformations - Header name transformations for this SDK\n\t*/\n\tconstructor(config, baseUrl, headerTransformations = {}) {\n\t\tthis.config = { ...config };\n\t\tthis.headerTransformations = headerTransformations;\n\t\tthis.baseUrl = baseUrl;\n\t\tthis.client = createClient({ baseUrl: this.baseUrl });\n\t\tthis.setupMiddleware();\n\t}\n\t/**\n\t* Set up all middleware for the client\n\t*/\n\tsetupMiddleware() {\n\t\tif (this.config.timeout) {\n\t\t\tconst timeoutMiddleware = createTimeoutMiddleware(this.config.timeout);\n\t\t\tthis.client.use(timeoutMiddleware);\n\t\t}\n\t\tif (this.config.debug) {\n\t\t\tconst debugMiddleware = createDebugMiddleware(this.config.logger);\n\t\t\tthis.client.use(debugMiddleware);\n\t\t}\n\t}\n\t/**\n\t* Get the base URL of the API\n\t*\n\t* @returns The base URL of the API\n\t*/\n\tgetBaseUrl() {\n\t\treturn this.baseUrl;\n\t}\n\t/**\n\t* Execute a request and handle the response consistently\n\t* This provides unified error handling and response processing\n\t*\n\t* @param apiCall - Function that executes the API request\n\t* @returns Promise with the API response in standardized format\n\t*/\n\tasync executeRequest(apiCall) {\n\t\treturn executeRequest(apiCall);\n\t}\n\t/**\n\t* Merge default headers with method-level headers\n\t* Method-level headers take precedence over default headers\n\t* Automatically applies SDK-specific header transformations\n\t*\n\t* @param methodHeaders - Headers passed to the specific method call\n\t* @returns Merged headers object with proper HTTP header names\n\t*/\n\tmergeHeaders(methodHeaders) {\n\t\treturn mergeAndTransformHeaders(this.config.defaultHeaders, methodHeaders, this.headerTransformations);\n\t}\n\t/**\n\t* Set default headers for the client\n\t*\n\t* @param headers - Default headers to set\n\t*/\n\tsetDefaultHeaders(headers) {\n\t\tthis.config.defaultHeaders = headers;\n\t}\n\t/**\n\t* Get current default headers\n\t*\n\t* @returns Current default headers\n\t*/\n\tgetDefaultHeaders() {\n\t\treturn this.config.defaultHeaders;\n\t}\n};\n\n//#endregion\n//#region src/utils/url.ts\n/**\n* Generic URL utility functions for any SDK\n*/\n/**\n* Extract pathname from URL\n* Useful for middleware that needs to inspect request paths\n*/\nfunction getPathnameFromUrl(url) {\n\ttry {\n\t\treturn new URL(url).pathname;\n\t} catch {\n\t\treturn url.split(\"?\")[0] || url;\n\t}\n}\n\n//#endregion\nexport { BaseAPIClient, DebugLogger, ResponseUtils, createDebugMiddleware, createTimeoutMiddleware, executeRequest, extractRequestBody, getPathnameFromUrl, mergeAndTransformHeaders, mergeHeaders, transformHeaders };","/**\n * URL utility functions for the Storefront SDK\n */\n\n/**\n * Available API environments for Commerce Engine\n */\nexport enum Environment {\n /**\n * Staging environment\n */\n Staging = \"staging\",\n\n /**\n * Production environment\n */\n Production = \"production\",\n}\n\n/**\n * Commerce Engine specific SDK configuration\n */\nexport interface CommerceEngineConfig {\n /**\n * Store ID for the API requests\n */\n storeId: string;\n\n /**\n * Environment to use (staging or production)\n */\n environment?: Environment;\n\n /**\n * Custom base URL (overrides environment if provided)\n */\n baseUrl?: string;\n}\n\n/**\n * Build base URL for Storefront API\n */\nexport function buildStorefrontURL(config: CommerceEngineConfig): string {\n // If explicit baseUrl is provided, use it\n if (config.baseUrl) {\n return config.baseUrl;\n }\n\n // Otherwise construct URL based on environment and storeId\n const env = config.environment || Environment.Production;\n\n switch (env) {\n case Environment.Staging:\n return `https://staging.api.commercengine.io/api/v1/${config.storeId}/storefront`;\n case Environment.Production:\n default:\n return `https://prod.api.commercengine.io/api/v1/${config.storeId}/storefront`;\n }\n}\n","import { BaseAPIClient, type BaseSDKOptions } from \"@commercengine/sdk-core\";\nimport type { paths } from \"@/types/storefront\";\nimport { buildStorefrontURL } from \"@/lib/shared/url-utils\";\nimport type {\n PublicStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"@/lib/shared/sdk-types\";\n\nexport type StorefrontClientBaseConfig =\n BaseSDKOptions<SupportedDefaultHeaders> & {\n storeId: string;\n environment?: PublicStorefrontSDKOptions[\"environment\"];\n baseUrl?: string;\n apiKey?: string;\n};\n\n/**\n * Shared base class for Storefront API clients.\n *\n * This centralizes Storefront-specific URL construction, default header\n * transformations, and shared API key state while leaving auth middleware\n * decisions to the public and session-specific subclasses.\n */\nexport class StorefrontAPIClientBase extends BaseAPIClient<\n paths,\n SupportedDefaultHeaders\n> {\n public apiKey?: string;\n\n constructor(config: StorefrontClientBaseConfig) {\n const baseUrl = buildStorefrontURL({\n storeId: config.storeId,\n environment: config.environment,\n baseUrl: config.baseUrl,\n });\n\n const headerTransformations = {\n customer_group_id: \"x-customer-group-id\",\n debug_mode: \"x-debug-mode\",\n } as Record<keyof SupportedDefaultHeaders, string>;\n\n super(\n {\n baseUrl,\n timeout: config.timeout,\n defaultHeaders: config.defaultHeaders,\n debug: config.debug,\n logger: config.logger,\n },\n baseUrl,\n headerTransformations\n );\n\n this.apiKey = config.apiKey;\n }\n\n public setApiKey(apiKey: string): void {\n this.apiKey = apiKey;\n }\n\n public clearApiKey(): void {\n this.apiKey = undefined;\n }\n\n public useMiddleware(\n middleware: Parameters<typeof this.client.use>[0]\n ): void {\n this.client.use(middleware);\n }\n}\n","import type { paths } from \"@/types/storefront\";\nimport { StorefrontSessionManager } from \"./manager\";\nimport type {\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"@/lib/shared/sdk-types\";\nimport {\n StorefrontAPIClientBase,\n type StorefrontClientBaseConfig,\n} from \"@/lib/shared/client\";\n\ntype SessionStorefrontClientConfig = StorefrontClientBaseConfig &\n SessionStorefrontSDKOptions & {\n sessionManager: StorefrontSessionManager;\n};\n\nexport function attachSessionAuth(\n client: StorefrontAPIClientBase,\n sessionManager: StorefrontSessionManager\n): void {\n client.useMiddleware(sessionManager.createAuthMiddleware());\n}\n\n/**\n * Storefront API client that extends the generic BaseAPIClient\n * Adds Commerce Engine specific authentication and token management\n */\nexport class SessionStorefrontAPIClient extends StorefrontAPIClientBase {\n protected config: SessionStorefrontClientConfig;\n\n /**\n * Create a new SessionStorefrontAPIClient\n *\n * @param config - Configuration for the API client\n */\n constructor(config: SessionStorefrontClientConfig) {\n super(config);\n\n // Store full config for Storefront-specific features\n this.config = { ...config };\n\n // Set up Storefront-specific auth middleware\n this.setupStorefrontAuth();\n }\n\n /**\n * Set up Storefront-specific authentication middleware\n */\n private setupStorefrontAuth(): void {\n attachSessionAuth(this, this.config.sessionManager);\n }\n\n /**\n * Get the authorization header value\n * without creating a new session.\n *\n * @returns The Authorization header value or empty string if no token is set\n */\n public async getAuthorizationHeader(): Promise<string> {\n return this.config.sessionManager.getAuthorizationHeader();\n }\n\n /**\n * Set authentication tokens\n *\n * @param accessToken - The access token (required)\n * @param refreshToken - The refresh token (optional)\n *\n * Behavior:\n * - If tokenStorage is provided: Stores tokens for automatic management\n * - If tokenStorage is not provided: Only stores access token for manual management\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n await this.config.sessionManager.setTokens(accessToken, refreshToken);\n }\n\n /**\n * Clear all authentication tokens\n *\n * Behavior:\n * - If tokenStorage is provided: Clears both access and refresh tokens from storage\n * - If tokenStorage is not provided: Clears the manual access token\n */\n public async clearTokens(): Promise<void> {\n await this.config.sessionManager.clearTokens();\n }\n\n /**\n * Set the X-Api-Key header\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n super.setApiKey(apiKey);\n this.config.apiKey = apiKey;\n this.config.sessionManager.setApiKey(apiKey);\n }\n\n /**\n * Clear the X-Api-Key header\n */\n public clearApiKey(): void {\n super.clearApiKey();\n this.config.apiKey = undefined;\n this.config.sessionManager.clearApiKey();\n }\n\n /**\n * Resolve the current user ID from explicit parameters or the active session.\n *\n * @param explicitUserId - Optional user ID supplied by the caller\n * @returns The resolved user ID\n * @throws When no user ID is available\n */\n protected async resolveCurrentUserId(explicitUserId?: string): Promise<string> {\n if (explicitUserId) return explicitUserId;\n return this.config.sessionManager.ensureUserId();\n }\n\n /**\n * Resolve path parameters that require `user_id`.\n *\n * @param pathParams - Path parameters with an optional `user_id`\n * @returns Path parameters with a guaranteed `user_id`\n */\n protected async resolveUserPathParams<T extends { user_id: string }>(\n pathParams: Omit<T, \"user_id\"> & { user_id?: string }\n ): Promise<T> {\n return {\n ...pathParams,\n user_id: await this.resolveCurrentUserId(pathParams.user_id),\n } as T;\n }\n\n /**\n * Resolve query parameters that require `user_id`.\n *\n * @param queryParams - Query parameters with an optional `user_id`\n * @returns Query parameters with a guaranteed `user_id`\n */\n protected async resolveUserQueryParams<T extends { user_id: string }>(\n queryParams: Omit<T, \"user_id\"> & { user_id?: string }\n ): Promise<T> {\n return {\n ...queryParams,\n user_id: await this.resolveCurrentUserId(queryParams.user_id),\n } as T;\n }\n\n /**\n * Resolve path parameters that require `customer_id`.\n *\n * @param pathParams - Path parameters with an optional `customer_id`\n * @returns Path parameters with a guaranteed `customer_id`\n * @throws When the user is anonymous or no session can be established\n */\n protected async resolveCustomerPathParams<T extends { customer_id: string }>(\n pathParams: Omit<T, \"customer_id\"> & { customer_id?: string }\n ): Promise<T> {\n return {\n ...pathParams,\n customer_id:\n pathParams.customer_id ??\n (await this.config.sessionManager.ensureCustomerId()),\n } as T;\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n GetProductDetailContent,\n GetProductDetailPathParams,\n GetProductDetailHeaderParams,\n GetProductDetailQuery,\n GetVariantDetailContent,\n GetVariantDetailPathParams,\n GetVariantDetailHeaderParams,\n GetVariantDetailQuery,\n ListProductsContent,\n ListProductsQuery,\n ListProductsHeaderParams,\n ListProductVariantsContent,\n ListProductVariantsQuery,\n ListProductVariantsPathParams,\n ListProductVariantsHeaderParams,\n ListCategoriesQuery,\n ListCategoriesContent,\n ListProductReviewsQuery,\n ListProductReviewsPathParams,\n ListProductReviewsContent,\n SearchProductsBody,\n SearchProductsContent,\n ListSkusQuery,\n ListSkusContent,\n ListSkusHeaderParams,\n ListCrosssellProductsContent,\n ListCrosssellProductsQuery,\n ListCrosssellProductsHeaderParams,\n ListUpsellProductsQuery,\n ListUpsellProductsContent,\n ListUpsellProductsHeaderParams,\n ListSimilarProductsQuery,\n ListSimilarProductsContent,\n ListSimilarProductsHeaderParams,\n SearchProductsHeaderParams,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class BaseCatalogClient extends StorefrontAPIClientBase {\n /**\n * List all products\n *\n * @param options - Optional query parameters\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with products and pagination info\n *\n * @example\n * ```typescript\n * // Basic product listing\n * const { data, error } = await sdk.catalog.listProducts();\n *\n * if (error) {\n * console.error(\"Failed to list products:\", error);\n * return;\n * }\n *\n * console.log(\"Products found:\", data.products?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With filtering and pagination\n * const { data: filteredData, error: filteredError } = await sdk.catalog.listProducts({\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" }),\n * category_slug: [\"electronics\", \"smartphones\"]\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listProducts(\n * {\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" }),\n * category_slug: [\"electronics\", \"smartphones\"]\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (filteredError) {\n * console.error(\"Failed to get filtered products:\", filteredError);\n * return;\n * }\n *\n * filteredData.products?.forEach(product => {\n * console.log(`Product: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * ```\n */\n public async listProducts(\n options?: ListProductsQuery,\n headers?: ListProductsHeaderParams\n ): Promise<ApiResult<ListProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all skus\n *\n * @param options - Optional query parameters\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with skus and pagination info\n *\n * @example\n * ```typescript\n * // Basic SKU listing\n * const { data, error } = await sdk.catalog.listSkus();\n *\n * if (error) {\n * console.error(\"Failed to list SKUs:\", error);\n * return;\n * }\n *\n * console.log(\"SKUs found:\", data.skus?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With pagination\n * const { data: skuData, error: skuError } = await sdk.catalog.listSkus({\n * page: 1,\n * limit: 50\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listSkus(\n * {\n * page: 1,\n * limit: 50\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (skuError) {\n * console.error(\"Failed to get SKUs:\", skuError);\n * return;\n * }\n *\n * skuData.skus?.forEach(sku => {\n * console.log(`SKU: ${sku.sku} - Price: ${sku.price}`);\n * });\n * ```\n */\n public async listSkus(\n options?: ListSkusQuery,\n headers?: ListSkusHeaderParams\n ): Promise<ApiResult<ListSkusContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/skus\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get details for a specific product\n *\n * @param pathParams - The path parameters. Accepts product ID or product slug.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with product details\n *\n * @example\n * ```typescript\n * // Get product by ID\n * const { data, error } = await sdk.catalog.getProductDetail(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get product details:\", error);\n * return;\n * }\n *\n * console.log(\"Product:\", data.product.name);\n * console.log(\"Price:\", data.product.pricing?.selling_price);\n * console.log(\"Description:\", data.product.short_description);\n *\n * // Get product by slug (also accepted in place of product_id)\n * const { data: slugData, error: slugError } = await sdk.catalog.getProductDetail({\n * product_id: \"detox-candy\"\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.getProductDetail(\n * { product_id: \"detox-candy\" },\n * undefined,\n * {\n * \"x-customer-group-id\": \"premium_customers\" // Override default SDK config\n * }\n * );\n *\n * if (slugError) {\n * console.error(\"Failed to get product by slug:\", slugError);\n * return;\n * }\n *\n * console.log(\"Product with custom pricing:\", slugData.product.pricing?.selling_price);\n * ```\n */\n public async getProductDetail(\n pathParams: GetProductDetailPathParams,\n options?: GetProductDetailQuery,\n headers?: GetProductDetailHeaderParams\n ): Promise<ApiResult<GetProductDetailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all variants for a specific product\n *\n * @param pathParams - The path parameters. Accepts product ID or product slug.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with product variants and pagination info\n *\n * @example\n * ```typescript\n * // By product ID\n * const { data, error } = await sdk.catalog.listProductVariants(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to list product variants:\", error);\n * return;\n * }\n *\n * console.log(\"Variants found:\", data.variants?.length || 0);\n *\n * data.variants?.forEach(variant => {\n * console.log(`Variant: ${variant.name} - SKU: ${variant.sku} - Price: ${variant.pricing?.selling_price}`);\n * });\n *\n * // By product slug (also accepted in place of product_id)\n * const { data: slugData, error: slugError } = await sdk.catalog.listProductVariants(\n * { product_id: \"detox-candy\" }\n * );\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.listProductVariants(\n * { product_id: \"prod_123\" },\n * undefined,\n * {\n * \"x-customer-group-id\": \"wholesale_customers\" // Override default SDK config\n * }\n * );\n * ```\n */\n public async listProductVariants(\n pathParams: ListProductVariantsPathParams,\n options?: ListProductVariantsQuery,\n headers?: ListProductVariantsHeaderParams\n ): Promise<ApiResult<ListProductVariantsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/variants\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get details for a specific product variant\n *\n * @param pathParams - The path parameters. Accepts product ID or slug for product_id, and variant ID or slug for variant_id.\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with variant details\n *\n * @example\n * ```typescript\n * // By product ID and variant ID\n * const { data, error } = await sdk.catalog.getVariantDetail(\n * {\n * product_id: \"prod_123\",\n * variant_id: \"var_456\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get variant details:\", error);\n * return;\n * }\n *\n * console.log(\"Variant:\", data.variant.name);\n * console.log(\"SKU:\", data.variant.sku);\n * console.log(\"Price:\", data.variant.pricing?.selling_price);\n * console.log(\"Stock available:\", data.variant.stock_available);\n *\n * // By product slug and variant slug (also accepted in place of IDs)\n * const { data: slugData, error: slugError } = await sdk.catalog.getVariantDetail(\n * {\n * product_id: \"detox-candy\",\n * variant_id: \"detox-candy-100g\"\n * }\n * );\n * ```\n */\n public async getVariantDetail(\n pathParams: GetVariantDetailPathParams,\n options?: GetVariantDetailQuery,\n headers?: GetVariantDetailHeaderParams\n ): Promise<ApiResult<GetVariantDetailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/variants/{variant_id}\", {\n params: {\n path: pathParams,\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List all product categories\n *\n * @param options - Optional query parameters\n * @returns Promise with categories and pagination info\n *\n * @example\n * ```typescript\n * // Basic category listing\n * const { data, error } = await sdk.catalog.listCategories();\n *\n * if (error) {\n * console.error(\"Failed to list categories:\", error);\n * return;\n * }\n *\n * console.log(\"Categories found:\", data.categories?.length || 0);\n *\n * data.categories?.forEach(category => {\n * console.log(`Category: ${category.name} - ${category.description}`);\n * });\n *\n * // With pagination\n * const { data: catData, error: catError } = await sdk.catalog.listCategories({\n * page: 1,\n * limit: 10\n * });\n * ```\n */\n public async listCategories(\n options?: ListCategoriesQuery\n ): Promise<ApiResult<ListCategoriesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/categories\", {\n params: {\n query: options,\n },\n })\n );\n }\n\n /**\n * List all reviews for a specific product\n *\n * @param pathParams - The path parameters (product ID)\n * @param queryParams - Optional query parameters\n * @returns Promise with product reviews and pagination info\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.catalog.listProductReviews(\n * { product_id: \"prod_123\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to list product reviews:\", error);\n * return;\n * }\n *\n * console.log(\"Reviews found:\", data.reviews?.length || 0);\n *\n * data.reviews?.forEach(review => {\n * console.log(`Review by ${review.name}: ${review.rating}/5`);\n * console.log(\"Review text:\", review.review_text);\n * });\n *\n * // With pagination\n * const { data: reviewData, error: reviewError } = await sdk.catalog.listProductReviews(\n * { product_id: \"prod_123\" },\n * {\n * page: 1,\n * limit: 5\n * }\n * );\n * ```\n */\n public async listProductReviews(\n pathParams: ListProductReviewsPathParams,\n queryParams?: ListProductReviewsQuery\n ): Promise<ApiResult<ListProductReviewsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/{product_id}/reviews\", {\n params: {\n path: pathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Search for products\n *\n * @param searchData - The search query, filters, sort, and pagination options\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with search results including SKUs, facet distribution, facet stats, and pagination\n *\n * @example\n * ```typescript\n * // Basic search\n * const { data, error } = await sdk.catalog.searchProducts({\n * query: \"smartphone\",\n * page: 1,\n * limit: 20\n * });\n *\n * if (error) {\n * console.error(\"Failed to search products:\", error);\n * return;\n * }\n *\n * console.log(\"Search results:\", data.skus?.length || 0, \"products found\");\n * console.log(\"Facet distribution:\", data.facet_distribution);\n * console.log(\"Facet stats:\", data.facet_stats);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.skus?.forEach(sku => {\n * console.log(`Found: ${sku.product_name} - ${sku.pricing?.selling_price}`);\n * });\n *\n * // With filter (string expression — Meilisearch syntax)\n * const { data: filtered, error: filteredError } = await sdk.catalog.searchProducts({\n * query: \"laptop\",\n * filter: \"pricing.selling_price 500 TO 2000 AND product_type = physical\",\n * sort: [\"pricing.selling_price:asc\"],\n * facets: [\"product_type\", \"categories.name\", \"tags\"],\n * page: 1,\n * limit: 10\n * });\n *\n * // With filter (array of conditions — combined with AND)\n * const { data: arrayFiltered, error: arrayError } = await sdk.catalog.searchProducts({\n * query: \"shoes\",\n * filter: [\"product_type = physical\", \"rating >= 4\", \"stock_available > 0\"],\n * sort: [\"rating:desc\"],\n * facets: [\"*\"],\n * page: 1,\n * limit: 25\n * });\n *\n * // With filter (nested arrays — inner arrays use OR, outer uses AND)\n * const { data: nestedFiltered, error: nestedError } = await sdk.catalog.searchProducts({\n * query: \"headphones\",\n * filter: [\n * \"pricing.selling_price 50 TO 300\",\n * [\"product_type = physical\", \"product_type = bundle\"]\n * ],\n * page: 1,\n * limit: 25\n * });\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.catalog.searchProducts(\n * {\n * query: \"laptop\",\n * filter: \"categories.name = computers\",\n * page: 1,\n * limit: 20\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n * ```\n */\n public async searchProducts(\n searchData: SearchProductsBody,\n headers?: SearchProductsHeaderParams\n ): Promise<ApiResult<SearchProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/catalog/products/search\", {\n params: {\n header: mergedHeaders,\n },\n body: searchData,\n })\n );\n }\n\n /**\n * List cross-sell products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with cross-sell products\n * @example\n * ```typescript\n * // Basic usage - get cross-sell products for cart items\n * const { data, error } = await sdk.catalog.listCrossSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\", \"prod_01H9ABC67890FGHIJ\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listCrossSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 10,\n * sort_by: '{\"price\":\"asc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listCrossSellProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 10\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get cross-sell products:\", error.message);\n * } else {\n * console.log(\"Cross-sell products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Product: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listCrossSellProducts(\n options?: ListCrosssellProductsQuery,\n headers?: ListCrosssellProductsHeaderParams\n ): Promise<ApiResult<ListCrosssellProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/cross-sell\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List up-sell products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with up-sell products\n * @example\n * ```typescript\n * // Basic usage - get up-sell products for cart items\n * const { data, error } = await sdk.catalog.listUpSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listUpSellProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 15,\n * sort_by: '{\"relevance\":\"desc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listUpSellProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 15\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get up-sell products:\", error.message);\n * } else {\n * console.log(\"Up-sell products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Up-sell: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listUpSellProducts(\n options?: ListUpsellProductsQuery,\n headers?: ListUpsellProductsHeaderParams\n ): Promise<ApiResult<ListUpsellProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/up-sell\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * List similar products\n *\n * @param options - Optional query parameters for filtering and pagination\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with similar products\n * @example\n * ```typescript\n * // Basic usage - get similar products for a specific product\n * const { data, error } = await sdk.catalog.listSimilarProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"]\n * });\n *\n * // Advanced usage with pagination and custom sorting\n * const { data, error } = await sdk.catalog.listSimilarProducts({\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 20,\n * sort_by: '{\"relevance\":\"desc\"}'\n * });\n *\n * // Override customer group ID for this specific request\n * const { data, error } = await sdk.catalog.listSimilarProducts(\n * {\n * product_id: [\"prod_01H9XYZ12345ABCDE\"],\n * page: 1,\n * limit: 20\n * },\n * {\n * \"x-customer-group-id\": \"01H9XYZ12345USERID\" // Override default SDK config\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to get similar products:\", error.message);\n * } else {\n * console.log(\"Similar products found:\", data.products.length);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.products.forEach(product => {\n * console.log(`Similar: ${product.name} - ${product.pricing?.selling_price}`);\n * });\n * }\n * ```\n */\n public async listSimilarProducts(\n options?: ListSimilarProductsQuery,\n headers?: ListSimilarProductsHeaderParams\n ): Promise<ApiResult<ListSimilarProductsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/catalog/products/similar\", {\n params: {\n query: options,\n header: mergedHeaders,\n },\n })\n );\n }\n}\n","import {\n StorefrontAPIClientBase,\n type StorefrontClientBaseConfig,\n} from \"@/lib/shared/client\";\n\n/**\n * Storefront API client that always authenticates with `X-Api-Key`.\n *\n * This client is used by the public storefront surface where no session or\n * token lifecycle should be involved.\n */\nexport class PublicStorefrontAPIClient extends StorefrontAPIClientBase {\n constructor(config: StorefrontClientBaseConfig) {\n super(config);\n attachPublicAuth(this);\n }\n}\n\nexport function attachPublicAuth(client: StorefrontAPIClientBase): void {\n client.useMiddleware({\n onRequest: async ({ request }) => {\n if (client.apiKey) {\n request.headers.set(\"X-Api-Key\", client.apiKey);\n }\n\n return request;\n },\n });\n}\n","import { BaseCatalogClient } from \"@/lib/shared/catalog\";\nimport {\n attachPublicAuth,\n PublicStorefrontAPIClient,\n} from \"@/lib/public/client\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class PublicCatalogClient extends BaseCatalogClient {\n constructor(config: ConstructorParameters<typeof PublicStorefrontAPIClient>[0]) {\n super(config);\n attachPublicAuth(this);\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CreateProductReviewFormData,\n CreateProductReviewPathParams,\n CreateProductReviewResponse,\n} from \"@/types/storefront-api-types\";\nimport { BaseCatalogClient } from \"@/lib/shared/catalog\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with catalog endpoints\n */\nexport class CatalogClient extends BaseCatalogClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n\n /**\n * Create a product review\n *\n * @param pathParams - The path parameters (product ID)\n * @param formData - The review data including rating, comment, and optional images\n * @returns Promise with review creation response\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.catalog.createProductReview(\n * { product_id: \"prod_123\" },\n * {\n * user_id: \"user_123\",\n * order_number: \"ORD-001\",\n * rating: 5,\n * review_text: \"Excellent product! Highly recommended.\",\n * images: [\n * new File([\"image data\"], \"review1.jpg\", { type: \"image/jpeg\" }),\n * new File([\"image data\"], \"review2.jpg\", { type: \"image/jpeg\" })\n * ]\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to create review:\", error);\n * return;\n * }\n *\n * console.log(\"Review created successfully:\", data.message);\n * ```\n */\n public async createProductReview(\n pathParams: CreateProductReviewPathParams,\n formData: CreateProductReviewFormData\n ): Promise<ApiResult<CreateProductReviewResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/catalog/products/{product_id}/reviews\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n if (value instanceof File || value instanceof Blob) {\n fd.append(key, value);\n } else {\n fd.append(key, String(value));\n }\n }\n }\n return fd;\n },\n })\n );\n }\n}\n","import { SessionStorefrontAPIClient } from \"./session/client\";\nimport type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n AddToWishlistBody,\n AddToWishlistContent,\n AddToWishlistPathParams,\n ApplyCouponBody,\n ApplyCouponContent,\n ApplyCouponPathParams,\n CreateCartContent,\n CreateCartAddressBody,\n CreateCartAddressContent,\n CreateCartAddressPathParams,\n CreateCartBody,\n DeleteCartPathParams,\n DeleteCartResponse,\n DeleteFromWishlistBody,\n DeleteFromWishlistContent,\n DeleteFromWishlistPathParams,\n DeleteUserCartPathParams,\n DeleteUserCartResponse,\n GetCartContent,\n GetCartPathParams,\n GetUserCartContent,\n GetUserCartPathParams,\n GetWishlistContent,\n GetWishlistPathParams,\n RedeemCreditBalanceBody,\n RedeemCreditBalanceContent,\n RedeemCreditBalancePathParams,\n RedeemLoyaltyPointsBody,\n RedeemLoyaltyPointsContent,\n RedeemLoyaltyPointsPathParams,\n RemoveCouponContent,\n RemoveCouponPathParams,\n RemoveCreditBalanceContent,\n RemoveCreditBalancePathParams,\n RemoveLoyaltyPointsContent,\n RemoveLoyaltyPointsPathParams,\n UpdateCartBody,\n UpdateCartContent,\n UpdateCartPathParams,\n UpdateFulfillmentPreferenceContent,\n UpdateFulfillmentPreferencePathParams,\n UpdateFulfillmentPreferenceBody,\n ListCouponsContent,\n ListPromotionsContent,\n ListCouponsHeaderParams,\n ListPromotionsHeaderParams,\n EvaluatePromotionsPathParams,\n EvaluatePromotionsContent,\n EvaluateCouponsContent,\n EvaluateCouponsPathParams,\n CheckFulfillmentContent,\n CheckFulfillmentBody,\n GetFulfillmentOptionsBody,\n GetFulfillmentOptionsContent,\n GetWishlistQuery,\n} from \"@/types/storefront-api-types\";\n\n/**\n * Client for interacting with cart endpoints\n */\nexport class CartClient extends SessionStorefrontAPIClient {\n // ===============================\n // CART ENDPOINTS\n // ===============================\n\n /**\n * Create a new cart\n *\n * @param payload - Object containing the items to add to the cart\n * @returns Promise with the created cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.createCart({\n * items: [\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 2\n * },\n * {\n * product_id: \"01H9ABC67890FGHIJ\",\n * variant_id: \"01H9XYZ67890KLMNO\",\n * quantity: 1\n * }\n * ],\n * metadata: {\n * \"source\": \"web\",\n * \"campaign\": \"summer_sale\"\n * }\n * });\n *\n * if (error) {\n * console.error(\"Failed to create cart:\", error.message);\n * } else {\n * console.log(\"Cart created:\", data.cart.id);\n * }\n * ```\n */\n public async createCart(\n payload: CreateCartBody\n ): Promise<ApiResult<CreateCartContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts\", {\n body: payload,\n })\n );\n }\n\n /**\n * Get cart details - either by ID or using the stored cart ID\n *\n * @param cartId - The ID of the cart\n * @returns Promise with cart details\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getCart({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get cart:\", error.message);\n * } else {\n * const cart = data.cart;\n * console.log(\"Cart total:\", cart.grand_total);\n * console.log(\"Items count:\", cart.cart_items.length);\n * }\n * ```\n */\n public async getCart(\n cartId: GetCartPathParams\n ): Promise<ApiResult<GetCartContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Delete a cart - either by ID or using the stored cart ID\n *\n * @param cartId - The ID of the cart\n * @returns Promise that resolves when the cart is deleted\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.deleteCart({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete cart:\", error.message);\n * } else {\n * console.log(\"Cart deleted:\", data.message);\n * }\n * ```\n */\n public async deleteCart(\n cartId: DeleteCartPathParams\n ): Promise<ApiResult<DeleteCartResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Update cart items (add, update quantity, remove)\n *\n * @param cartId - The cart id\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // Add item to cart\n * const { data, error } = await sdk.cart.addDeleteCartItem(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 3\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update cart:\", error.message);\n * } else {\n * console.log(\"Cart updated:\", data.cart.cart_items.length);\n * }\n *\n * // Remove item from cart (set quantity to 0)\n * const { data: removeData, error: removeError } = await sdk.cart.addDeleteCartItem(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * product_id: \"01H9XYZ12345ABCDE\",\n * variant_id: null,\n * quantity: 0\n * }\n * );\n * ```\n */\n public async addDeleteCartItem(\n cartId: UpdateCartPathParams,\n body: UpdateCartBody\n ): Promise<ApiResult<UpdateCartContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/items\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Get cart details by user ID\n *\n * @param pathParams - Optional path parameters. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with cart details\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getUserCart();\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.getUserCart({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to get user cart:\", error.message);\n * } else {\n * console.log(\"User cart ID:\", data.cart.id);\n * console.log(\"Cart value:\", data.cart.subtotal);\n * }\n * ```\n */\n public async getUserCart(): Promise<ApiResult<GetUserCartContent>>;\n public async getUserCart(\n pathParams: { user_id: string }\n ): Promise<ApiResult<GetUserCartContent>>;\n public async getUserCart(\n pathParams: { user_id?: string } = {}\n ): Promise<ApiResult<GetUserCartContent>> {\n const resolvedPathParams =\n await this.resolveUserPathParams<GetUserCartPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/carts/users/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Delete a cart by user ID\n *\n * @param pathParams - Optional path parameters. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise that resolves when the cart is deleted\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.deleteUserCart();\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.deleteUserCart({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete user cart:\", error.message);\n * } else {\n * console.log(\"User cart cleared:\", data.message);\n * }\n * ```\n */\n public async deleteUserCart(): Promise<ApiResult<DeleteUserCartResponse>>;\n public async deleteUserCart(\n pathParams: { user_id: string }\n ): Promise<ApiResult<DeleteUserCartResponse>>;\n public async deleteUserCart(\n pathParams: { user_id?: string } = {}\n ): Promise<ApiResult<DeleteUserCartResponse>> {\n const resolvedPathParams =\n await this.resolveUserPathParams<DeleteUserCartPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/users/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // CART ADDRESS ENDPOINTS\n // ===============================\n\n /**\n * Update cart addresses\n *\n * @param cartId - The ID of the cart\n * @param addressData - The address data\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // For registered users with saved addresses\n * const { data, error } = await sdk.cart.updateCartAddress(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * billing_address_id: \"01H9ADDR12345BILL\",\n * shipping_address_id: \"01H9ADDR12345SHIP\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update cart address:\", error.message);\n * } else {\n * console.log(\"Addresses updated:\", data.cart);\n * }\n *\n * // For guest checkout with new addresses\n * const { data: guestData, error: guestError } = await sdk.cart.updateCartAddress(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * billing_address: {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * address_line1: \"123 Main Street\",\n * address_line2: \"Apt 4B\",\n * city: \"Mumbai\",\n * state: \"Maharashtra\",\n * pincode: \"400001\",\n * country: \"India\",\n * landmark: \"Near Station\",\n * tax_identification_number: null,\n * business_name: null\n * },\n * shipping_address: {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * address_line1: \"456 Oak Avenue\",\n * address_line2: null,\n * city: \"Pune\",\n * state: \"Maharashtra\",\n * pincode: \"411001\",\n * country: \"India\",\n * landmark: \"Near Mall\",\n * tax_identification_number: null,\n * business_name: null\n * }\n * }\n * );\n * ```\n */\n public async updateCartAddress(\n cartId: CreateCartAddressPathParams,\n addressData: CreateCartAddressBody\n ): Promise<ApiResult<CreateCartAddressContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/address\", {\n params: {\n path: cartId,\n },\n body: addressData,\n })\n );\n }\n\n // ===============================\n // COUPON & PROMOTION ENDPOINTS\n // ===============================\n\n /**\n * Apply a coupon to the cart\n *\n * @param cartId - The ID of the cart\n * @param couponCode - The coupon code\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.applyCoupon(\n * { id: \"01H9CART12345ABCDE\" },\n * { coupon_code: \"FLAT100OFF\" }\n * );\n *\n * if (error) {\n * console.error(\"Failed to apply coupon:\", error.message);\n * } else {\n * console.log(\"Coupon applied, new total:\", data.cart.grand_total);\n * console.log(\"Discount amount:\", data.cart.coupon_discount_amount);\n * }\n * ```\n */\n public async applyCoupon(\n cartId: ApplyCouponPathParams,\n couponCode: ApplyCouponBody\n ): Promise<ApiResult<ApplyCouponContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/coupon\", {\n params: {\n path: cartId,\n },\n body: couponCode,\n })\n );\n }\n\n /**\n * Remove a coupon from the cart\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeCoupon({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove coupon:\", error.message);\n * } else {\n * console.log(\"Coupon removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeCoupon(\n cartId: RemoveCouponPathParams\n ): Promise<ApiResult<RemoveCouponContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/coupon\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n /**\n * Get all available coupons\n *\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with all available coupons\n * @example\n * ```typescript\n * // Get all available coupons\n * const { data, error } = await sdk.cart.getAvailableCoupons();\n *\n * if (error) {\n * console.error(\"Failed to get available coupons:\", error.message);\n * } else {\n * const coupons = data.coupons || [];\n * console.log(\"Available coupons:\", coupons.length);\n * coupons.forEach(coupon => {\n * console.log(\"Coupon:\", coupon.coupon_code, \"Name:\", coupon.name);\n * });\n * }\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.cart.getAvailableCoupons({\n * \"x-customer-group-id\": \"01H9GROUP12345ABC\" // Override default SDK config\n * });\n * ```\n */\n public async getAvailableCoupons(\n headers?: ListCouponsHeaderParams\n ): Promise<ApiResult<ListCouponsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/carts/available-coupons\", {\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Get all available promotions\n *\n * @param headers - Optional header parameters (customer_group_id, etc.)\n * @returns Promise with all available promotions\n * @example\n * ```typescript\n * // Get all available promotions\n * const { data, error } = await sdk.cart.getAvailablePromotions();\n *\n * if (error) {\n * console.error(\"Failed to get available promotions:\", error.message);\n * } else {\n * const promotions = data.promotions || [];\n * console.log(\"Available promotions:\", promotions.length);\n * promotions.forEach(promotion => {\n * console.log(\"Promotion:\", promotion.name, \"Type:\", promotion.promotion_type);\n * });\n * }\n *\n * // Override customer group ID for this specific request\n * const { data: overrideData, error: overrideError } = await sdk.cart.getAvailablePromotions({\n * \"x-customer-group-id\": \"01H9GROUP12345ABC\" // Override default SDK config\n * });\n * ```\n */\n public async getAvailablePromotions(\n headers?: ListPromotionsHeaderParams\n ): Promise<ApiResult<ListPromotionsContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.GET(\"/carts/available-promotions\", {\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Evaluate promotions\n *\n * @param cartId - The ID of the cart\n * @returns Promise with evaluated promotions\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.evaluatePromotions({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to evaluate promotions:\", error.message);\n * } else {\n * const applicable = data.applicable_promotions || [];\n * const inapplicable = data.inapplicable_promotions || [];\n *\n * console.log(\"Applicable promotions:\", applicable.length);\n * applicable.forEach(promo => {\n * console.log(`- ${promo.name}: ${promo.savings_message}`);\n * });\n *\n * console.log(\"Inapplicable promotions:\", inapplicable.length);\n * inapplicable.forEach(promo => {\n * console.log(`- ${promo.name}: ${promo.reason}`);\n * });\n * }\n * ```\n */\n public async evaluatePromotions(\n cartId: EvaluatePromotionsPathParams\n ): Promise<ApiResult<EvaluatePromotionsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}/evaluate-promotions\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n /**\n * Evaluate coupons\n *\n * @param cartId - The ID of the cart\n * @returns Promise with evaluated coupons\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.evaluateCoupons({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to evaluate coupons:\", error.message);\n * } else {\n * const applicable = data.applicable_coupons || [];\n * const inapplicable = data.inapplicable_coupons || [];\n *\n * console.log(\"Applicable coupons:\", applicable.length);\n * applicable.forEach(coupon => {\n * console.log(`- ${coupon.coupon_code?.join(\", \")}: Save $${coupon.estimated_discount}`);\n * });\n *\n * console.log(\"Inapplicable coupons:\", inapplicable.length);\n * inapplicable.forEach(coupon => {\n * console.log(`- ${coupon.coupon_code?.join(\", \")}: ${coupon.reason}`);\n * });\n * }\n * ```\n */\n public async evaluateCoupons(\n cartId: EvaluateCouponsPathParams\n ): Promise<ApiResult<EvaluateCouponsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/carts/{id}/evaluate-coupons\", {\n params: {\n path: cartId,\n },\n })\n );\n }\n\n\n // ===============================\n // LOYALTY POINTS ENDPOINTS\n // ===============================\n\n /**\n * Redeem loyalty points\n *\n * @param cartId - The ID of the cart\n * @param points - The number of points to redeem\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.redeemLoyaltyPoints(\n * { id: \"01H9CART12345ABCDE\" },\n * { loyalty_point_redeemed: 500 }\n * );\n *\n * if (error) {\n * console.error(\"Failed to redeem loyalty points:\", error.message);\n * } else {\n * console.log(\"Points redeemed, new total:\", data.cart.grand_total);\n * console.log(\"Points redeemed:\", data.cart.loyalty_points_redeemed);\n * }\n * ```\n */\n public async redeemLoyaltyPoints(\n cartId: RedeemLoyaltyPointsPathParams,\n points: RedeemLoyaltyPointsBody\n ): Promise<ApiResult<RedeemLoyaltyPointsContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/loyalty-points\", {\n params: {\n path: cartId,\n },\n body: points,\n })\n );\n }\n\n /**\n * Remove loyalty points\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeLoyaltyPoints({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove loyalty points:\", error.message);\n * } else {\n * console.log(\"Loyalty points removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeLoyaltyPoints(\n cartId: RemoveLoyaltyPointsPathParams\n ): Promise<ApiResult<RemoveLoyaltyPointsContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/loyalty-points\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // FULFILLMENT ENDPOINTS\n // ===============================\n\n /**\n * Update fulfillment preference\n *\n * @param cartId - The ID of the cart\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * // For delivery fulfillment with shipments\n * const { data, error } = await sdk.cart.updateFulfillmentPreference(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * fulfillment_type: \"delivery\",\n * shipments: [\n * {\n * id: \"01H9SHIP12345ABCDE\",\n * shipping_provider_id: \"01H9PROV12345FAST\",\n * courier_company_id: \"01H9COY12345FAST\" // Optional\n * }\n * ]\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update fulfillment preference:\", error.message);\n * } else {\n * console.log(\"Fulfillment preference updated:\", data.cart.fulfillment_preference?.fulfillment_type);\n * console.log(\"Shipping cost:\", data.cart.shipping_amount);\n * }\n *\n * // For collect-in-store fulfillment\n * const { data: collectData, error: collectError } = await sdk.cart.updateFulfillmentPreference(\n * { id: \"01H9CART12345ABCDE\" },\n * {\n * fulfillment_type: \"collect-in-store\",\n * pickup_location_id: \"01H9STORE12345ABC\"\n * }\n * );\n * ```\n */\n public async updateFulfillmentPreference(\n cartId: UpdateFulfillmentPreferencePathParams,\n body: UpdateFulfillmentPreferenceBody\n ): Promise<ApiResult<UpdateFulfillmentPreferenceContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/fulfillment-preference\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Check fulfillment serviceability\n *\n * Checks if fulfillment (delivery or collect-in-store) is available to the specified pincode\n * based on shipping zones and inventories.\n *\n * @param body - Fulfillment check body (cart-based or items-based)\n * @returns Promise with fulfillment serviceability result\n * @example\n * ```typescript\n * // Cart-based fulfillment check\n * const { data, error } = await sdk.cart.checkPincodeDeliverability({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * delivery_pincode: \"400001\",\n * fulfillment_type: \"delivery\" // optional: \"delivery\" | \"collect-in-store\"\n * });\n *\n * // Items-based fulfillment check\n * const { data, error } = await sdk.cart.checkPincodeDeliverability({\n * delivery_pincode: \"400001\",\n * items: [\n * { product_id: \"prod_123\", variant_id: \"var_456\" },\n * { product_id: \"prod_789\", variant_id: null }\n * ]\n * // fulfillment_type is optional\n * });\n *\n * if (error) {\n * console.error(\"Failed to check fulfillment serviceability:\", error.message);\n * } else {\n * console.log(\"Serviceable:\", data.is_serviceable);\n *\n * if (!data.is_serviceable && data.unserviceable_items) {\n * data.unserviceable_items.forEach(item => {\n * console.log(`Unserviceable: ${item.product_name}, max available: ${item.max_available_quantity}`);\n * });\n * }\n * }\n * ```\n */\n public async checkPincodeDeliverability(\n body: CheckFulfillmentBody\n ): Promise<ApiResult<CheckFulfillmentContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/fulfillment/serviceability\", {\n body: body,\n })\n );\n }\n\n /**\n * Get fulfillment options for an order\n *\n * @param body - Fulfillment options body containing cart_id and optional fulfillment_type\n * @returns Promise with fulfillment options including collect and delivery methods. The response contains:\n * - `summary`: Object with `collect_available`, `deliver_available`, `recommended_fulfillment_type`, and optional `recommended_store`\n * - `collect`: Optional array of `CollectInStore` objects for collect-in-store options\n * - `deliver`: Optional `DeliveryOption` object with `is_serviceable` and `shipments` array. Each shipment contains `id`, `items`, and `shipping_methods` array. Shipping methods may have optional `courier_companies` for auto shipping types.\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getFulfillmentOptions({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * fulfillment_type: \"delivery\" // optional: \"delivery\" | \"collect-in-store\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get fulfillment options:\", error.message);\n * } else {\n * // Check summary information\n * console.log(\"Collect available:\", data.summary.collect_available);\n * console.log(\"Deliver available:\", data.summary.deliver_available);\n * console.log(\"Recommended fulfillment type:\", data.summary.recommended_fulfillment_type);\n *\n * // Access collect options\n * if (data.collect && data.collect.length > 0) {\n * console.log(\"Available stores for collection:\");\n * data.collect.forEach(store => {\n * console.log(`${store.name} - ${store.distance_km}km away, ETA: ${store.collect_eta_minutes} minutes`);\n * });\n * }\n *\n * // Access delivery options (with shipments)\n * if (data.deliver && data.deliver.is_serviceable) {\n * console.log(\"Available shipments and shipping methods:\");\n * data.deliver.shipments.forEach(shipment => {\n * console.log(`Shipment ${shipment.id}:`);\n * console.log(` Items: ${shipment.items.length}`);\n * shipment.shipping_methods.forEach(method => {\n * console.log(` - ${method.name}: ${method.shipping_amount}, ${method.estimated_delivery_days} days`);\n * // Access courier companies for auto shipping methods\n * if (method.courier_companies) {\n * method.courier_companies.forEach(courier => {\n * console.log(` Courier: ${courier.name} - ${courier.shipping_amount}, ${courier.estimated_delivery_days} days`);\n * });\n * }\n * });\n * });\n * }\n * }\n * ```\n */\n public async getFulfillmentOptions(\n body: GetFulfillmentOptionsBody\n ): Promise<ApiResult<GetFulfillmentOptionsContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/fulfillment-options\", {\n body: body,\n })\n );\n }\n\n // ===============================\n // CREDIT BALANCE ENDPOINTS\n // ===============================\n\n /**\n * Use credit balance\n *\n * @param cartId - The ID of the cart\n * @param body - The body of the request\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.redeemCreditBalance(\n * { id: \"01H9CART12345ABCDE\" },\n * { credit_balance_used: 250.00 }\n * );\n *\n * if (error) {\n * console.error(\"Failed to redeem credit balance:\", error.message);\n * } else {\n * console.log(\"Credit applied, new total:\", data.cart.grand_total);\n * console.log(\"Credit used:\", data.cart.credit_balance_used);\n * }\n * ```\n */\n public async redeemCreditBalance(\n cartId: RedeemCreditBalancePathParams,\n body: RedeemCreditBalanceBody\n ): Promise<ApiResult<RedeemCreditBalanceContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/carts/{id}/credit-balance\", {\n params: {\n path: cartId,\n },\n body: body,\n })\n );\n }\n\n /**\n * Remove credit balance\n *\n * @param cartId - The ID of the cart\n * @returns Promise with updated cart\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeCreditBalance({\n * id: \"01H9CART12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to remove credit balance:\", error.message);\n * } else {\n * console.log(\"Credit balance removed, new total:\", data.cart.grand_total);\n * }\n * ```\n */\n public async removeCreditBalance(\n cartId: RemoveCreditBalancePathParams\n ): Promise<ApiResult<RemoveCreditBalanceContent>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/carts/{id}/credit-balance\", {\n params: {\n path: cartId,\n },\n body: undefined,\n })\n );\n }\n\n // ===============================\n // WISHLIST ENDPOINTS\n // ===============================\n\n /**\n * Get wishlist items\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param options - Optional query parameters for filtering by seller_id (only for multi-seller marketplace stores)\n * @returns Promise with wishlist items\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.getWishlist();\n *\n * // With query parameters\n * const { data: filtered } = await sdk.cart.getWishlist({\n * seller_id: \"seller_123\",\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.getWishlist({\n * user_id: \"01H9USER12345ABCDE\",\n * });\n *\n * if (error) {\n * console.error(\"Failed to get wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Wishlist items:\", products.length);\n * products.forEach(product => {\n * console.log(\"Product:\", product.product_name, \"Price:\", product.pricing?.selling_price);\n * });\n * }\n * ```\n */\n public async getWishlist(): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n queryParams: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n pathParams: { user_id: string },\n queryParams?: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>>;\n public async getWishlist(\n pathParamsOrQuery?:\n | { user_id?: string }\n | GetWishlistQuery,\n options?: GetWishlistQuery\n ): Promise<ApiResult<GetWishlistContent>> {\n const hasPathParams =\n options !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"user_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { user_id?: string })\n : {};\n const queryParams = hasPathParams\n ? options\n : (pathParamsOrQuery as GetWishlistQuery | undefined);\n const resolvedPathParams =\n await this.resolveUserPathParams<GetWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Add item to wishlist\n *\n * @param pathParamsOrBody - Optional path parameters or the wishlist body.\n * @param maybeBody - The wishlist body when path parameters are provided.\n * @returns Promise with updated wishlist\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.addToWishlist({\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.addToWishlist(\n * { user_id: \"01H9USER12345ABCDE\" },\n * {\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to add to wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Item added to wishlist, total items:\", products.length);\n * }\n * ```\n */\n public async addToWishlist(\n body: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>>;\n public async addToWishlist(\n pathParams: { user_id: string },\n body: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>>;\n public async addToWishlist(\n pathParamsOrBody:\n | { user_id?: string }\n | AddToWishlistBody,\n maybeBody?: AddToWishlistBody\n ): Promise<ApiResult<AddToWishlistContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { user_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as AddToWishlistBody);\n const resolvedPathParams =\n await this.resolveUserPathParams<AddToWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.POST(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Remove item from wishlist\n *\n * @param pathParamsOrBody - Optional path parameters or the wishlist body.\n * @param maybeBody - The wishlist body when path parameters are provided.\n * @returns Promise with updated wishlist\n * @example\n * ```typescript\n * const { data, error } = await sdk.cart.removeFromWishlist({\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * });\n *\n * // You can still pass an explicit user_id when needed\n * const { data: asUser } = await sdk.cart.removeFromWishlist(\n * { user_id: \"01H9USER12345ABCDE\" },\n * {\n * product_id: \"01F3Z7KG06J4ACWH1C4926KJEC\",\n * variant_id: null,\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to remove from wishlist:\", error.message);\n * } else {\n * const products = data.products;\n * console.log(\"Item removed from wishlist, remaining items:\", products.length);\n * }\n * ```\n */\n public async removeFromWishlist(\n body: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>>;\n public async removeFromWishlist(\n pathParams: { user_id: string },\n body: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>>;\n public async removeFromWishlist(\n pathParamsOrBody:\n | { user_id?: string }\n | DeleteFromWishlistBody,\n maybeBody?: DeleteFromWishlistBody\n ): Promise<ApiResult<DeleteFromWishlistContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { user_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as DeleteFromWishlistBody);\n const resolvedPathParams =\n await this.resolveUserPathParams<DeleteFromWishlistPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/wishlist/{user_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n\n}\n","import { SessionStorefrontAPIClient } from \"./session/client\";\nimport type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n AddProfileImageContent,\n AddProfileImageFormData,\n AddProfileImagePathParams,\n ChangePasswordBody,\n ChangePasswordContent,\n CheckVerificationStatusBody,\n CheckVerificationStatusContent,\n DeactivateUserPathParams,\n DeactivateUserResponse,\n DeleteUserPathParams,\n DeleteUserResponse,\n ForgotPasswordBody,\n ForgotPasswordContent,\n ForgotPasswordHeaderParams,\n GenerateOtpHeaderParams,\n GenerateOtpBody,\n GenerateOtpContent,\n GetAnonymousTokenContent,\n GetProfileImageContent,\n GetProfileImagePathParams,\n GetUserDetailContent,\n GetUserDetailPathParams,\n LoginWithEmailHeaderParams,\n LoginWithEmailBody,\n LoginWithEmailContent,\n LoginWithPasswordBody,\n LoginWithPasswordContent,\n LoginWithPhoneHeaderParams,\n LoginWithPhoneBody,\n LoginWithPhoneContent,\n LoginWithWhatsappHeaderParams,\n LoginWithWhatsappBody,\n LoginWithWhatsappContent,\n LogoutContent,\n RefreshTokenBody,\n RefreshTokenContent,\n RegisterWithEmailBody,\n RegisterWithEmailContent,\n RegisterWithEmailHeaderParams,\n RegisterWithPasswordBody,\n RegisterWithPasswordContent,\n RegisterWithPasswordHeaderParams,\n RegisterWithPhoneBody,\n RegisterWithPhoneContent,\n RegisterWithPhoneHeaderParams,\n RegisterWithWhatsappBody,\n RegisterWithWhatsappContent,\n RegisterWithWhatsappHeaderParams,\n RemoveProfileImagePathParams,\n RemoveProfileImageResponse,\n ResetPasswordBody,\n ResetPasswordContent,\n UpdateProfileImageContent,\n UpdateProfileImageFormData,\n UpdateProfileImagePathParams,\n UpdateUserBody,\n UpdateUserContent,\n UpdateUserPathParams,\n VerifyOtpBody,\n VerifyOtpContent,\n} from \"@/types/storefront-api-types\";\n\n/**\n * Client for interacting with authentication endpoints\n */\nexport class AuthClient extends SessionStorefrontAPIClient {\n /**\n * Get anonymous token for guest users\n *\n * @example\n * ```typescript\n * // Get token for guest browsing\n * const { data, error } = await sdk.auth.getAnonymousToken();\n *\n * if (error) {\n * console.error(\"Failed to get anonymous token:\", error.message);\n * } else {\n * console.log(\"Anonymous token:\", data.access_token);\n * // Store token or proceed with guest operations\n * }\n * ```\n */\n public async getAnonymousToken(): Promise<\n ApiResult<GetAnonymousTokenContent>\n > {\n return this.executeRequest(() => this.client.POST(\"/auth/anonymous\"));\n }\n\n /**\n * Login with phone number\n *\n * @param body - Login request body containing phone number and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with phone number\n * const { data, error } = await sdk.auth.loginWithPhone({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"Login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * // Redirect user to OTP verification screen\n * }\n * ```\n */\n public async loginWithPhone(\n body: LoginWithPhoneBody,\n headers?: LoginWithPhoneHeaderParams\n ): Promise<ApiResult<LoginWithPhoneContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/phone\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with WhatsApp\n *\n * @param body - Login request body containing phone number and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with WhatsApp number\n * const { data, error } = await sdk.auth.loginWithWhatsApp({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"WhatsApp login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent to WhatsApp. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * }\n * ```\n */\n public async loginWithWhatsApp(\n body: LoginWithWhatsappBody,\n headers?: LoginWithWhatsappHeaderParams\n ): Promise<ApiResult<LoginWithWhatsappContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/whatsapp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with email\n *\n * @param body - Login request body containing email and options\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Login with email address\n * const { data, error } = await sdk.auth.loginWithEmail({\n * email: \"customer@example.com\",\n * register_if_not_exists: true\n * });\n *\n * if (error) {\n * console.error(\"Email login failed:\", error.message);\n * } else {\n * console.log(\"OTP sent to email. Token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action); // \"login\" or \"register\"\n * // Show OTP input form\n * }\n * ```\n */\n public async loginWithEmail(\n body: LoginWithEmailBody,\n headers?: LoginWithEmailHeaderParams\n ): Promise<ApiResult<LoginWithEmailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/email\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Login with password\n *\n * @param body - Login credentials containing email/phone and password\n * @returns Promise with user info and tokens\n * @example\n * ```typescript\n * // Login with email and password\n * const { data, error } = await sdk.auth.loginWithPassword({\n * email: \"customer@example.com\",\n * password: \"securePassword123\"\n * });\n *\n * if (error) {\n * console.error(\"Password login failed:\", error.message);\n * } else {\n * console.log(\"Login successful:\", data.user.email);\n * console.log(\"Access token:\", data.access_token);\n * }\n * ```\n */\n public async loginWithPassword(\n body: LoginWithPasswordBody\n ): Promise<ApiResult<LoginWithPasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/login/password\", {\n body: body,\n })\n );\n }\n\n /**\n * Start forgot-password OTP flow\n *\n * @param body - Request body containing email or phone details\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for the reset flow\n * @example\n * ```typescript\n * // Send password reset OTP\n * const { data, error } = await sdk.auth.forgotPassword({\n * email: \"customer@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"Password reset failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async forgotPassword(\n body: ForgotPasswordBody,\n headers?: ForgotPasswordHeaderParams\n ): Promise<ApiResult<ForgotPasswordContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/forgot-password\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Reset password\n *\n * @param body - Reset password request body containing new password and OTP token\n * @returns Promise with new access and refresh tokens\n * @example\n * ```typescript\n * // Reset password with OTP token from forgot password flow\n * const { data, error } = await sdk.auth.resetPassword({\n * new_password: \"newSecurePassword123\",\n * confirm_password: \"newSecurePassword123\",\n * otp_token: \"abc123otptoken\"\n * });\n *\n * if (error) {\n * console.error(\"Password reset failed:\", error.message);\n * } else {\n * console.log(\"Password reset successful\");\n * console.log(\"New access token:\", data.access_token);\n * }\n * ```\n */\n public async resetPassword(\n body: ResetPasswordBody\n ): Promise<ApiResult<ResetPasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/reset-password\", {\n body: body,\n })\n );\n }\n\n /**\n * Change password\n *\n * @param body - Change password request body containing old and new passwords\n * @returns Promise with new access and refresh tokens\n * @example\n * ```typescript\n * // Change user's password\n * const { data, error } = await sdk.auth.changePassword({\n * old_password: \"currentPassword123\",\n * new_password: \"newSecurePassword456\",\n * confirm_password: \"newSecurePassword456\"\n * });\n *\n * if (error) {\n * console.error(\"Password change failed:\", error.message);\n * } else {\n * console.log(\"Password changed successfully\");\n * console.log(\"New access token:\", data.access_token);\n * }\n * ```\n */\n public async changePassword(\n body: ChangePasswordBody\n ): Promise<ApiResult<ChangePasswordContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/change-password\", {\n body: body,\n })\n );\n }\n\n /**\n * Verify OTP\n *\n * @param body - OTP verification data including code and tokens\n * @returns Promise with user info and tokens\n * @example\n * ```typescript\n * // Verify OTP after login attempt\n * const { data, error } = await sdk.auth.verifyOtp({\n * otp: \"1234\",\n * otp_token: \"56895455\",\n * otp_action: \"login\" // or \"register\"\n * });\n *\n * if (error) {\n * console.error(\"OTP verification failed:\", error.message);\n * // Show error message, allow retry\n * } else {\n * console.log(\"Login successful:\", data.user.email);\n * console.log(\"User ID:\", data.user.id);\n * }\n * ```\n */\n public async verifyOtp(\n body: VerifyOtpBody\n ): Promise<ApiResult<VerifyOtpContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/verify-otp\", {\n body: body,\n })\n );\n }\n\n /**\n * Register with phone\n *\n * @param body - Registration details including phone number and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with phone number\n * const { data, error } = await sdk.auth.registerWithPhone({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"Phone registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithPhone(\n body: RegisterWithPhoneBody,\n headers?: RegisterWithPhoneHeaderParams\n ): Promise<ApiResult<RegisterWithPhoneContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/phone\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with email\n *\n * @param body - Registration details including email and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with email address\n * const { data, error } = await sdk.auth.registerWithEmail({\n * email: \"jane.smith@example.com\",\n * first_name: \"Jane\",\n * last_name: \"Smith\",\n * phone: \"9876543210\"\n * });\n *\n * if (error) {\n * console.error(\"Email registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithEmail(\n body: RegisterWithEmailBody,\n headers?: RegisterWithEmailHeaderParams\n ): Promise<ApiResult<RegisterWithEmailContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/email\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with WhatsApp\n *\n * @param body - Registration details including WhatsApp number and user information\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * // Register a new user with WhatsApp number\n * const { data, error } = await sdk.auth.registerWithWhatsapp({\n * phone: \"9876543210\",\n * country_code: \"+91\",\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\"\n * });\n *\n * if (error) {\n * console.error(\"WhatsApp registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithWhatsapp(\n body: RegisterWithWhatsappBody,\n headers?: RegisterWithWhatsappHeaderParams\n ): Promise<ApiResult<RegisterWithWhatsappContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/whatsapp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Register with password\n *\n * @param body - Registration details including email or phone and password\n * @param headers - Optional header parameters (for example `x-debug-mode`)\n * @returns Promise with OTP token and action for completing registration\n * @example\n * ```typescript\n * const { data, error } = await sdk.auth.registerWithPassword({\n * email: \"jane.smith@example.com\",\n * password: \"securePassword123\",\n * confirm_password: \"securePassword123\",\n * });\n *\n * if (error) {\n * console.error(\"Password registration failed:\", error.message);\n * } else {\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async registerWithPassword(\n body: RegisterWithPasswordBody,\n headers?: RegisterWithPasswordHeaderParams\n ): Promise<ApiResult<RegisterWithPasswordContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/register/password\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Refresh the access token using a refresh token\n * @param body - Request body containing the refresh token\n * @returns Promise with the new access token and refresh token\n * @example\n * ```typescript\n * // Refresh access token when it expires\n * const { data, error } = await sdk.auth.refreshToken({\n * refresh_token: \"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...\"\n * });\n *\n * if (error) {\n * console.error(\"Token refresh failed:\", error.message);\n * // Redirect to login\n * } else {\n * console.log(\"Token refreshed successfully\");\n * console.log(\"New access token:\", data.access_token);\n * console.log(\"New refresh token:\", data.refresh_token);\n * }\n * ```\n */\n public async refreshToken(\n body: RefreshTokenBody\n ): Promise<ApiResult<RefreshTokenContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/refresh-token\", {\n body: body,\n })\n );\n }\n\n /**\n * Logout\n *\n * @returns Promise that resolves when logout is complete\n * @example\n * ```typescript\n * // Logout current user\n * const { data, error } = await sdk.auth.logout();\n *\n * if (error) {\n * console.error(\"Logout failed:\", error.message);\n * } else {\n * console.log(\"Logout successful\");\n * console.log(\"Session ended for user:\", data.user.email);\n * }\n * ```\n */\n public async logout(): Promise<ApiResult<LogoutContent>> {\n return this.executeRequest(() => this.client.POST(\"/auth/logout\"));\n }\n\n /**\n * Get user details\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with user details\n * @example\n * ```typescript\n * // Get details for a specific user\n * const { data, error } = await sdk.auth.getUserDetails({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get user details:\", error.message);\n * } else {\n * console.log(\"User details:\", data.user);\n * console.log(\"Email:\", data.user.email);\n * console.log(\"Phone:\", data.user.phone);\n * console.log(\"Created:\", data.user.created_at);\n * }\n * ```\n */\n public async getUserDetails(\n pathParams: GetUserDetailPathParams\n ): Promise<ApiResult<GetUserDetailContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Update user details\n *\n * @param pathParams - Path parameters containing user ID\n * @param body - Updated user information\n * @returns Promise with updated user details\n * @example\n * ```typescript\n * // Update user profile information\n * const { data, error } = await sdk.auth.updateUserDetails(\n * { id: \"01H9XYZ12345USERID\" },\n * {\n * first_name: \"John\",\n * last_name: \"Doe\",\n * email: \"john.doe@example.com\",\n * phone: \"9876543210\",\n * country_code: \"+91\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update user:\", error.message);\n * } else {\n * console.log(\"User updated successfully:\", data.user.first_name);\n * }\n * ```\n */\n public async updateUserDetails(\n pathParams: UpdateUserPathParams,\n body: UpdateUserBody\n ): Promise<ApiResult<UpdateUserContent>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n\n /**\n * Delete user account\n *\n * @description Deletes a user account. If the user is a primary user, deletes the associated\n * customer and all linked users. If the user is a normal user, deletes only that user without\n * affecting the customer or other users.\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deletion confirmation\n * @example\n * ```typescript\n * // Delete a user account\n * const { data, error } = await sdk.auth.deleteUser({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete user:\", error.message);\n * } else {\n * console.log(\"User deleted successfully\");\n * console.log(\"Success:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async deleteUser(\n pathParams: DeleteUserPathParams\n ): Promise<ApiResult<DeleteUserResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/auth/user/{id}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Add profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @param formData - Form data containing the image file\n * @returns Promise with profile image URL\n * @example\n * ```typescript\n * // Add profile image for a user\n * const imageFile = document.getElementById('file-input').files[0];\n * const { data, error } = await sdk.auth.addProfileImage(\n * { id: \"01H9XYZ12345USERID\" },\n * { image: imageFile }\n * );\n *\n * if (error) {\n * console.error(\"Failed to add profile image:\", error.message);\n * } else {\n * console.log(\"Profile image added successfully\");\n * console.log(\"Image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async addProfileImage(\n pathParams: AddProfileImagePathParams,\n formData: AddProfileImageFormData\n ): Promise<ApiResult<AddProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n fd.append(key, value);\n }\n }\n return fd;\n },\n })\n );\n }\n\n /**\n * Update profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @param formData - Form data containing the new image file\n * @returns Promise with updated profile image URL\n * @example\n * ```typescript\n * // Update existing profile image\n * const newImageFile = document.getElementById('file-input').files[0];\n * const { data, error } = await sdk.auth.updateProfileImage(\n * { id: \"01H9XYZ12345USERID\" },\n * { image: newImageFile }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update profile image:\", error.message);\n * } else {\n * console.log(\"Profile image updated successfully\");\n * console.log(\"New image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async updateProfileImage(\n pathParams: UpdateProfileImagePathParams,\n formData: UpdateProfileImageFormData\n ): Promise<ApiResult<UpdateProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n body: formData,\n bodySerializer: (body) => {\n const fd = new FormData();\n for (const [key, value] of Object.entries(body)) {\n if (value !== undefined && value !== null) {\n fd.append(key, value);\n }\n }\n return fd;\n },\n })\n );\n }\n\n /**\n * Delete profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deletion confirmation\n * @example\n * ```typescript\n * // Delete user's profile image\n * const { data, error } = await sdk.auth.deleteProfileImage({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete profile image:\", error.message);\n * } else {\n * console.log(\"Profile image deleted successfully\");\n * console.log(\"Success:\", data.success);\n * }\n * ```\n */\n public async deleteProfileImage(\n pathParams: RemoveProfileImagePathParams\n ): Promise<ApiResult<RemoveProfileImageResponse>> {\n return this.executeRequest(() =>\n this.client.DELETE(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Get profile image\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with profile image URL\n * @example\n * ```typescript\n * // Get user's profile image URL\n * const { data, error } = await sdk.auth.getProfileImage({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get profile image:\", error.message);\n * } else {\n * console.log(\"Profile image URL:\", data.profile_image_url);\n * }\n * ```\n */\n public async getProfileImage(\n pathParams: GetProfileImagePathParams\n ): Promise<ApiResult<GetProfileImageContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/auth/user/{id}/profile-image\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Deactivate user account\n *\n * @param pathParams - Path parameters containing user ID\n * @returns Promise with deactivation confirmation\n * @example\n * ```typescript\n * // Deactivate a user account\n * const { data, error } = await sdk.auth.deactivateUserAccount({\n * id: \"01H9XYZ12345USERID\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to deactivate account:\", error.message);\n * } else {\n * console.log(\"Account deactivated successfully\");\n * console.log(\"Success:\", data.success);\n * }\n * ```\n */\n public async deactivateUserAccount(\n pathParams: DeactivateUserPathParams\n ): Promise<ApiResult<DeactivateUserResponse>> {\n return this.executeRequest(() =>\n this.client.PUT(\"/auth/user/{id}/deactivate\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Generate OTP\n *\n * @param body - OTP generation body (phone or email)\n * @returns Promise with OTP token and action\n * @example\n * ```typescript\n * // Generate OTP for phone number\n * const { data, error } = await sdk.auth.generateOtp({\n * phone: \"9876543210\",\n * country_code: \"+91\"\n * });\n *\n * if (error) {\n * console.error(\"OTP generation failed:\", error.message);\n * } else {\n * console.log(\"OTP sent successfully\");\n * console.log(\"OTP token:\", data.otp_token);\n * console.log(\"Action:\", data.otp_action);\n * }\n * ```\n */\n public async generateOtp(\n body: GenerateOtpBody,\n headers?: GenerateOtpHeaderParams\n ): Promise<ApiResult<GenerateOtpContent>> {\n const mergedHeaders = this.mergeHeaders(headers);\n return this.executeRequest(() =>\n this.client.POST(\"/auth/generate-otp\", {\n body: body,\n params: {\n header: mergedHeaders,\n },\n })\n );\n }\n\n /**\n * Check whether email or phone is already verified\n *\n * @param body - Request body containing phone numbers or email addresses to verify\n * @returns Promise with verification status for provided contacts\n * @example\n * ```typescript\n * // Check verification status for multiple contacts\n * const { data, error } = await sdk.auth.checkEmailOrPhoneIsVerified({\n * phone: [\"9876543210\", \"9123456789\"],\n * email: [\"user1@example.com\", \"user2@example.com\"]\n * });\n *\n * if (error) {\n * console.error(\"Verification check failed:\", error.message);\n * } else {\n * console.log(\"Verified phones:\", data.verified_phone);\n * console.log(\"Verified emails:\", data.verified_email);\n * }\n * ```\n */\n public async checkEmailOrPhoneIsVerified(\n body: CheckVerificationStatusBody\n ): Promise<ApiResult<CheckVerificationStatusContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/auth/verified-email-phone\", {\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CancelOrderBody,\n CancelOrderContent,\n CancelOrderPathParams,\n CancelPaymentRequestPathParams,\n CancelPaymentRequestResponse,\n CreateOrderBody,\n CreateOrderContent,\n GetOrderDetailContent,\n GetOrderDetailPathParams,\n GetPaymentStatusContent,\n ListOrderPaymentsContent,\n ListOrderPaymentsPathParams,\n ListOrderRefundsContent,\n ListOrderRefundsPathParams,\n ListOrdersContent,\n ListOrderShipmentsContent,\n ListOrderShipmentsPathParams,\n ListOrdersQuery,\n RetryOrderPaymentBody,\n RetryOrderPaymentContent,\n RetryOrderPaymentPathParams,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with order endpoints\n */\nexport class OrderClient extends SessionStorefrontAPIClient {\n /**\n * Get order details\n *\n * @param orderNumber - Order number\n * @returns Promise with order details\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.getOrderDetails({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order details:\", error.message);\n * } else {\n * console.log(\"Order details:\", data.order);\n * console.log(\"Order status:\", data.order.status);\n * console.log(\"Total amount:\", data.order.grand_total);\n * }\n * ```\n */\n public async getOrderDetails(\n pathParams: GetOrderDetailPathParams\n ): Promise<ApiResult<GetOrderDetailContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Create order\n *\n * @param body - Order creation request body\n * @returns Promise with order details\n * @example\n * ```typescript\n * // Juspay Hyper Checkout - Redirects to hosted payment page\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"hyper-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * action: \"paymentPage\"\n * }\n * });\n *\n * // Juspay Express Checkout - New Card\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"CARD\",\n * payment_method: \"VISA\",\n * auth_type: \"OTP\",\n * save_to_locker: true,\n * card_number: \"4111111111111111\",\n * card_exp_month: \"12\",\n * card_exp_year: \"2025\",\n * name_on_card: \"John Doe\",\n * card_security_code: \"123\"\n * }\n * });\n *\n * // Juspay Express Checkout - Saved Card Token\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * get_client_auth_token: true,\n * payment_method_type: \"CARD\",\n * payment_method: \"VISA\",\n * auth_type: \"OTP\",\n * save_to_locker: false,\n * card_token: \"token_abc123\",\n * card_security_code: \"123\"\n * }\n * });\n *\n * // Juspay Express Checkout - UPI Collect\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"UPI\",\n * payment_method: \"UPI_COLLECT\",\n * upi_vpa: \"user@upi\"\n * }\n * });\n *\n * // Juspay Express Checkout - Net Banking\n * const { data, error } = await sdk.order.createOrder({\n * cart_id: \"cart_01H9XYZ12345ABCDE\",\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"NB\",\n * payment_method: \"NB_HDFC\"\n * }\n * });\n *\n * if (error) {\n * console.error(\"Failed to create order:\", error.message);\n * } else {\n * console.log(\"Order created:\", data.order.id);\n * console.log(\"Payment required:\", data.payment_required);\n * console.log(\"Payment info:\", data.payment_info);\n *\n * // For hyper-checkout, redirect to payment page\n * if (\"payment_links\" in data.payment_info) {\n * window.location.href = data.payment_info.payment_links?.web;\n * }\n *\n * // For express-checkout with OTP authentication\n * if (\"payment\" in data.payment_info && data.payment_info.payment?.authentication?.params) {\n * const { id: txn_id, challenge_id } = data.payment_info.payment.authentication.params;\n * // Use txn_id and challenge_id with sdk.payments.authenticateDirectOtp()\n * }\n * }\n * ```\n */\n public async createOrder(\n body: CreateOrderBody\n ): Promise<ApiResult<CreateOrderContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders\", {\n body: body,\n })\n );\n }\n\n /**\n * List all orders\n *\n * @param queryParams - Optional query parameters for filtering and pagination. When `user_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with order list\n * @example\n * ```typescript\n * // Basic usage\n * const { data, error } = await sdk.order.listOrders();\n *\n * // Advanced usage with optional parameters\n * const { data, error } = await sdk.order.listOrders({\n * page: 1,\n * limit: 20,\n * sort_by: '{\"created_at\":\"desc\"}',\n * status: [\"confirmed\", \"shipped\", \"delivered\"]\n * });\n *\n * if (error) {\n * console.error(\"Failed to list orders:\", error.message);\n * } else {\n * console.log(\"Orders found:\", data.orders?.length || 0);\n * console.log(\"Pagination:\", data.pagination);\n *\n * data.orders?.forEach(order => {\n * console.log(`Order ${order.order_number}: ${order.status}`);\n * });\n * }\n * ```\n */\n public async listOrders(): Promise<ApiResult<ListOrdersContent>>;\n public async listOrders(\n queryParams: Partial<ListOrdersQuery>\n ): Promise<ApiResult<ListOrdersContent>>;\n public async listOrders(\n queryParams: Partial<ListOrdersQuery> = {}\n ): Promise<ApiResult<ListOrdersContent>> {\n const resolvedQueryParams =\n await this.resolveUserQueryParams<ListOrdersQuery>(queryParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/orders\", {\n params: {\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * Get payment status for an order\n *\n * @param orderNumber - Order number\n * @returns Promise with payment status\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.getPaymentStatus(\"ORD-2024-001\");\n *\n * if (error) {\n * console.error(\"Failed to get payment status:\", error.message);\n * } else {\n * console.log(\"Payment status:\", data.status);\n * console.log(\"Amount paid:\", data.amount_paid);\n * console.log(\"Amount unpaid:\", data.amount_unpaid);\n * console.log(\"Retry available:\", data.is_retry_available);\n * }\n * ```\n */\n public async getPaymentStatus(\n orderNumber: string\n ): Promise<ApiResult<GetPaymentStatusContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/payment-status\", {\n params: {\n path: { order_number: orderNumber },\n },\n })\n );\n }\n\n /**\n * Get all shipments for an order\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with shipments\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderShipments({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order shipments:\", error.message);\n * } else {\n * console.log(\"Shipments found:\", data.shipments?.length || 0);\n *\n * data.shipments?.forEach(shipment => {\n * console.log(`Shipment ${shipment.reference_number}: ${shipment.status}`);\n * console.log(\"AWB:\", shipment.awb_no);\n * console.log(\"Courier:\", shipment.courier_company_name);\n * });\n * }\n * ```\n */\n public async listOrderShipments(\n pathParams: ListOrderShipmentsPathParams\n ): Promise<ApiResult<ListOrderShipmentsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/shipments\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * List order payments\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with payments\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderPayments({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order payments:\", error.message);\n * } else {\n * console.log(\"Payments found:\", data.payments?.length || 0);\n *\n * data.payments?.forEach(payment => {\n * console.log(`Payment ${payment.request_number}: ${payment.payment_status}`);\n * console.log(\"Amount:\", payment.amount);\n * console.log(\"Reference:\", payment.payment_reference_number);\n * });\n * }\n * ```\n */\n public async listOrderPayments(\n pathParams: ListOrderPaymentsPathParams\n ): Promise<ApiResult<ListOrderPaymentsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/payments\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * List order refunds\n *\n * @param pathParams - Order number path parameters\n * @returns Promise with refunds\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.listOrderRefunds({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get order refunds:\", error.message);\n * } else {\n * console.log(\"Refunds found:\", data.refunds?.length || 0);\n *\n * data.refunds?.forEach(refund => {\n * console.log(`Refund ${refund.request_number}: ${refund.status}`);\n * console.log(\"Amount:\", refund.refund_amount);\n * console.log(\"Reason:\", refund.refund_remarks);\n * console.log(\"Processed at:\", refund.refund_date);\n * });\n * }\n * ```\n */\n public async listOrderRefunds(\n pathParams: ListOrderRefundsPathParams\n ): Promise<ApiResult<ListOrderRefundsContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/orders/{order_number}/refunds\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Cancel an order\n *\n * @param pathParams - Order number path parameters\n * @param body - Cancellation request body\n * @returns Promise with order details\n * @example\n * ```typescript\n * const { data, error } = await sdk.order.cancelOrder(\n * { order_number: \"ORD-2024-001\" },\n * {\n * cancellation_reason: \"Customer requested cancellation\",\n * refund_mode: \"original_payment_mode\",\n * feedback: \"Customer changed their mind about the purchase\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to cancel order:\", error.message);\n * } else {\n * console.log(\"Order cancelled successfully\");\n * console.log(\"Updated order status:\", data.order?.status);\n * console.log(\"Cancellation reason:\", data.order?.cancellation_reason);\n * }\n * ```\n */\n public async cancelOrder(\n pathParams: CancelOrderPathParams,\n body: CancelOrderBody\n ): Promise<ApiResult<CancelOrderContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/cancel\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n\n /**\n * Cancel a payment request for an order\n *\n * @description Use when the express checkout payment flow is used and the user wants to switch\n * payment methods (e.g. started with UPI, then chose another). Without this call, the user must\n * wait until the payment-status API returns `status: failed` and `is_retry_available: true`\n * (typically ~3 minutes). Calling this endpoint cancels the existing payment request so the user\n * can retry payment immediately.\n *\n * @param pathParams - Path parameters containing the order number\n * @returns Promise with cancellation confirmation\n * @example\n * ```typescript\n * // Cancel an in-progress payment request to switch payment methods\n * const { data, error } = await sdk.order.cancelPaymentRequest({\n * order_number: \"ORD-2024-001\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to cancel payment request:\", error.message);\n * } else {\n * console.log(\"Payment request cancelled:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async cancelPaymentRequest(\n pathParams: CancelPaymentRequestPathParams\n ): Promise<ApiResult<CancelPaymentRequestResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/cancel-payment-request\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Retry payment for an order\n *\n * @param pathParams - Order number path parameters\n * @param body - Payment retry request body\n * @returns Promise with payment information\n * @example\n * ```typescript\n * // Juspay Hyper Checkout - Redirects to hosted payment page\n * const { data, error } = await sdk.order.retryOrderPayment(\n * { order_number: \"ORD-2024-001\" },\n * {\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"hyper-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * action: \"paymentPage\"\n * }\n * }\n * );\n *\n * // Juspay Express Checkout - UPI Collect\n * const { data, error } = await sdk.order.retryOrderPayment(\n * { order_number: \"ORD-2024-001\" },\n * {\n * payment_method: {\n * payment_provider_slug: \"juspay\",\n * integration_type: \"express-checkout\",\n * gateway_reference_id: \"gateway_ref_123\",\n * return_url: \"https://yourapp.com/payment/return\",\n * payment_method_type: \"UPI\",\n * payment_method: \"UPI_COLLECT\",\n * upi_vpa: \"user@upi\"\n * }\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to retry payment:\", error.message);\n * } else {\n * console.log(\"Payment retry initiated\");\n * console.log(\"Payment info:\", data.payment_info);\n *\n * // For hyper-checkout, redirect to payment page\n * if (\"payment_links\" in data.payment_info) {\n * window.location.href = data.payment_info.payment_links?.web;\n * }\n * }\n * ```\n */\n public async retryOrderPayment(\n pathParams: RetryOrderPaymentPathParams,\n body: RetryOrderPaymentBody\n ): Promise<ApiResult<RetryOrderPaymentContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/orders/{order_number}/retry-payment\", {\n params: {\n path: pathParams,\n },\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n ListPaymentMethodsContent,\n ListPaymentMethodsQuery,\n VerifyVpaContent,\n VerifyVpaQuery,\n AuthenticateDirectOtpBody,\n AuthenticateDirectOtpResponse,\n ResendDirectOtpBody,\n ResendDirectOtpContent,\n GetCardInfoContent,\n GetCardInfoQuery,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with payment endpoints\n */\nexport class PaymentsClient extends SessionStorefrontAPIClient {\n /**\n * List all available payment methods\n *\n * @param queryParams - Query parameters containing the payment method type and payment provider slug\n * @returns Promise with list of payment methods\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.listPaymentMethods({\n * payment_method_type: \"card\",\n * payment_provider_slug: \"payu\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list payment methods:\", error.message);\n * } else {\n * console.log(\"Payment methods:\", data.payment_methods);\n *\n * data.payment_methods?.forEach(method => {\n * console.log(\"Payment method:\", method.name);\n * console.log(\"Gateway:\", method.payment_gateway);\n * });\n * }\n * ```\n */\n public async listPaymentMethods(\n queryParams?: ListPaymentMethodsQuery\n ): Promise<\n ApiResult<ListPaymentMethodsContent>\n > {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/payment-methods\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Verify a UPI Virtual Payment Address (VPA)\n *\n * @description The Virtual Payment Address or VPA is a unique ID given to an individual\n * using the Unified Payment Interface (UPI) service to send or receive money.\n * Validating the VPA helps reduce payment failure rates due to incorrect VPA.\n *\n * @param queryParams - Query parameters containing the VPA to verify\n * @returns Promise with VPA verification result\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.verifyVpa({\n * vpa: \"user@upi\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to verify VPA:\", error.message);\n * } else {\n * console.log(\"VPA:\", data.vpa);\n * console.log(\"Status:\", data.status);\n *\n * if (data.status === \"valid\") {\n * console.log(\"VPA is valid and can be used for UPI payments\");\n * } else {\n * console.log(\"VPA is invalid, please check and try again\");\n * }\n * }\n * ```\n */\n public async verifyVpa(\n queryParams?: VerifyVpaQuery\n ): Promise<ApiResult<VerifyVpaContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/verify-vpa\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * Get card information\n *\n * Retrieves card information based on the initial 9 digits (card BIN) of the card number.\n *\n * @param queryParams - Query parameters containing the card BIN\n * @returns Promise with card information\n * @example\n * ```typescript\n * const { data, error } = await sdk.payments.getCardInfo({\n * cardbin: \"411111111\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get card information:\", error.message);\n * } else {\n * console.log(\"Card information:\", data.card_info);\n * }\n * ```\n */\n public async getCardInfo(\n queryParams: GetCardInfoQuery\n ): Promise<ApiResult<GetCardInfoContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/payments/card-info\", {\n params: {\n query: queryParams,\n },\n })\n );\n }\n \n /**\n * Authenticate a direct OTP for payment verification\n *\n * @description Used to authenticate OTP during payment flows that require 2FA verification.\n * The txn_id and challenge_id can be obtained from the create order API response\n * under the payment_info.authentication.params object.\n *\n * @param body - OTP authentication request body\n * @returns Promise with authentication result\n * @example\n * ```typescript\n * // After creating an order, if OTP authentication is required:\n * const { data, error } = await sdk.payments.authenticateDirectOtp({\n * txn_id: \"txn_01H9XYZ12345ABCDE\",\n * challenge_id: \"challenge_01H9XYZ12345ABCDE\",\n * otp: \"123456\"\n * });\n *\n * if (error) {\n * console.error(\"OTP authentication failed:\", error.message);\n * } else {\n * console.log(\"Authentication success:\", data.success);\n * console.log(\"Message:\", data.message);\n * }\n * ```\n */\n public async authenticateDirectOtp(\n body: AuthenticateDirectOtpBody\n ): Promise<ApiResult<AuthenticateDirectOtpResponse>> {\n return this.executeRequest(() =>\n this.client.POST(\"/payments/authenticate-direct-otp\", {\n body: body,\n })\n );\n }\n\n /**\n * Resend a direct OTP for payment verification\n *\n * @description Used to resend OTP during payment flows that require 2FA verification.\n * The txn_id and challenge_id can be obtained from the create order API response\n * under the payment_info.authentication.params object.\n *\n * @param body - OTP resend request body\n * @returns Promise with new payment info containing updated OTP challenge\n * @example\n * ```typescript\n * // If user didn't receive OTP or it expired:\n * const { data, error } = await sdk.payments.resendDirectOtp({\n * txn_id: \"txn_01H9XYZ12345ABCDE\",\n * challenge_id: \"challenge_01H9XYZ12345ABCDE\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to resend OTP:\", error.message);\n * } else {\n * console.log(\"OTP resent successfully\");\n * console.log(\"New payment info:\", data.payment_info);\n * }\n * ```\n */\n public async resendDirectOtp(\n body: ResendDirectOtpBody\n ): Promise<ApiResult<ResendDirectOtpContent>> {\n return this.executeRequest(() =>\n this.client.POST(\"/payments/resend-direct-otp\", {\n body: body,\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n ListCountriesContent,\n ListCountryPincodesContent,\n ListCountryPincodesPathParams,\n ListCountryPincodesQuery,\n ListCountryStatesContent,\n ListCountryStatesPathParams,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class BaseHelpersClient extends StorefrontAPIClientBase {\n /**\n * Get a list of countries\n *\n * @returns Promise with countries\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountries();\n *\n * if (error) {\n * console.error(\"Failed to get countries:\", error);\n * return;\n * }\n *\n * console.log(\"Countries found:\", data.countries?.length || 0);\n *\n * data.countries?.forEach(country => {\n * console.log(`Country: ${country.country_name} (${country.country_iso_code})`);\n * console.log(\"Currency:\", country.currency_code);\n * });\n * ```\n */\n public async listCountries(): Promise<ApiResult<ListCountriesContent>> {\n return this.executeRequest(() => this.client.GET(\"/common/countries\", {}));\n }\n\n /**\n * Get a list of states for a country\n *\n * @param pathParams - Path parameters\n * @returns Promise with states\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountryStates({\n * country_iso_code: \"IN\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get states:\", error);\n * return;\n * }\n *\n * console.log(\"States found:\", data.states?.length || 0);\n *\n * data.states?.forEach(state => {\n * console.log(`State: ${state.name} (${state.iso_code})`);\n * });\n *\n * // Get states for different country\n * const { data: usStates, error: usError } = await sdk.helpers.listCountryStates({\n * country_iso_code: \"US\"\n * });\n *\n * if (usError) {\n * console.error(\"Failed to get US states:\", usError);\n * return;\n * }\n *\n * console.log(\"US States:\", usStates.states?.map(s => s.name).join(\", \"));\n * ```\n */\n public async listCountryStates(\n pathParams: ListCountryStatesPathParams\n ): Promise<ApiResult<ListCountryStatesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/common/countries/{country_iso_code}/states\", {\n params: {\n path: pathParams,\n },\n })\n );\n }\n\n /**\n * Get pincodes for a country\n *\n * @param pathParams - Path parameters\n * @returns Promise with pincodes\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.helpers.listCountryPincodes({\n * country_iso_code: \"IN\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get pincodes:\", error);\n * return;\n * }\n *\n * console.log(\"Pincodes found:\", data.pincodes?.length || 0);\n *\n * data.pincodes?.forEach(pincode => {\n * console.log(`Pincode: ${pincode.pincode} - ${pincode.city}, ${pincode.state_name}`);\n * });\n *\n * // Get pincodes for different country\n * const { data: usPincodes, error: usError } = await sdk.helpers.listCountryPincodes({\n * country_iso_code: \"US\"\n * });\n *\n * if (usError) {\n * console.error(\"Failed to get US pincodes:\", usError);\n * return;\n * }\n *\n * console.log(\"US Pincodes:\", usPincodes.pincodes?.map(p => p.pincode).join(\", \"));\n * ```\n */\n public async listCountryPincodes(\n pathParams: ListCountryPincodesPathParams,\n queryParams?: ListCountryPincodesQuery\n ): Promise<ApiResult<ListCountryPincodesContent>> {\n return this.executeRequest(() =>\n this.client.GET(\"/common/countries/{country_iso_code}/pincodes\", {\n params: {\n path: pathParams,\n query: queryParams,\n },\n })\n );\n }\n}\n","import { BaseHelpersClient } from \"@/lib/shared/helper\";\nimport {\n attachPublicAuth,\n PublicStorefrontAPIClient,\n} from \"@/lib/public/client\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class PublicHelpersClient extends BaseHelpersClient {\n constructor(config: ConstructorParameters<typeof PublicStorefrontAPIClient>[0]) {\n super(config);\n attachPublicAuth(this);\n }\n}\n","import { BaseHelpersClient } from \"@/lib/shared/helper\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with helper endpoints\n */\nexport class HelpersClient extends BaseHelpersClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CreateAddressBody,\n CreateAddressContent,\n CreateAddressPathParams,\n DeleteAddressPathParams,\n DeleteAddressResponse,\n GetAddressDetailContent,\n GetAddressDetailPathParams,\n GetLoyaltyDetailsContent,\n GetLoyaltyDetailsPathParams,\n ListAddressesContent,\n ListAddressesPathParams,\n ListAddressesQuery,\n ListCustomerReviewsContent,\n ListCustomerReviewsPathParams,\n ListLoyaltyActivitiesContent,\n ListLoyaltyActivitiesPathParams,\n ListLoyaltyActivitiesQuery,\n UpdateAddressDetailBody,\n UpdateAddressDetailContent,\n UpdateAddressDetailPathParams,\n ListSavedPaymentMethodsContent,\n ListSavedPaymentMethodsPathParams,\n ListCustomerCardsContent,\n ListCustomerCardsPathParams,\n ListSavedPaymentMethodsQuery,\n} from \"@/types/storefront-api-types\";\nimport { SessionStorefrontAPIClient } from \"./session/client\";\n\n/**\n * Client for interacting with customer endpoints\n */\nexport class CustomerClient extends SessionStorefrontAPIClient {\n\n /**\n * Get all saved addresses for a customer\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param queryParams - Optional query parameters when path params are provided.\n * @returns Promise with addresses\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listAddresses();\n *\n * if (error) {\n * console.error(\"Failed to list addresses:\", error);\n * return;\n * }\n *\n * console.log(\"Addresses:\", data.addresses);\n * console.log(\"Pagination:\", data.pagination);\n *\n * // With pagination\n * const { data: page2, error: page2Error } = await sdk.customer.listAddresses({\n * page: 2,\n * limit: 10\n * });\n * ```\n */\n public async listAddresses(): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n queryParams: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n pathParams: { customer_id: string },\n queryParams?: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>>;\n public async listAddresses(\n pathParamsOrQuery?:\n | { customer_id?: string }\n | ListAddressesQuery,\n queryParams?: ListAddressesQuery\n ): Promise<ApiResult<ListAddressesContent>> {\n const hasPathParams =\n queryParams !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"customer_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { customer_id?: string })\n : {};\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListAddressesPathParams>(pathParams);\n const resolvedQueryParams = hasPathParams\n ? queryParams\n : (pathParamsOrQuery as ListAddressesQuery | undefined);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/addresses\", {\n params: {\n path: resolvedPathParams,\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * Create a new address for a customer\n *\n * @param pathParamsOrBody - Optional path parameters or the address body.\n * @param maybeBody - Address body when path params are provided.\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.createAddress({\n * address_line1: \"123 Main Street\",\n * address_line2: \"Apt 4B\",\n * city: \"New York\",\n * state: \"NY\",\n * country: \"US\",\n * pincode: \"10001\",\n * is_default_billing: true,\n * is_default_shipping: false\n * });\n *\n * if (error) {\n * console.error(\"Failed to create address:\", error);\n * return;\n * }\n *\n * console.log(\"Address created:\", data.address);\n * ```\n */\n public async createAddress(\n body: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>>;\n public async createAddress(\n pathParams: { customer_id: string },\n body: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>>;\n public async createAddress(\n pathParamsOrBody:\n | { customer_id?: string }\n | CreateAddressBody,\n maybeBody?: CreateAddressBody\n ): Promise<ApiResult<CreateAddressContent>> {\n const pathParams = maybeBody\n ? (pathParamsOrBody as { customer_id?: string })\n : {};\n const body = maybeBody ?? (pathParamsOrBody as CreateAddressBody);\n const resolvedPathParams =\n await this.resolveCustomerPathParams<CreateAddressPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.POST(\"/customers/{customer_id}/addresses\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Get an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.getAddress({\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to get address:\", error);\n * return;\n * }\n *\n * console.log(\"Address details:\", data.address);\n * ```\n */\n public async getAddress(\n pathParams: { address_id: string }\n ): Promise<ApiResult<GetAddressDetailContent>>;\n public async getAddress(\n pathParams: { address_id: string; customer_id: string }\n ): Promise<ApiResult<GetAddressDetailContent>>;\n public async getAddress(\n pathParams: { address_id: string; customer_id?: string }\n ): Promise<ApiResult<GetAddressDetailContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<GetAddressDetailPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Update an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @param body - Address update body\n * @returns Promise with address details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.updateAddress(\n * {\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * },\n * {\n * address_line1: \"456 Oak Avenue\",\n * city: \"Los Angeles\",\n * state: \"CA\",\n * pincode: \"90210\"\n * }\n * );\n *\n * if (error) {\n * console.error(\"Failed to update address:\", error);\n * return;\n * }\n *\n * console.log(\"Address updated:\", data.address);\n * ```\n */\n public async updateAddress(\n pathParams: { address_id: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>>;\n public async updateAddress(\n pathParams: { address_id: string; customer_id: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>>;\n public async updateAddress(\n pathParams: { address_id: string; customer_id?: string },\n body: UpdateAddressDetailBody\n ): Promise<ApiResult<UpdateAddressDetailContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<UpdateAddressDetailPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.PUT(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n body,\n })\n );\n }\n\n /**\n * Delete an address for a customer\n *\n * @param pathParams - Path parameters. `customer_id` is optional and resolved from the active session when omitted.\n * @returns Promise with deletion response\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.deleteAddress({\n * customer_id: \"customer_456\",\n * address_id: \"addr_789\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to delete address:\", error);\n * return;\n * }\n *\n * console.log(\"Address deleted:\", data.message);\n * ```\n */\n public async deleteAddress(\n pathParams: { address_id: string }\n ): Promise<ApiResult<DeleteAddressResponse>>;\n public async deleteAddress(\n pathParams: { address_id: string; customer_id: string }\n ): Promise<ApiResult<DeleteAddressResponse>>;\n public async deleteAddress(\n pathParams: { address_id: string; customer_id?: string }\n ): Promise<ApiResult<DeleteAddressResponse>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<DeleteAddressPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.DELETE(\"/customers/{customer_id}/addresses/{address_id}\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * Get customer loyalty details\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with loyalty details\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.getLoyaltyDetails();\n *\n * if (error) {\n * console.error(\"Failed to get loyalty details:\", error);\n * return;\n * }\n *\n * console.log(\"Loyalty info:\", data.loyalty);\n * console.log(\"Points balance:\", data.loyalty_point_balance);\n * ```\n */\n public async getLoyaltyDetails(): Promise<ApiResult<GetLoyaltyDetailsContent>>;\n public async getLoyaltyDetails(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<GetLoyaltyDetailsContent>>;\n public async getLoyaltyDetails(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<GetLoyaltyDetailsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<GetLoyaltyDetailsPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/loyalty\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * List all loyalty points activity for a customer\n *\n * @param pathParamsOrQuery - Optional path parameters or query parameters.\n * @param queryParams - Optional query parameters when path params are provided.\n * @returns Promise with loyalty points activity\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listLoyaltyPointsActivity();\n *\n * if (error) {\n * console.error(\"Failed to get loyalty activity:\", error);\n * return;\n * }\n *\n * console.log(\"Loyalty activity:\", data.loyalty_points_activity);\n *\n * // With pagination and sorting\n * const { data: sortedData, error: sortedError } = await sdk.customer.listLoyaltyPointsActivity({\n * page: 1,\n * limit: 20,\n * sort_by: JSON.stringify({ \"created_at\": \"desc\" })\n * });\n * ```\n */\n public async listLoyaltyPointsActivity(): Promise<\n ApiResult<ListLoyaltyActivitiesContent>\n >;\n public async listLoyaltyPointsActivity(\n queryParams: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>>;\n public async listLoyaltyPointsActivity(\n pathParams: { customer_id: string },\n queryParams?: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>>;\n public async listLoyaltyPointsActivity(\n pathParamsOrQuery?:\n | { customer_id?: string }\n | ListLoyaltyActivitiesQuery,\n queryParams?: ListLoyaltyActivitiesQuery\n ): Promise<ApiResult<ListLoyaltyActivitiesContent>> {\n const hasPathParams =\n queryParams !== undefined ||\n !!pathParamsOrQuery &&\n typeof pathParamsOrQuery === \"object\" &&\n \"customer_id\" in pathParamsOrQuery;\n\n const pathParams = hasPathParams\n ? (pathParamsOrQuery as { customer_id?: string })\n : {};\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListLoyaltyActivitiesPathParams>(\n pathParams\n );\n const resolvedQueryParams = hasPathParams\n ? queryParams\n : (pathParamsOrQuery as ListLoyaltyActivitiesQuery | undefined);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/loyalty-points-activity\", {\n params: {\n path: resolvedPathParams,\n query: resolvedQueryParams,\n },\n })\n );\n }\n\n /**\n * List all reviews left by a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with reviews\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.customer.listCustomerReviews();\n *\n * if (error) {\n * console.error(\"Failed to get customer reviews:\", error);\n * return;\n * }\n *\n * console.log(\"Customer reviews:\", data.reviews);\n * console.log(\"Ready for review:\", data.ready_for_review);\n * ```\n */\n public async listCustomerReviews(): Promise<ApiResult<ListCustomerReviewsContent>>;\n public async listCustomerReviews(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<ListCustomerReviewsContent>>;\n public async listCustomerReviews(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<ListCustomerReviewsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListCustomerReviewsPathParams>(pathParams);\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/reviews\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n\n /**\n * List all saved payment methods for a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @param queryParams - Optional query parameters for filtering.\n * @returns Promise with payment methods\n *\n * @example\n * ```typescript\n * // Uses customer_id from active session\n * const { data, error } = await sdk.customer.listSavedPaymentMethods();\n *\n * // With explicit customer_id\n * const { data: explicit } = await sdk.customer.listSavedPaymentMethods({\n * customer_id: \"customer_123\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list saved payment methods:\", error);\n * return;\n * }\n *\n * console.log(\"Saved payment methods:\", data.saved_payment_methods);\n * ```\n */\n public async listSavedPaymentMethods(): Promise<\n ApiResult<ListSavedPaymentMethodsContent>\n >;\n public async listSavedPaymentMethods(\n pathParams: { customer_id: string },\n queryParams?: ListSavedPaymentMethodsQuery\n ): Promise<ApiResult<ListSavedPaymentMethodsContent>>;\n public async listSavedPaymentMethods(\n pathParams: { customer_id?: string } = {},\n queryParams?: ListSavedPaymentMethodsQuery\n ): Promise<ApiResult<ListSavedPaymentMethodsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListSavedPaymentMethodsPathParams>(\n pathParams\n );\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/payment-methods\", {\n params: {\n path: resolvedPathParams,\n query: queryParams,\n },\n })\n );\n }\n\n /**\n * List all saved cards for a customer\n *\n * @param pathParams - Optional path parameters. When `customer_id` is omitted, the SDK resolves it from the active session.\n * @returns Promise with cards\n *\n * @example\n * ```typescript\n * // Uses customer_id from active session\n * const { data, error } = await sdk.customer.listCustomerCards();\n *\n * // With explicit customer_id\n * const { data: explicit } = await sdk.customer.listCustomerCards({\n * customer_id: \"customer_123\"\n * });\n *\n * if (error) {\n * console.error(\"Failed to list customer cards:\", error);\n * return;\n * }\n *\n * console.log(\"Customer cards:\", data.cards);\n * ```\n */\n public async listCustomerCards(): Promise<ApiResult<ListCustomerCardsContent>>;\n public async listCustomerCards(\n pathParams: { customer_id: string }\n ): Promise<ApiResult<ListCustomerCardsContent>>;\n public async listCustomerCards(\n pathParams: { customer_id?: string } = {}\n ): Promise<ApiResult<ListCustomerCardsContent>> {\n const resolvedPathParams =\n await this.resolveCustomerPathParams<ListCustomerCardsPathParams>(\n pathParams\n );\n\n return this.executeRequest(() =>\n this.client.GET(\"/customers/{customer_id}/cards\", {\n params: {\n path: resolvedPathParams,\n },\n })\n );\n }\n}\n","import type { ApiResult } from \"@commercengine/sdk-core\";\nimport type {\n CheckStoreResponse,\n GetConfigContent,\n} from \"@/types/storefront-api-types\";\nimport { StorefrontAPIClientBase } from \"@/lib/shared/client\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class BaseStoreConfigClient extends StorefrontAPIClientBase {\n /**\n * Check store existence\n *\n * @description Checks whether a store with the configured store ID exists.\n * Returns `success: true` if the store exists, `false` otherwise.\n *\n * @returns Promise with store existence check result\n * @example\n * ```typescript\n * const { data, error } = await sdk.store.checkStore();\n *\n * if (error) {\n * console.error(\"Failed to check store:\", error.message);\n * } else {\n * console.log(\"Store exists:\", data.success);\n * }\n * ```\n */\n public async checkStore(): Promise<ApiResult<CheckStoreResponse>> {\n return this.executeRequest(() => this.client.GET(\"/store/check\"));\n }\n\n /**\n * Get store config\n *\n * @returns Promise with store configuration data\n *\n * @example\n * ```typescript\n * const { data, error } = await sdk.store.getStoreConfig();\n *\n * if (error) {\n * console.error('Failed to get store config:', error.message);\n * return;\n * }\n *\n * // Access store configuration data\n * const storeConfig = data.store_config;\n * console.log('Store brand:', storeConfig.brand.name);\n * console.log('Currency:', storeConfig.currency.code);\n * console.log('KYC enabled:', storeConfig.is_kyc_enabled);\n * console.log('Customer groups enabled:', storeConfig.is_customer_group_enabled);\n * ```\n */\n public async getStoreConfig(): Promise<ApiResult<GetConfigContent>> {\n return this.executeRequest(() => this.client.GET(\"/store/config\"));\n }\n}\n","import { BaseStoreConfigClient } from \"@/lib/shared/store-config\";\nimport {\n attachPublicAuth,\n PublicStorefrontAPIClient,\n} from \"@/lib/public/client\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class PublicStoreConfigClient extends BaseStoreConfigClient {\n constructor(config: ConstructorParameters<typeof PublicStorefrontAPIClient>[0]) {\n super(config);\n attachPublicAuth(this);\n }\n}\n","import { BaseStoreConfigClient } from \"@/lib/shared/store-config\";\nimport {\n attachSessionAuth,\n SessionStorefrontAPIClient,\n} from \"@/lib/session/client\";\n\n/**\n * Client for interacting with store config endpoints\n */\nexport class StoreConfigClient extends BaseStoreConfigClient {\n constructor(\n config: ConstructorParameters<typeof SessionStorefrontAPIClient>[0]\n ) {\n super(config);\n attachSessionAuth(this, config.sessionManager);\n }\n}\n","/**\n * Token storage interface for the auth middleware\n */\nexport interface TokenStorage {\n getAccessToken(): Promise<string | null>;\n setAccessToken(token: string): Promise<void>;\n getRefreshToken(): Promise<string | null>;\n setRefreshToken(token: string): Promise<void>;\n clearTokens(): Promise<void>;\n}\n\n/**\n * Simple in-memory token storage implementation\n */\nexport class MemoryTokenStorage implements TokenStorage {\n private accessToken: string | null = null;\n private refreshToken: string | null = null;\n\n async getAccessToken(): Promise<string | null> {\n return this.accessToken;\n }\n\n async setAccessToken(token: string): Promise<void> {\n this.accessToken = token;\n }\n\n async getRefreshToken(): Promise<string | null> {\n return this.refreshToken;\n }\n\n async setRefreshToken(token: string): Promise<void> {\n this.refreshToken = token;\n }\n\n async clearTokens(): Promise<void> {\n this.accessToken = null;\n this.refreshToken = null;\n }\n}\n\n/**\n * Browser localStorage token storage implementation\n */\nexport class BrowserTokenStorage implements TokenStorage {\n private accessTokenKey: string;\n private refreshTokenKey: string;\n\n constructor(prefix: string = \"storefront_\") {\n this.accessTokenKey = `${prefix}access_token`;\n this.refreshTokenKey = `${prefix}refresh_token`;\n }\n\n async getAccessToken(): Promise<string | null> {\n if (typeof localStorage === \"undefined\") return null;\n return localStorage.getItem(this.accessTokenKey);\n }\n\n async setAccessToken(token: string): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.setItem(this.accessTokenKey, token);\n }\n }\n\n async getRefreshToken(): Promise<string | null> {\n if (typeof localStorage === \"undefined\") return null;\n return localStorage.getItem(this.refreshTokenKey);\n }\n\n async setRefreshToken(token: string): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.setItem(this.refreshTokenKey, token);\n }\n }\n\n async clearTokens(): Promise<void> {\n if (typeof localStorage !== \"undefined\") {\n localStorage.removeItem(this.accessTokenKey);\n localStorage.removeItem(this.refreshTokenKey);\n }\n }\n}\n\n/**\n * Cookie-based token storage implementation\n */\nexport class CookieTokenStorage implements TokenStorage {\n private accessTokenKey: string;\n private refreshTokenKey: string;\n private options: CookieOptions;\n\n constructor(options: CookieTokenStorageOptions = {}) {\n const prefix = options.prefix || \"storefront_\";\n this.accessTokenKey = `${prefix}access_token`;\n this.refreshTokenKey = `${prefix}refresh_token`;\n\n this.options = {\n maxAge: options.maxAge || 7 * 24 * 60 * 60, // 7 days default\n path: options.path || \"/\",\n domain: options.domain,\n secure:\n options.secure ??\n (typeof window !== \"undefined\" &&\n window.location?.protocol === \"https:\"),\n sameSite: options.sameSite || \"Lax\",\n httpOnly: false, // Must be false for client-side access\n };\n }\n\n async getAccessToken(): Promise<string | null> {\n return this.getCookie(this.accessTokenKey);\n }\n\n async setAccessToken(token: string): Promise<void> {\n this.setCookie(this.accessTokenKey, token);\n }\n\n async getRefreshToken(): Promise<string | null> {\n return this.getCookie(this.refreshTokenKey);\n }\n\n async setRefreshToken(token: string): Promise<void> {\n this.setCookie(this.refreshTokenKey, token);\n }\n\n async clearTokens(): Promise<void> {\n this.deleteCookie(this.accessTokenKey);\n this.deleteCookie(this.refreshTokenKey);\n }\n\n private getCookie(name: string): string | null {\n if (typeof document === \"undefined\") return null;\n\n const value = `; ${document.cookie}`;\n const parts = value.split(`; ${name}=`);\n\n if (parts.length === 2) {\n const cookieValue = parts.pop()?.split(\";\").shift();\n return cookieValue ? decodeURIComponent(cookieValue) : null;\n }\n\n return null;\n }\n\n private setCookie(name: string, value: string): void {\n if (typeof document === \"undefined\") return;\n\n const encodedValue = encodeURIComponent(value);\n let cookieString = `${name}=${encodedValue}`;\n\n if (this.options.maxAge) {\n cookieString += `; Max-Age=${this.options.maxAge}`;\n }\n\n if (this.options.path) {\n cookieString += `; Path=${this.options.path}`;\n }\n\n if (this.options.domain) {\n cookieString += `; Domain=${this.options.domain}`;\n }\n\n if (this.options.secure) {\n cookieString += `; Secure`;\n }\n\n if (this.options.sameSite) {\n cookieString += `; SameSite=${this.options.sameSite}`;\n }\n\n document.cookie = cookieString;\n }\n\n private deleteCookie(name: string): void {\n if (typeof document === \"undefined\") return;\n\n let cookieString = `${name}=; Max-Age=0`;\n\n if (this.options.path) {\n cookieString += `; Path=${this.options.path}`;\n }\n\n if (this.options.domain) {\n cookieString += `; Domain=${this.options.domain}`;\n }\n\n document.cookie = cookieString;\n }\n}\n\n/**\n * Configuration options for CookieTokenStorage\n */\nexport interface CookieTokenStorageOptions {\n /**\n * Prefix for cookie names (default: \"storefront_\")\n */\n prefix?: string;\n\n /**\n * Maximum age of cookies in seconds (default: 7 days)\n */\n maxAge?: number;\n\n /**\n * Cookie path (default: \"/\")\n */\n path?: string;\n\n /**\n * Cookie domain (default: current domain)\n */\n domain?: string;\n\n /**\n * Whether cookies should be secure (default: auto-detect based on protocol)\n */\n secure?: boolean;\n\n /**\n * SameSite cookie attribute (default: \"Lax\")\n */\n sameSite?: \"Strict\" | \"Lax\" | \"None\";\n}\n\n/**\n * Internal cookie options interface\n */\ninterface CookieOptions {\n maxAge?: number;\n path?: string;\n domain?: string;\n secure?: boolean;\n sameSite?: \"Strict\" | \"Lax\" | \"None\";\n httpOnly?: boolean;\n}\n","/**\n * Decode a JWT token payload without signature verification.\n * This is a lightweight replacement for jose's decodeJwt.\n *\n * @param token - The JWT token to decode\n * @returns The decoded payload\n * @throws Error if the token is malformed\n */\nfunction decodeJwt<T = Record<string, unknown>>(token: string): T {\n if (typeof token !== \"string\") {\n throw new Error(\"Invalid token: must be a string\");\n }\n\n const parts = token.split(\".\");\n if (parts.length !== 3) {\n throw new Error(\"Invalid token: must have 3 parts\");\n }\n\n const base64Url = parts[1];\n if (!base64Url) throw new Error(\"Invalid token: missing payload\");\n\n let base64 = base64Url.replace(/-/g, \"+\").replace(/_/g, \"/\");\n const padding = base64.length % 4;\n if (padding) base64 += \"=\".repeat(4 - padding);\n\n // UTF-8 safe decoding\n const binaryStr = atob(base64);\n const bytes = new Uint8Array(binaryStr.length);\n for (let i = 0; i < binaryStr.length; i++) {\n bytes[i] = binaryStr.charCodeAt(i);\n }\n\n const payload = JSON.parse(new TextDecoder().decode(bytes));\n if (typeof payload !== \"object\" || payload === null) {\n throw new Error(\"Invalid token: payload must be an object\");\n }\n\n return payload;\n}\n\n/**\n * Channel information from JWT token\n */\nexport interface Channel {\n id: string;\n name: string;\n type: string;\n}\n\n/**\n * JWT payload structure for storefront tokens\n */\nexport interface JwtPayload {\n token_type: string;\n exp: number;\n iat: number;\n jti: string;\n ulid: string;\n email: string | null;\n phone: string | null;\n username: string;\n first_name: string | null;\n last_name: string | null;\n store_id: string;\n is_logged_in: boolean;\n customer_id: string | null;\n customer_group_id: string | null;\n anonymous_id: string;\n is_anonymous: boolean;\n channel: Channel;\n}\n\n/**\n * User information extracted from JWT token\n */\nexport interface UserInfo {\n id: string;\n email: string | null;\n phone: string | null;\n username: string;\n firstName: string | null;\n lastName: string | null;\n storeId: string;\n isLoggedIn: boolean;\n isAnonymous: boolean;\n customerId: string | null;\n customerGroupId: string | null;\n anonymousId: string;\n channel: Channel;\n tokenExpiry: Date;\n tokenIssuedAt: Date;\n}\n\n/**\n * Decode and extract user information from a JWT token\n * \n * @param token - The JWT token to decode\n * @returns User information or null if token is invalid\n */\nexport function extractUserInfoFromToken(token: string): UserInfo | null {\n try {\n const payload = decodeJwt(token) as JwtPayload;\n \n return {\n id: payload.ulid,\n email: payload.email,\n phone: payload.phone,\n username: payload.username,\n firstName: payload.first_name,\n lastName: payload.last_name,\n storeId: payload.store_id,\n isLoggedIn: payload.is_logged_in,\n isAnonymous: payload.is_anonymous,\n customerId: payload.customer_id,\n customerGroupId: payload.customer_group_id,\n anonymousId: payload.anonymous_id,\n channel: payload.channel,\n tokenExpiry: new Date(payload.exp * 1000),\n tokenIssuedAt: new Date(payload.iat * 1000),\n };\n } catch (error) {\n console.warn(\"Failed to decode JWT token:\", error);\n return null;\n }\n}\n\n/**\n * Check if a JWT token is expired\n * \n * @param token - The JWT token to check\n * @param bufferSeconds - Buffer time in seconds (default: 30)\n * @returns True if token is expired or will expire within buffer time\n */\nexport function isTokenExpired(token: string, bufferSeconds: number = 30): boolean {\n try {\n const payload = decodeJwt<{ exp?: number }>(token);\n if (!payload.exp) return true;\n\n const currentTime = Math.floor(Date.now() / 1000);\n const expiryTime = payload.exp;\n \n // Consider token expired if it expires within the buffer time\n return currentTime >= (expiryTime - bufferSeconds);\n } catch (error) {\n console.warn(\"Failed to decode JWT token:\", error);\n return true; // Treat invalid tokens as expired\n }\n}\n\n/**\n * Get the user ID from a JWT token\n * \n * @param token - The JWT token\n * @returns User ID (ulid) or null if token is invalid\n */\nexport function getUserIdFromToken(token: string): string | null {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.id || null;\n}\n\n/**\n * Check if user is logged in based on JWT token\n * \n * @param token - The JWT token\n * @returns True if user is logged in, false otherwise\n */\nexport function isUserLoggedIn(token: string): boolean {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.isLoggedIn || false;\n}\n\n/**\n * Check if user is anonymous based on JWT token\n * \n * @param token - The JWT token\n * @returns True if user is anonymous, false otherwise\n */\nexport function isUserAnonymous(token: string): boolean {\n const userInfo = extractUserInfoFromToken(token);\n return userInfo?.isAnonymous ?? true;\n} \n","// Auto-generated auth operation metadata from the OpenAPI spec\n// Do not edit manually - regenerate using generate-auth-operation-metadata.py\n\nexport type StorefrontHttpMethod = \"GET\" | \"POST\" | \"PUT\" | \"DELETE\" | \"PATCH\" | \"HEAD\" | \"OPTIONS\";\n\nexport type StorefrontAuthOperation = {\n method: StorefrontHttpMethod;\n path: string;\n};\n\nexport const API_KEY_ONLY_OPERATIONS = [\n { method: \"POST\", path: \"/auth/anonymous\" },\n { method: \"GET\", path: \"/common/countries\" },\n { method: \"GET\", path: \"/common/countries/{country_iso_code}/pincodes\" },\n { method: \"GET\", path: \"/common/countries/{country_iso_code}/states\" },\n { method: \"GET\", path: \"/store/check\" },\n { method: \"GET\", path: \"/store/config\" },\n { method: \"GET\", path: \"/store/kyc-document\" },\n { method: \"GET\", path: \"/store/sellers/{id}\" },\n { method: \"GET\", path: \"/store/sellers/{id}/reviews\" },\n] as const;\n\nexport const DUAL_AUTH_OPERATIONS = [\n { method: \"GET\", path: \"/catalog/categories\" },\n { method: \"GET\", path: \"/catalog/products\" },\n { method: \"GET\", path: \"/catalog/products/cross-sell\" },\n { method: \"POST\", path: \"/catalog/products/search\" },\n { method: \"GET\", path: \"/catalog/products/similar\" },\n { method: \"GET\", path: \"/catalog/products/up-sell\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/variants\" },\n { method: \"GET\", path: \"/catalog/products/{product_id}/variants/{variant_id}\" },\n { method: \"GET\", path: \"/catalog/skus\" },\n] as const;\n\nexport const SESSION_ONLY_OPERATIONS = [\n { method: \"POST\", path: \"/analytics/track\" },\n { method: \"POST\", path: \"/auth/change-password\" },\n { method: \"POST\", path: \"/auth/forgot-password\" },\n { method: \"POST\", path: \"/auth/generate-otp\" },\n { method: \"POST\", path: \"/auth/login/email\" },\n { method: \"POST\", path: \"/auth/login/password\" },\n { method: \"POST\", path: \"/auth/login/phone\" },\n { method: \"POST\", path: \"/auth/login/whatsapp\" },\n { method: \"POST\", path: \"/auth/logout\" },\n { method: \"POST\", path: \"/auth/refresh-token\" },\n { method: \"POST\", path: \"/auth/register/email\" },\n { method: \"POST\", path: \"/auth/register/password\" },\n { method: \"POST\", path: \"/auth/register/phone\" },\n { method: \"POST\", path: \"/auth/register/whatsapp\" },\n { method: \"POST\", path: \"/auth/reset-password\" },\n { method: \"DELETE\", path: \"/auth/user/{id}\" },\n { method: \"GET\", path: \"/auth/user/{id}\" },\n { method: \"PUT\", path: \"/auth/user/{id}\" },\n { method: \"PUT\", path: \"/auth/user/{id}/deactivate\" },\n { method: \"DELETE\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"GET\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"POST\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"PUT\", path: \"/auth/user/{id}/profile-image\" },\n { method: \"POST\", path: \"/auth/verified-email-phone\" },\n { method: \"POST\", path: \"/auth/verify-otp\" },\n { method: \"POST\", path: \"/campaigns/newsletter-subscribe\" },\n { method: \"POST\", path: \"/carts\" },\n { method: \"GET\", path: \"/carts/available-coupons\" },\n { method: \"GET\", path: \"/carts/available-promotions\" },\n { method: \"POST\", path: \"/carts/fulfillment-options\" },\n { method: \"DELETE\", path: \"/carts/users/{user_id}\" },\n { method: \"GET\", path: \"/carts/users/{user_id}\" },\n { method: \"DELETE\", path: \"/carts/{id}\" },\n { method: \"GET\", path: \"/carts/{id}\" },\n { method: \"POST\", path: \"/carts/{id}/address\" },\n { method: \"DELETE\", path: \"/carts/{id}/coupon\" },\n { method: \"POST\", path: \"/carts/{id}/coupon\" },\n { method: \"DELETE\", path: \"/carts/{id}/credit-balance\" },\n { method: \"POST\", path: \"/carts/{id}/credit-balance\" },\n { method: \"GET\", path: \"/carts/{id}/evaluate-coupons\" },\n { method: \"GET\", path: \"/carts/{id}/evaluate-promotions\" },\n { method: \"POST\", path: \"/carts/{id}/fulfillment-preference\" },\n { method: \"POST\", path: \"/carts/{id}/items\" },\n { method: \"DELETE\", path: \"/carts/{id}/loyalty-points\" },\n { method: \"POST\", path: \"/carts/{id}/loyalty-points\" },\n { method: \"GET\", path: \"/catalog/marketplace/categories\" },\n { method: \"GET\", path: \"/catalog/marketplace/products\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/cross-sell\" },\n { method: \"POST\", path: \"/catalog/marketplace/products/search\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/similar\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/up-sell\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/reviews\" },\n { method: \"POST\", path: \"/catalog/marketplace/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/variants\" },\n { method: \"GET\", path: \"/catalog/marketplace/products/{product_id}/variants/{variant_id}\" },\n { method: \"GET\", path: \"/catalog/marketplace/skus\" },\n { method: \"POST\", path: \"/catalog/products/{product_id}/reviews\" },\n { method: \"GET\", path: \"/customers/{customer_id}/addresses\" },\n { method: \"POST\", path: \"/customers/{customer_id}/addresses\" },\n { method: \"DELETE\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"PUT\", path: \"/customers/{customer_id}/addresses/{address_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/cards\" },\n { method: \"GET\", path: \"/customers/{customer_id}/documents\" },\n { method: \"POST\", path: \"/customers/{customer_id}/documents\" },\n { method: \"POST\", path: \"/customers/{customer_id}/documents/verify\" },\n { method: \"DELETE\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"PUT\", path: \"/customers/{customer_id}/documents/{document_id}\" },\n { method: \"GET\", path: \"/customers/{customer_id}/loyalty\" },\n { method: \"GET\", path: \"/customers/{customer_id}/loyalty-points-activity\" },\n { method: \"GET\", path: \"/customers/{customer_id}/payment-methods\" },\n { method: \"GET\", path: \"/customers/{customer_id}/reviews\" },\n { method: \"POST\", path: \"/fulfillment/serviceability\" },\n { method: \"GET\", path: \"/orders\" },\n { method: \"POST\", path: \"/orders\" },\n { method: \"GET\", path: \"/orders/returns\" },\n { method: \"GET\", path: \"/orders/{order_number}\" },\n { method: \"POST\", path: \"/orders/{order_number}/cancel\" },\n { method: \"POST\", path: \"/orders/{order_number}/cancel-payment-request\" },\n { method: \"GET\", path: \"/orders/{order_number}/payment-status\" },\n { method: \"GET\", path: \"/orders/{order_number}/payments\" },\n { method: \"GET\", path: \"/orders/{order_number}/refunds\" },\n { method: \"POST\", path: \"/orders/{order_number}/retry-payment\" },\n { method: \"POST\", path: \"/orders/{order_number}/return\" },\n { method: \"GET\", path: \"/orders/{order_number}/return/{return_id}\" },\n { method: \"GET\", path: \"/orders/{order_number}/shipments\" },\n { method: \"POST\", path: \"/payments/authenticate-direct-otp\" },\n { method: \"GET\", path: \"/payments/card-info\" },\n { method: \"POST\", path: \"/payments/generate-hash\" },\n { method: \"POST\", path: \"/payments/juspay/create-order\" },\n { method: \"POST\", path: \"/payments/juspay/customers\" },\n { method: \"GET\", path: \"/payments/juspay/customers/{user_id}\" },\n { method: \"GET\", path: \"/payments/payment-methods\" },\n { method: \"POST\", path: \"/payments/resend-direct-otp\" },\n { method: \"GET\", path: \"/payments/verify-vpa\" },\n { method: \"GET\", path: \"/subscriptions\" },\n { method: \"POST\", path: \"/subscriptions\" },\n { method: \"GET\", path: \"/subscriptions/{id}\" },\n { method: \"PUT\", path: \"/subscriptions/{id}\" },\n { method: \"DELETE\", path: \"/wishlist/{user_id}\" },\n { method: \"GET\", path: \"/wishlist/{user_id}\" },\n { method: \"POST\", path: \"/wishlist/{user_id}\" },\n] as const;\n","import {\n API_KEY_ONLY_OPERATIONS,\n DUAL_AUTH_OPERATIONS,\n type StorefrontAuthOperation,\n} from \"@/types/auth-operation-metadata\";\n\nconst TOKEN_RETURNING_OPERATIONS = [\n { method: \"POST\", path: \"/auth/change-password\" },\n { method: \"POST\", path: \"/auth/login/password\" },\n { method: \"POST\", path: \"/auth/reset-password\" },\n { method: \"POST\", path: \"/auth/verify-otp\" },\n { method: \"POST\", path: \"/auth/refresh-token\" },\n { method: \"POST\", path: \"/auth/logout\" },\n] as const satisfies readonly StorefrontAuthOperation[];\n\nconst ANONYMOUS_AUTH_OPERATION = {\n method: \"POST\",\n path: \"/auth/anonymous\",\n} as const satisfies StorefrontAuthOperation;\n\nfunction normalizeMethod(method: string): string {\n return method.toUpperCase();\n}\n\nfunction normalizePathname(pathname: string): string {\n let normalizedPathname = pathname;\n\n const storefrontMarker = \"/storefront\";\n const storefrontMarkerIndex = normalizedPathname.indexOf(storefrontMarker);\n\n // Requests in middleware carry the full API pathname\n // (`/api/v1/{storeId}/storefront/...`), while generated auth metadata is\n // keyed by storefront-relative operation paths (`/auth/anonymous`). Strip\n // the API prefix so method+path matching stays aligned with the spec.\n if (storefrontMarkerIndex !== -1) {\n normalizedPathname =\n normalizedPathname.slice(storefrontMarkerIndex + storefrontMarker.length) ||\n \"/\";\n }\n\n if (normalizedPathname.length > 1 && normalizedPathname.endsWith(\"/\")) {\n return normalizedPathname.slice(0, -1);\n }\n\n return normalizedPathname;\n}\n\nfunction matchesPathTemplate(pathTemplate: string, pathname: string): boolean {\n const normalizedTemplate = normalizePathname(pathTemplate);\n const normalizedPathname = normalizePathname(pathname);\n\n const templateSegments = normalizedTemplate.split(\"/\").filter(Boolean);\n const pathSegments = normalizedPathname.split(\"/\").filter(Boolean);\n\n if (templateSegments.length !== pathSegments.length) {\n return false;\n }\n\n return templateSegments.every((templateSegment, index) => {\n if (\n templateSegment.startsWith(\"{\") &&\n templateSegment.endsWith(\"}\")\n ) {\n return true;\n }\n\n return templateSegment === pathSegments[index];\n });\n}\n\nfunction matchesOperation(\n method: string,\n pathname: string,\n operation: StorefrontAuthOperation\n): boolean {\n return (\n normalizeMethod(method) === operation.method &&\n matchesPathTemplate(operation.path, pathname)\n );\n}\n\nfunction matchesOperationList(\n method: string,\n pathname: string,\n operations: readonly StorefrontAuthOperation[]\n): boolean {\n return operations.some((operation) => matchesOperation(method, pathname, operation));\n}\n\n/**\n * Check if a method+path pair is the anonymous auth operation.\n */\nexport function isAnonymousAuthOperation(method: string, pathname: string): boolean {\n return matchesOperation(method, pathname, ANONYMOUS_AUTH_OPERATION);\n}\n\n/**\n * Check if a method+path pair requires API key only authentication.\n */\nexport function isApiKeyOnlyOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, API_KEY_ONLY_OPERATIONS);\n}\n\n/**\n * Check if a method+path pair supports both bearer and API key authentication.\n */\nexport function isDualAuthOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, DUAL_AUTH_OPERATIONS);\n}\n\n/**\n * Check if a method+path pair returns tokens in a successful response.\n */\nexport function isTokenReturningOperation(method: string, pathname: string): boolean {\n return matchesOperationList(method, pathname, TOKEN_RETURNING_OPERATIONS);\n}\n","import { getPathnameFromUrl } from \"@commercengine/sdk-core\";\nimport type { Middleware } from \"openapi-fetch\";\nimport {\n isAnonymousAuthOperation,\n isApiKeyOnlyOperation,\n isTokenReturningOperation,\n} from \"./auth-utils\";\nimport type { TokenStorage } from \"@/lib/storage/token-storage\";\nimport {\n extractUserInfoFromToken,\n getUserIdFromToken,\n isTokenExpired,\n isUserLoggedIn,\n type UserInfo,\n} from \"./jwt-utils\";\n\n/**\n * Public session helpers exposed as `sdk.session`.\n *\n * These methods are split into two groups:\n * - `peek*`: passive lookups that never create or refresh tokens\n * - `ensure*`: active helpers that may create or refresh tokens when automatic\n * token management is enabled. They throw when no session can be established.\n */\nexport interface StorefrontSession {\n /**\n * Read the current access token without creating a new session.\n *\n * @returns The current access token, or `null` when no token is available\n */\n peekAccessToken(): Promise<string | null>;\n\n /**\n * Read the current refresh token without creating a new session.\n *\n * @returns The current refresh token, or `null` when no token is available\n */\n peekRefreshToken(): Promise<string | null>;\n\n /**\n * Read user information from the current token without creating a new session.\n *\n * @returns Decoded user information, or `null` when no token is available\n */\n peekUserInfo(): Promise<UserInfo | null>;\n\n /**\n * Read the current user ID without creating a new session.\n *\n * @returns The current user ID, or `null` when no token is available\n */\n peekUserId(): Promise<string | null>;\n\n /**\n * Read the current customer ID without creating a new session.\n *\n * @returns The current customer ID, or `null` when no token is available\n */\n peekCustomerId(): Promise<string | null>;\n\n /**\n * Read the current customer group ID without creating a new session.\n *\n * @returns The current customer group ID, or `null` when no token is available\n */\n peekCustomerGroupId(): Promise<string | null>;\n\n /**\n * Ensure an access token is available for the current session.\n *\n * In managed mode, this may create an anonymous session or refresh an expired\n * token. In manual mode, it only returns the currently configured token.\n *\n * @returns A usable access token\n * @throws When no session can be established\n */\n ensureAccessToken(): Promise<string>;\n\n /**\n * Ensure user information is available for the current session.\n *\n * @returns Decoded user information\n * @throws When no session can be established\n */\n ensureUserInfo(): Promise<UserInfo>;\n\n /**\n * Ensure a user ID is available for the current session.\n *\n * @returns The current user ID\n * @throws When no session can be established\n */\n ensureUserId(): Promise<string>;\n\n /**\n * Ensure a customer ID is available for the current session.\n *\n * @returns The current customer ID\n * @throws When the user is anonymous or no session can be established\n */\n ensureCustomerId(): Promise<string>;\n\n /**\n * Clear all known session tokens.\n */\n clear(): Promise<void>;\n}\n\ninterface SessionManagerOptions {\n accessToken?: string;\n apiKey?: string;\n baseUrl: string;\n onTokensCleared?: () => void;\n onTokensUpdated?: (accessToken: string, refreshToken: string) => void;\n refreshToken?: string;\n tokenStorage?: TokenStorage;\n\n /**\n * Custom function to refresh tokens.\n * When provided, this is used instead of the default fetch to `/auth/refresh-token`.\n */\n refreshTokenFn?: (refreshToken: string) => Promise<{\n access_token: string;\n refresh_token: string;\n }>;\n}\n\ntype TokenPair = {\n access_token: string;\n refresh_token: string;\n};\n\n/**\n * Snapshot of the current access and refresh tokens, used by\n * {@link StorefrontSessionManager.notifyTokensUpdatedIfChanged} to detect\n * whether `setTokens()` actually changed anything before firing the callback.\n */\ntype SessionTokenState = {\n accessToken: string | null;\n refreshToken: string | null;\n};\n\n/**\n * Internal per-SDK session controller.\n *\n * A single instance is shared by all API clients created from the same\n * `SessionStorefrontSDK`. This keeps refresh locks, token assessment, and session\n * bootstrap logic coordinated in one place while preserving optional manual\n * token management when `tokenStorage` is not provided.\n */\nexport class StorefrontSessionManager implements StorefrontSession {\n private readonly tokenStorage?: TokenStorage;\n private readonly onTokensUpdated?: (accessToken: string, refreshToken: string) => void;\n private readonly onTokensCleared?: () => void;\n private readonly baseUrl: string;\n private readonly refreshTokenFn?: (refreshToken: string) => Promise<TokenPair>;\n private apiKey?: string;\n private accessToken: string | null;\n private refreshToken: string | null;\n private initializationPromise: Promise<void> | null = null;\n private refreshPromise: Promise<void> | null = null;\n private bootstrapPromise: Promise<string | null> | null = null;\n private hasAssessedTokens = false;\n\n constructor(options: SessionManagerOptions) {\n this.tokenStorage = options.tokenStorage;\n this.baseUrl = options.baseUrl;\n this.apiKey = options.apiKey;\n this.onTokensUpdated = options.onTokensUpdated;\n this.onTokensCleared = options.onTokensCleared;\n this.accessToken = options.accessToken ?? null;\n this.refreshToken = options.refreshToken ?? null;\n this.refreshTokenFn = options.refreshTokenFn;\n\n if (this.tokenStorage && this.accessToken) {\n this.initializationPromise = this.initializeManagedTokens(\n this.accessToken,\n this.refreshToken\n );\n }\n }\n\n /**\n * Update the API key used by session bootstrap and refresh flows.\n */\n public setApiKey(apiKey: string): void {\n this.apiKey = apiKey;\n }\n\n /**\n * Remove the API key used by session bootstrap and refresh flows.\n */\n public clearApiKey(): void {\n this.apiKey = undefined;\n }\n\n /**\n * Create the auth middleware used by each API client.\n *\n * The returned middleware shares the same session state and refresh locking\n * across all clients attached to a single `SessionStorefrontSDK` instance.\n */\n public createAuthMiddleware(): Middleware {\n return {\n onRequest: async ({ request }) => this.handleRequest(request),\n onResponse: async ({ request, response }) =>\n this.handleResponse(request, response),\n };\n }\n\n /**\n * Read the current authorization header without creating a new session.\n *\n * @returns A `Bearer` header value, or an empty string when no token exists\n */\n public async getAuthorizationHeader(): Promise<string> {\n const token = await this.peekAccessToken();\n return token ? `Bearer ${token}` : \"\";\n }\n\n /**\n * Persist new session tokens.\n *\n * In managed mode, tokens are written to the configured token storage. In\n * manual mode, they are stored in memory for header injection and session\n * inspection.\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n const previousTokens = await this.getCurrentTokenState();\n\n if (this.tokenStorage) {\n await this.awaitInitialization();\n await this.storeManagedTokens(accessToken, refreshToken ?? null);\n } else {\n this.accessToken = accessToken;\n\n if (refreshToken) {\n this.refreshToken = refreshToken;\n console.warn(\n \"Refresh token provided but automatic refresh is disabled because tokenStorage is not configured.\"\n );\n }\n }\n\n const nextTokens = await this.getCurrentTokenState();\n this.notifyTokensUpdatedIfChanged(previousTokens, nextTokens);\n }\n\n /**\n * Clear all session tokens managed by this controller.\n */\n public async clearTokens(): Promise<void> {\n if (this.tokenStorage) {\n await this.awaitInitialization();\n await this.tokenStorage.clearTokens();\n } else {\n this.accessToken = null;\n this.refreshToken = null;\n }\n this.onTokensCleared?.();\n }\n\n /**\n * Clear all session tokens through the public session interface.\n */\n public async clear(): Promise<void> {\n await this.clearTokens();\n }\n\n // ---------------------------------------------------------------------------\n // Passive peek methods — never create or refresh tokens\n // ---------------------------------------------------------------------------\n\n public async peekAccessToken(): Promise<string | null> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return this.tokenStorage.getAccessToken();\n }\n\n return this.accessToken;\n }\n\n public async peekRefreshToken(): Promise<string | null> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return this.tokenStorage.getRefreshToken();\n }\n\n return this.refreshToken;\n }\n\n public async peekUserInfo(): Promise<UserInfo | null> {\n const token = await this.peekAccessToken();\n if (!token) return null;\n return extractUserInfoFromToken(token);\n }\n\n public async peekUserId(): Promise<string | null> {\n const token = await this.peekAccessToken();\n if (!token) return null;\n return getUserIdFromToken(token);\n }\n\n public async peekCustomerId(): Promise<string | null> {\n const userInfo = await this.peekUserInfo();\n return userInfo?.customerId ?? null;\n }\n\n public async peekCustomerGroupId(): Promise<string | null> {\n const userInfo = await this.peekUserInfo();\n return userInfo?.customerGroupId ?? null;\n }\n\n // ---------------------------------------------------------------------------\n // Active ensure methods — may create/refresh tokens, throw on failure\n // ---------------------------------------------------------------------------\n\n public async ensureAccessToken(): Promise<string> {\n const token = await this.getOrCreateAccessToken();\n if (!token) {\n throw new Error(\n \"No session available. Configure tokenStorage + apiKey for automatic session management, or call setTokens() to set tokens manually.\"\n );\n }\n return token;\n }\n\n public async ensureUserInfo(): Promise<UserInfo> {\n const token = await this.ensureAccessToken();\n const userInfo = extractUserInfoFromToken(token);\n if (!userInfo) {\n throw new Error(\"Failed to extract user information from access token.\");\n }\n return userInfo;\n }\n\n public async ensureUserId(): Promise<string> {\n const token = await this.ensureAccessToken();\n const userId = getUserIdFromToken(token);\n if (!userId) {\n throw new Error(\"Failed to extract user ID from access token.\");\n }\n return userId;\n }\n\n public async ensureCustomerId(): Promise<string> {\n const userInfo = await this.ensureUserInfo();\n if (!userInfo.customerId) {\n throw new Error(\n \"No customer_id available. User must be logged in (not anonymous) for this operation. Pass customer_id explicitly or log in first.\"\n );\n }\n return userInfo.customerId;\n }\n\n // ---------------------------------------------------------------------------\n // Middleware handlers\n // ---------------------------------------------------------------------------\n\n private async handleRequest(request: Request): Promise<Request | Response> {\n const method = request.method;\n const pathname = getPathnameFromUrl(request.url);\n\n if (this.tokenStorage) {\n await this.assessTokenStateOnce();\n }\n\n if (isAnonymousAuthOperation(method, pathname)) {\n return this.prepareAnonymousAuthRequest(request);\n }\n\n if (isApiKeyOnlyOperation(method, pathname)) {\n this.applyApiKeyHeader(request);\n return request;\n }\n\n // Middleware uses the non-throwing variant so requests degrade\n // gracefully (server returns 401) rather than throwing before send.\n const accessToken = await this.getOrCreateAccessToken();\n if (accessToken) {\n request.headers.set(\"Authorization\", `Bearer ${accessToken}`);\n }\n\n return request;\n }\n\n private async handleResponse(\n request: Request,\n response: Response\n ): Promise<Response> {\n if (!this.tokenStorage) {\n return response;\n }\n\n const method = request.method;\n const pathname = getPathnameFromUrl(request.url);\n\n if (response.ok) {\n await this.captureTokensFromResponse(method, pathname, response);\n return response;\n }\n\n if (\n response.status === 401 &&\n !isAnonymousAuthOperation(method, pathname) &&\n !isApiKeyOnlyOperation(method, pathname)\n ) {\n const currentToken = await this.peekAccessToken();\n\n if (currentToken && isTokenExpired(currentToken, 0)) {\n try {\n await this.refreshTokens();\n\n const refreshedToken = await this.peekAccessToken();\n if (refreshedToken) {\n const retryRequest = request.clone();\n retryRequest.headers.set(\"Authorization\", `Bearer ${refreshedToken}`);\n return fetch(retryRequest);\n }\n } catch (error) {\n console.warn(\"Token refresh failed on 401 response:\", error);\n }\n }\n }\n\n return response;\n }\n\n private async prepareAnonymousAuthRequest(\n request: Request\n ): Promise<Request | Response> {\n this.applyApiKeyHeader(request);\n\n const existingToken = await this.peekAccessToken();\n\n if (\n this.tokenStorage &&\n existingToken &&\n !isTokenExpired(existingToken) &&\n isUserLoggedIn(existingToken)\n ) {\n return new Response(\n JSON.stringify({\n message: \"Cannot create anonymous session while authenticated\",\n success: false,\n code: \"USER_ALREADY_AUTHENTICATED\",\n }),\n {\n status: 400,\n headers: { \"Content-Type\": \"application/json\" },\n }\n );\n }\n\n if (existingToken) {\n request.headers.set(\"Authorization\", `Bearer ${existingToken}`);\n }\n\n return request;\n }\n\n // ---------------------------------------------------------------------------\n // Internal helpers\n // ---------------------------------------------------------------------------\n\n private applyApiKeyHeader(request: Request): void {\n if (this.apiKey) {\n request.headers.set(\"X-Api-Key\", this.apiKey);\n }\n }\n\n /**\n * Snapshot the effective token pair from storage (managed mode) or\n * in-memory fields (manual mode). Used before and after `setTokens()` to\n * detect whether the tokens actually changed.\n */\n private async getCurrentTokenState(): Promise<SessionTokenState> {\n await this.awaitInitialization();\n\n if (this.tokenStorage) {\n return {\n accessToken: await this.tokenStorage.getAccessToken(),\n refreshToken: await this.tokenStorage.getRefreshToken(),\n };\n }\n\n return {\n accessToken: this.accessToken,\n refreshToken: this.refreshToken,\n };\n }\n\n /**\n * Fire `onTokensUpdated` only when the effective token pair differs from\n * the previous snapshot. This prevents duplicate notifications when\n * `setTokens()` is called with the same values already in storage.\n */\n private notifyTokensUpdatedIfChanged(\n previousTokens: SessionTokenState,\n nextTokens: SessionTokenState\n ): void {\n if (!this.onTokensUpdated || !nextTokens.accessToken) {\n return;\n }\n\n if (\n previousTokens.accessToken === nextTokens.accessToken &&\n previousTokens.refreshToken === nextTokens.refreshToken\n ) {\n return;\n }\n\n this.onTokensUpdated(\n nextTokens.accessToken,\n nextTokens.refreshToken ?? \"\"\n );\n }\n\n /**\n * Internal token acquisition — returns null on failure instead of throwing.\n * Used by middleware so requests degrade gracefully.\n */\n private async getOrCreateAccessToken(): Promise<string | null> {\n if (!this.tokenStorage) {\n return this.peekAccessToken();\n }\n\n await this.awaitInitialization();\n await this.assessTokenStateOnce();\n\n let accessToken = await this.tokenStorage.getAccessToken();\n\n if (!accessToken) {\n accessToken = await this.bootstrapAnonymousSession();\n }\n\n if (accessToken && isTokenExpired(accessToken)) {\n try {\n await this.refreshTokens();\n accessToken = await this.tokenStorage.getAccessToken();\n } catch {\n accessToken = await this.tokenStorage.getAccessToken();\n }\n }\n\n return accessToken;\n }\n\n private async initializeManagedTokens(\n accessToken: string,\n refreshToken: string | null\n ): Promise<void> {\n try {\n await this.storeManagedTokens(accessToken, refreshToken);\n } catch (error) {\n console.warn(\"Failed to initialize tokens in storage:\", error);\n } finally {\n this.accessToken = null;\n this.refreshToken = null;\n }\n }\n\n private async awaitInitialization(): Promise<void> {\n if (this.initializationPromise) {\n await this.initializationPromise;\n this.initializationPromise = null;\n }\n }\n\n private async assessTokenStateOnce(): Promise<void> {\n if (!this.tokenStorage || this.hasAssessedTokens) {\n return;\n }\n\n this.hasAssessedTokens = true;\n\n try {\n const accessToken = await this.tokenStorage.getAccessToken();\n const refreshToken = await this.tokenStorage.getRefreshToken();\n\n if (!accessToken && refreshToken) {\n await this.tokenStorage.clearTokens();\n console.info(\"Cleaned up orphaned refresh token\");\n }\n } catch (error) {\n console.warn(\"Token state assessment failed:\", error);\n }\n }\n\n private async bootstrapAnonymousSession(): Promise<string | null> {\n if (!this.tokenStorage) {\n return null;\n }\n\n if (this.bootstrapPromise) {\n return this.bootstrapPromise;\n }\n\n this.bootstrapPromise = (async () => {\n try {\n const response = await fetch(`${this.baseUrl}/auth/anonymous`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(this.apiKey && { \"X-Api-Key\": this.apiKey }),\n },\n });\n\n if (!response.ok) {\n return null;\n }\n\n const data = await response.json();\n const tokens = data.content;\n\n if (tokens?.access_token && tokens?.refresh_token) {\n await this.storeManagedTokens(\n tokens.access_token,\n tokens.refresh_token\n );\n this.onTokensUpdated?.(tokens.access_token, tokens.refresh_token);\n console.info(\n \"Automatically created anonymous session for first API request\"\n );\n return tokens.access_token as string;\n }\n\n return null;\n } catch (error) {\n console.warn(\"Failed to automatically create anonymous tokens:\", error);\n return null;\n } finally {\n this.bootstrapPromise = null;\n }\n })();\n\n return this.bootstrapPromise;\n }\n\n private async refreshTokens(): Promise<void> {\n if (!this.tokenStorage) {\n return;\n }\n const tokenStorage = this.tokenStorage;\n\n if (this.refreshPromise) {\n return this.refreshPromise;\n }\n\n this.refreshPromise = (async () => {\n try {\n const refreshToken = await tokenStorage.getRefreshToken();\n let newTokens: TokenPair;\n\n if (refreshToken && !isTokenExpired(refreshToken)) {\n if (this.refreshTokenFn) {\n newTokens = await this.refreshTokenFn(refreshToken);\n } else {\n const response = await fetch(`${this.baseUrl}/auth/refresh-token`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({ refresh_token: refreshToken }),\n });\n\n if (!response.ok) {\n throw new Error(`Token refresh failed: ${response.status}`);\n }\n\n const data = await response.json();\n newTokens = data.content;\n }\n } else {\n const currentAccessToken = await tokenStorage.getAccessToken();\n\n if (!currentAccessToken) {\n throw new Error(\"No tokens available for refresh\");\n }\n\n const reason = refreshToken\n ? \"refresh token expired\"\n : \"no refresh token available\";\n\n const response = await fetch(`${this.baseUrl}/auth/anonymous`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(this.apiKey && { \"X-Api-Key\": this.apiKey }),\n Authorization: `Bearer ${currentAccessToken}`,\n },\n });\n\n if (!response.ok) {\n throw new Error(\n `Anonymous token fallback failed: ${response.status}`\n );\n }\n\n const data = await response.json();\n newTokens = data.content;\n\n console.info(\n `Token refreshed via anonymous fallback (${reason}) - user may need to re-authenticate for privileged operations`\n );\n }\n\n await this.storeManagedTokens(\n newTokens.access_token,\n newTokens.refresh_token\n );\n this.onTokensUpdated?.(\n newTokens.access_token,\n newTokens.refresh_token\n );\n } catch (error) {\n console.error(\"Token refresh failed:\", error);\n await this.clearTokens();\n throw error;\n } finally {\n this.refreshPromise = null;\n }\n })();\n\n return this.refreshPromise;\n }\n\n private async captureTokensFromResponse(\n method: string,\n pathname: string,\n response: Response\n ): Promise<void> {\n if (\n !this.tokenStorage ||\n !(\n isTokenReturningOperation(method, pathname) ||\n isAnonymousAuthOperation(method, pathname)\n )\n ) {\n return;\n }\n\n try {\n const data = await response.clone().json();\n const content = data.content;\n\n if (content?.access_token && content?.refresh_token) {\n await this.storeManagedTokens(content.access_token, content.refresh_token);\n this.onTokensUpdated?.(content.access_token, content.refresh_token);\n }\n } catch (error) {\n console.warn(\"Failed to extract tokens from response:\", error);\n }\n }\n\n private async storeManagedTokens(\n accessToken: string,\n refreshToken: string | null\n ): Promise<void> {\n if (!this.tokenStorage) {\n return;\n }\n\n await this.tokenStorage.setAccessToken(accessToken);\n\n if (refreshToken) {\n await this.tokenStorage.setRefreshToken(refreshToken);\n }\n }\n}\n","import { SessionStorefrontAPIClient } from \"./lib/session/client\";\nimport { Environment } from \"./lib/shared/url-utils\";\nimport { PublicCatalogClient } from \"./lib/public/catalog\";\nimport { CatalogClient } from \"./lib/catalog\";\nimport { CartClient } from \"./lib/cart\";\nimport { AuthClient } from \"./lib/auth\";\nimport { OrderClient } from \"./lib/order\";\nimport { PaymentsClient } from \"./lib/payments\";\nimport { PublicHelpersClient } from \"./lib/public/helper\";\nimport { HelpersClient } from \"./lib/helper\";\nimport { CustomerClient } from \"./lib/customer\";\nimport { PublicStoreConfigClient } from \"./lib/public/store-config\";\nimport { StoreConfigClient } from \"./lib/store-config\";\nimport {\n type TokenStorage,\n MemoryTokenStorage,\n BrowserTokenStorage,\n CookieTokenStorage,\n} from \"./lib/storage/token-storage\";\nimport {\n isUserLoggedIn,\n isUserAnonymous,\n type UserInfo,\n} from \"./lib/session/jwt-utils\";\nimport {\n StorefrontSessionManager,\n type StorefrontSession,\n} from \"./lib/session/manager\";\nimport { ResponseUtils } from \"@commercengine/sdk-core\";\nimport { buildStorefrontURL } from \"./lib/shared/url-utils\";\nimport { PublicStorefrontAPIClient } from \"./lib/public/client\";\nimport type {\n PublicStorefrontSDKOptions,\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"./lib/shared/sdk-types\";\n\n/**\n * Public SDK class for the Storefront API.\n *\n * This surface is intentionally limited to API-key-backed, public read\n * operations so it can be used safely during build and prerender flows.\n */\nexport class PublicStorefrontSDK {\n /**\n * Client for catalog-related read-only endpoints\n */\n public readonly catalog: PublicCatalogClient;\n\n /**\n * Client for helper-related endpoints\n */\n public readonly helpers: PublicHelpersClient;\n\n /**\n * Client for store config-related endpoints\n */\n public readonly store: PublicStoreConfigClient;\n\n /**\n * Centrally stored default headers for consistency\n */\n private defaultHeaders?: SupportedDefaultHeaders;\n\n constructor(options: PublicStorefrontSDKOptions) {\n this.defaultHeaders = options.defaultHeaders;\n\n const config = {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n apiKey: options.apiKey,\n timeout: options.timeout,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n };\n\n this.catalog = new PublicCatalogClient(config);\n this.helpers = new PublicHelpersClient(config);\n this.store = new PublicStoreConfigClient(config);\n }\n\n /**\n * Set the API key for all public clients\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n this.catalog.setApiKey(apiKey);\n this.helpers.setApiKey(apiKey);\n this.store.setApiKey(apiKey);\n }\n\n /**\n * Clear the API key from all public clients\n */\n public clearApiKey(): void {\n this.catalog.clearApiKey();\n this.helpers.clearApiKey();\n this.store.clearApiKey();\n }\n\n /**\n * Set default headers for all public clients\n *\n * @param headers - Default headers to set (only supported headers allowed)\n */\n public setDefaultHeaders(headers: SupportedDefaultHeaders): void {\n this.defaultHeaders = headers;\n this.catalog.setDefaultHeaders(headers);\n this.helpers.setDefaultHeaders(headers);\n this.store.setDefaultHeaders(headers);\n }\n\n /**\n * Get current default headers\n *\n * @returns Current default headers from central storage (always consistent)\n */\n public getDefaultHeaders(): SupportedDefaultHeaders | undefined {\n return this.defaultHeaders;\n }\n}\n\n/**\n * Main session-aware SDK class for the Storefront API\n */\nexport class SessionStorefrontSDK {\n /**\n * Client for catalog-related endpoints (products, categories, etc.)\n */\n public readonly catalog: CatalogClient;\n\n /**\n * Client for cart-related endpoints\n */\n public readonly cart: CartClient;\n\n /**\n * Client for authentication-related endpoints\n */\n public readonly auth: AuthClient;\n\n /**\n * Client for customer-related endpoints\n */\n public readonly customer: CustomerClient;\n\n /**\n * Client for helper-related endpoints\n */\n public readonly helpers: HelpersClient;\n\n /**\n * Client for order-related endpoints\n */\n public readonly order: OrderClient;\n\n /**\n * Client for payment-related endpoints\n */\n public readonly payments: PaymentsClient;\n\n /**\n * Client for store config-related endpoints\n */\n public readonly store: StoreConfigClient;\n\n /**\n * Centrally stored default headers for consistency\n */\n private defaultHeaders?: SupportedDefaultHeaders;\n\n /**\n * Shared session helper and coordinator for all API clients in this SDK instance.\n */\n public readonly session: StorefrontSession;\n private readonly sessionManager: StorefrontSessionManager;\n\n /**\n * Create a new SessionStorefrontSDK instance\n *\n * @param options - Configuration options for the SDK\n */\n constructor(options: SessionStorefrontSDKOptions) {\n // Store default headers centrally for consistency\n this.defaultHeaders = options.defaultHeaders;\n\n const sessionManager = new StorefrontSessionManager({\n accessToken: options.accessToken,\n apiKey: options.apiKey,\n baseUrl: buildStorefrontURL({\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n }),\n onTokensCleared: options.onTokensCleared,\n onTokensUpdated: options.onTokensUpdated,\n refreshToken: options.refreshToken,\n refreshTokenFn: options.refreshTokenFn,\n tokenStorage: options.tokenStorage,\n });\n\n this.sessionManager = sessionManager;\n this.session = sessionManager;\n\n // Convert options to internal config format\n const config = {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n accessToken: options.accessToken,\n refreshToken: options.refreshToken,\n apiKey: options.apiKey,\n timeout: options.timeout,\n tokenStorage: options.tokenStorage,\n onTokensUpdated: options.onTokensUpdated,\n onTokensCleared: options.onTokensCleared,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n sessionManager,\n };\n\n this.catalog = new CatalogClient(config);\n this.cart = new CartClient(config);\n this.auth = new AuthClient(config);\n this.customer = new CustomerClient(config);\n this.helpers = new HelpersClient(config);\n this.order = new OrderClient(config);\n this.payments = new PaymentsClient(config);\n this.store = new StoreConfigClient(config);\n }\n\n /**\n * Set authentication tokens for all clients\n *\n * @param accessToken - The access token (required)\n * @param refreshToken - The refresh token (optional)\n *\n * Behavior:\n * - If tokenStorage is provided: Stores tokens for automatic management\n * - If tokenStorage is not provided: Only stores access token for manual management\n */\n public async setTokens(\n accessToken: string,\n refreshToken?: string\n ): Promise<void> {\n await this.sessionManager.setTokens(accessToken, refreshToken);\n }\n\n /**\n * Clear all authentication tokens from all clients\n *\n * Behavior:\n * - If tokenStorage is provided: Clears both access and refresh tokens from storage\n * - If tokenStorage is not provided: Clears the manual access token\n */\n public async clearTokens(): Promise<void> {\n await this.sessionManager.clearTokens();\n }\n\n /**\n * Set the API key for all clients\n *\n * @param apiKey - The API key to set\n */\n public setApiKey(apiKey: string): void {\n this.sessionManager.setApiKey(apiKey);\n }\n\n /**\n * Clear the API key from all clients\n */\n public clearApiKey(): void {\n this.sessionManager.clearApiKey();\n }\n\n /**\n * Get the current access token if using token storage\n *\n * This is a passive lookup. It will not create or refresh a session.\n */\n public async getAccessToken(): Promise<string | null> {\n return this.session.peekAccessToken();\n }\n\n /**\n * Ensure an access token is available for the current session.\n *\n * This may create or refresh a managed session when automatic token\n * management is configured.\n *\n * @returns A usable access token\n */\n public async ensureAccessToken(): Promise<string> {\n return this.session.ensureAccessToken();\n }\n\n /**\n * Get user information from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns User information extracted from JWT token, or null if no token or invalid token\n */\n public async getUserInfo(): Promise<UserInfo | null> {\n return this.session.peekUserInfo();\n }\n\n /**\n * Get the current user ID from the access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns User ID (ulid) or null if no token or invalid token\n */\n public async getUserId(): Promise<string | null> {\n return this.session.peekUserId();\n }\n\n /**\n * Check if the current user is logged in (not anonymous)\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns True if user is logged in, false if anonymous or no token\n */\n public async isLoggedIn(): Promise<boolean> {\n const token = await this.getAccessToken();\n if (!token) return false;\n return isUserLoggedIn(token);\n }\n\n /**\n * Check if the current user is anonymous\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns True if user is anonymous or no token, false if logged in\n */\n public async isAnonymous(): Promise<boolean> {\n const token = await this.getAccessToken();\n if (!token) return true;\n return isUserAnonymous(token);\n }\n\n /**\n * Get the customer ID from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns Customer ID or null if no token, invalid token, or user has no customer ID\n */\n public async getCustomerId(): Promise<string | null> {\n return this.session.peekCustomerId();\n }\n\n /**\n * Get the customer group ID from the current access token\n *\n * This is a passive lookup. It will not create or refresh a session.\n *\n * @returns Customer group ID or null if no token, invalid token, or user has no customer group\n */\n public async getCustomerGroupId(): Promise<string | null> {\n return this.session.peekCustomerGroupId();\n }\n\n /**\n * Set default headers for all clients\n *\n * @param headers - Default headers to set (only supported headers allowed)\n */\n public setDefaultHeaders(headers: SupportedDefaultHeaders): void {\n // Update central storage first\n this.defaultHeaders = headers;\n\n // Sync to all clients using their inherited setDefaultHeaders method\n this.catalog.setDefaultHeaders(headers);\n this.cart.setDefaultHeaders(headers);\n this.auth.setDefaultHeaders(headers);\n this.customer.setDefaultHeaders(headers);\n this.helpers.setDefaultHeaders(headers);\n this.order.setDefaultHeaders(headers);\n this.payments.setDefaultHeaders(headers);\n this.store.setDefaultHeaders(headers);\n }\n\n /**\n * Get current default headers\n *\n * @returns Current default headers from central storage (always consistent)\n */\n public getDefaultHeaders(): SupportedDefaultHeaders | undefined {\n // Return from central storage for guaranteed consistency\n return this.defaultHeaders;\n }\n}\n\nexport type SessionStorefrontConfig = Omit<\n SessionStorefrontSDKOptions,\n keyof PublicStorefrontSDKOptions\n>;\n\nexport interface CreateStorefrontOptions extends PublicStorefrontSDKOptions {\n /**\n * Optional default configuration for the cached session-aware SDK returned by\n * `storefront.session()`.\n */\n session?: SessionStorefrontConfig;\n}\n\nexport interface StorefrontFactory {\n /**\n * Get the cached public storefront SDK.\n *\n * This instance is safe for public reads and never participates in session\n * bootstrap, refresh, or token persistence.\n */\n public(): PublicStorefrontSDK;\n\n /**\n * Get the cached default session-aware SDK.\n *\n * Use this when your app should operate with a stable managed or manual\n * session configuration.\n */\n session(): SessionStorefrontSDK;\n\n /**\n * Create a one-off session-aware SDK with per-call overrides.\n *\n * This is useful for stateless/token-seeded requests that should not reuse\n * the cached session client from `storefront.session()`.\n *\n * @param overrides - Per-instance session configuration overrides\n */\n session(overrides: Partial<SessionStorefrontConfig>): SessionStorefrontSDK;\n}\n\nfunction buildPublicStorefrontOptions(\n options: PublicStorefrontSDKOptions\n): PublicStorefrontSDKOptions {\n return {\n storeId: options.storeId,\n environment: options.environment,\n baseUrl: options.baseUrl,\n apiKey: options.apiKey,\n timeout: options.timeout,\n defaultHeaders: options.defaultHeaders,\n debug: options.debug,\n logger: options.logger,\n };\n}\n\nfunction buildSessionStorefrontOptions(\n options: CreateStorefrontOptions,\n overrides?: Partial<SessionStorefrontConfig>\n): SessionStorefrontSDKOptions {\n return {\n ...buildPublicStorefrontOptions(options),\n ...options.session,\n ...overrides,\n };\n}\n\n/**\n * Create a configured storefront factory with explicit public and session\n * access patterns.\n *\n * @example\n * ```typescript\n * import {\n * BrowserTokenStorage,\n * createStorefront,\n * Environment,\n * } from \"@commercengine/storefront-sdk\";\n *\n * export const storefront = createStorefront({\n * storeId: \"your-store-id\",\n * apiKey: \"your-api-key\",\n * environment: Environment.Staging,\n * session: {\n * tokenStorage: new BrowserTokenStorage(\"myapp_\"),\n * },\n * });\n *\n * const { data: products } = await storefront.public().catalog.listProducts();\n * const { data: cart } = await storefront.session().cart.getCart();\n * ```\n *\n * @param options - Shared public config plus optional default session config\n * @returns A storefront factory with explicit `public()` and `session()` accessors\n */\nexport function createStorefront(\n options: CreateStorefrontOptions\n): StorefrontFactory {\n const publicOptions = buildPublicStorefrontOptions(options);\n let publicSDK: PublicStorefrontSDK | null = null;\n let sessionSDK: SessionStorefrontSDK | null = null;\n\n const session = (\n overrides?: Partial<SessionStorefrontConfig>\n ): SessionStorefrontSDK => {\n if (overrides && Object.keys(overrides).length > 0) {\n return new SessionStorefrontSDK(\n buildSessionStorefrontOptions(options, overrides)\n );\n }\n\n if (!sessionSDK) {\n sessionSDK = new SessionStorefrontSDK(\n buildSessionStorefrontOptions(options)\n );\n }\n\n return sessionSDK;\n };\n\n return {\n public: () => {\n if (!publicSDK) {\n publicSDK = new PublicStorefrontSDK(publicOptions);\n }\n\n return publicSDK;\n },\n session: session as StorefrontFactory[\"session\"],\n };\n}\n\n// Export individual clients for advanced usage\nexport {\n PublicStorefrontAPIClient,\n SessionStorefrontAPIClient,\n PublicCatalogClient,\n AuthClient,\n CartClient,\n CatalogClient,\n CustomerClient,\n PublicHelpersClient,\n HelpersClient,\n OrderClient,\n PaymentsClient,\n PublicStoreConfigClient,\n StoreConfigClient,\n ResponseUtils,\n};\n// Export environment enum\nexport { Environment } from \"./lib/shared/url-utils\";\n// Export token storage types\nexport type { TokenStorage };\nexport { MemoryTokenStorage, BrowserTokenStorage, CookieTokenStorage };\nexport type { StorefrontSession };\nexport type {\n PublicStorefrontSDKOptions,\n SessionStorefrontSDKOptions,\n SupportedDefaultHeaders,\n} from \"./lib/shared/sdk-types\";\n\n// Export token storage options\nexport type { CookieTokenStorageOptions } from \"./lib/storage/token-storage\";\n\n// Export JWT types that are used in public API\nexport type { UserInfo, Channel } from \"./lib/session/jwt-utils\";\n\n// Export ALL types from sdk-core\nexport type * from \"@commercengine/sdk-core\";\n\n// Export API types for consumer usage\nexport type { components, operations, paths } from \"./types/storefront\";\n\nexport type * from \"./types/storefront-api-types\";\n"],"x_google_ignoreList":[0],"mappings":"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"}
|