shop-client 3.11.0 → 3.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -192,7 +192,8 @@ async function getInfoForStore(args, options) {
192
192
  walletId: shopifyWalletId,
193
193
  subDomain: myShopifySubdomain != null ? myShopifySubdomain : null
194
194
  },
195
- country: countryDetection.country
195
+ country: countryDetection.country,
196
+ currency: (countryDetection == null ? void 0 : countryDetection.currencyCode) || null
196
197
  };
197
198
  const currencyCode = countryDetection == null ? void 0 : countryDetection.currencyCode;
198
199
  return { info, currencyCode };
@@ -450,6 +450,74 @@ function createProductOperations(baseUrl, storeDomain, fetchProducts, productsDt
450
450
  console.error("Failed to create product filters:", storeDomain, error);
451
451
  throw error;
452
452
  }
453
+ },
454
+ predictiveSearch: async (query, options) => {
455
+ var _a, _b, _c, _d, _e;
456
+ if (!query || typeof query !== "string") {
457
+ throw new Error("Query is required and must be a string");
458
+ }
459
+ const limit = Math.max(1, Math.min((_a = options == null ? void 0 : options.limit) != null ? _a : 10, 10));
460
+ const unavailable = (options == null ? void 0 : options.unavailableProducts) === "show" || (options == null ? void 0 : options.unavailableProducts) === "hide" ? options.unavailableProducts : "hide";
461
+ const localeValue = (options == null ? void 0 : options.locale) && options.locale.trim() || "en";
462
+ const localePrefix = `${localeValue.replace(/^\/|\/$/g, "")}/`;
463
+ const url = `${baseUrl}${localePrefix}search/suggest.json?q=${encodeURIComponent(query)}&resources[type]=product&resources[limit]=${limit}&resources[options][unavailable_products]=${unavailable}`;
464
+ const response = await rateLimitedFetch(url, {
465
+ rateLimitClass: "search:predictive",
466
+ timeoutMs: 7e3,
467
+ retry: { maxRetries: 2, baseDelayMs: 300 }
468
+ });
469
+ let resp = response;
470
+ if (!resp.ok && (resp.status === 404 || resp.status === 417)) {
471
+ const fallbackUrl = `${baseUrl}search/suggest.json?q=${encodeURIComponent(query)}&resources[type]=product&resources[limit]=${limit}&resources[options][unavailable_products]=${unavailable}`;
472
+ resp = await rateLimitedFetch(fallbackUrl, {
473
+ rateLimitClass: "search:predictive",
474
+ timeoutMs: 7e3,
475
+ retry: { maxRetries: 2, baseDelayMs: 300 }
476
+ });
477
+ }
478
+ if (!resp.ok) {
479
+ throw new Error(`HTTP ${resp.status}: ${resp.statusText}`);
480
+ }
481
+ const data = await resp.json();
482
+ const raw = (_d = (_c = (_b = data == null ? void 0 : data.resources) == null ? void 0 : _b.results) == null ? void 0 : _c.products) != null ? _d : [];
483
+ const handles = raw.filter((p) => {
484
+ var _a2;
485
+ return Boolean((_a2 = p == null ? void 0 : p.available) != null ? _a2 : true);
486
+ }).map((p) => {
487
+ var _a2;
488
+ return String((_a2 = p == null ? void 0 : p.handle) != null ? _a2 : "");
489
+ }).filter((h) => h.length > 0).slice(0, limit);
490
+ const fetched = await Promise.all(handles.map((h) => findProduct(h)));
491
+ const results = filter(fetched, isNonNullish);
492
+ const finalProducts = (_e = maybeOverrideProductsCurrency(results, options == null ? void 0 : options.currency)) != null ? _e : [];
493
+ return finalProducts;
494
+ },
495
+ recommendations: async (productId, options) => {
496
+ var _a, _b;
497
+ if (!Number.isFinite(productId) || productId <= 0) {
498
+ throw new Error("Valid productId is required");
499
+ }
500
+ const limit = Math.max(1, Math.min((_a = options == null ? void 0 : options.limit) != null ? _a : 10, 10));
501
+ const intent = (options == null ? void 0 : options.intent) === "complementary" ? "complementary" : "related";
502
+ const localeValue = (options == null ? void 0 : options.locale) && options.locale.trim() || "en";
503
+ const localePrefix = `${localeValue.replace(/^\/|\/$/g, "")}/`;
504
+ const url = `${baseUrl}${localePrefix}recommendations/products.json?product_id=${encodeURIComponent(String(productId))}&limit=${limit}&intent=${intent}`;
505
+ const resp = await rateLimitedFetch(url, {
506
+ rateLimitClass: "products:recommendations",
507
+ timeoutMs: 7e3,
508
+ retry: { maxRetries: 2, baseDelayMs: 300 }
509
+ });
510
+ if (!resp.ok) {
511
+ if (resp.status === 404) {
512
+ return [];
513
+ }
514
+ throw new Error(`HTTP ${resp.status}: ${resp.statusText}`);
515
+ }
516
+ const data = await resp.json();
517
+ const productsArray = Array.isArray(data) ? data : Array.isArray(data == null ? void 0 : data.products) ? data.products : [];
518
+ const normalized = productsDto(productsArray) || [];
519
+ const finalProducts = (_b = maybeOverrideProductsCurrency(normalized, options == null ? void 0 : options.currency)) != null ? _b : [];
520
+ return finalProducts;
453
521
  }
454
522
  };
455
523
  return operations;
package/dist/index.d.ts CHANGED
@@ -132,6 +132,7 @@ declare class ShopClient {
132
132
  * - `jsonLdData` - Structured data from JSON-LD scripts
133
133
  * - `techProvider` - Shopify-specific information (walletId, subDomain)
134
134
  * - `country` - Country detection results with ISO 3166-1 alpha-2 codes (e.g., "US", "GB")
135
+ * - `currency` - ISO 4217 currency code inferred from store (e.g., "USD")
135
136
  *
136
137
  * @throws {Error} When the store URL is unreachable or returns an error
137
138
  *
package/dist/index.mjs CHANGED
@@ -6,11 +6,11 @@ import {
6
6
  } from "./chunk-554O5ED6.mjs";
7
7
  import {
8
8
  createProductOperations
9
- } from "./chunk-CNJRHWIK.mjs";
9
+ } from "./chunk-ZF4M6GMB.mjs";
10
10
  import {
11
11
  createStoreOperations,
12
12
  getInfoForStore
13
- } from "./chunk-EUAKMCAX.mjs";
13
+ } from "./chunk-VK5666EK.mjs";
14
14
  import {
15
15
  classifyProduct,
16
16
  determineStoreType,
@@ -656,6 +656,7 @@ var ShopClient = class {
656
656
  * - `jsonLdData` - Structured data from JSON-LD scripts
657
657
  * - `techProvider` - Shopify-specific information (walletId, subDomain)
658
658
  * - `country` - Country detection results with ISO 3166-1 alpha-2 codes (e.g., "US", "GB")
659
+ * - `currency` - ISO 4217 currency code inferred from store (e.g., "USD")
659
660
  *
660
661
  * @throws {Error} When the store URL is unreachable or returns an error
661
662
  *
@@ -55,6 +55,24 @@ interface ProductOperations {
55
55
  * Creates a filter map of variant options and their distinct values from all products.
56
56
  */
57
57
  filter(): Promise<Record<string, string[]> | null>;
58
+ /**
59
+ * Predictive product search using Shopify Ajax API.
60
+ */
61
+ predictiveSearch(query: string, options?: {
62
+ limit?: number;
63
+ locale?: string;
64
+ currency?: CurrencyCode;
65
+ unavailableProducts?: "show" | "hide" | "last";
66
+ }): Promise<Product[]>;
67
+ /**
68
+ * Product recommendations for a given product ID using Shopify Ajax API.
69
+ */
70
+ recommendations(productId: number, options?: {
71
+ limit?: number;
72
+ intent?: "related" | "complementary";
73
+ locale?: string;
74
+ currency?: CurrencyCode;
75
+ }): Promise<Product[] | null>;
58
76
  }
59
77
  /**
60
78
  * Creates product operations for a store instance
package/dist/products.mjs CHANGED
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  createProductOperations
3
- } from "./chunk-CNJRHWIK.mjs";
3
+ } from "./chunk-ZF4M6GMB.mjs";
4
4
  import "./chunk-D5MTUWFO.mjs";
5
5
  import "./chunk-U3RQRBXZ.mjs";
6
6
  export {
package/dist/store.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { J as JsonLdEntry, d as CountryDetectionResult } from './types-luPg5O08.js';
1
+ import { J as JsonLdEntry, d as CountryDetectionResult, f as CurrencyCode } from './types-luPg5O08.js';
2
2
 
3
3
  /**
4
4
  * Store operations interface for managing store-related functionality.
@@ -36,6 +36,7 @@ interface StoreInfo {
36
36
  subDomain: string | null;
37
37
  };
38
38
  country: CountryDetectionResult["country"];
39
+ currency: CurrencyCode | null;
39
40
  }
40
41
  /**
41
42
  * Creates store operations for a ShopClient instance.
package/dist/store.mjs CHANGED
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  createStoreOperations
3
- } from "./chunk-EUAKMCAX.mjs";
3
+ } from "./chunk-VK5666EK.mjs";
4
4
  import "./chunk-D5MTUWFO.mjs";
5
5
  import "./chunk-G7OCMGA6.mjs";
6
6
  import "./chunk-U3RQRBXZ.mjs";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "shop-client",
3
- "version": "3.11.0",
3
+ "version": "3.12.0",
4
4
  "type": "module",
5
5
  "main": "./dist/index.mjs",
6
6
  "module": "./dist/index.mjs",