@bikematrix/web-components 1.0.18 → 1.1.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/README.md CHANGED
@@ -1,9 +1,14 @@
1
1
  # Bike Matrix Web Components
2
2
 
3
- A web component library for integrating bike matrix compatibility checking into your e-commerce platform.
3
+ Our Mission is to transform the bicycle industry by offering a comprehensive compatibility solution to all retailers, service providers, manufacturers, and riders, by seamlessly connecting replacement parts to a specific bike.
4
+
5
+ Using the Bike Matrix Web Components allows any web application to provide its users the accurate selection of a bike from our database of over 50,000 Bikes by Brand, Model, Spec, Year and Size. The web application can then run a series of complex compatibility algorithms over the nominated EAN, UPC or Manufacturer Part Number, returning a Compatibility Result with messages for display to your users for the selected bike and component.
6
+
7
+ ![Bike Matrix Compatibility](https://raw.githubusercontent.com/bikematrix/assets/main/files/compatibility_indicator.jpg)
4
8
 
5
9
  ## Table of Contents
6
10
 
11
+ - [Introduction](#introduction)
7
12
  - [Installation](#installation)
8
13
  - [Getting Started](#getting-started)
9
14
  - [Configuration](#configuration)
@@ -17,6 +22,48 @@ A web component library for integrating bike matrix compatibility checking into
17
22
  - [Framework Integration](#framework-integration)
18
23
  - [Common Scenarios](#common-scenarios)
19
24
 
25
+ ## Introduction
26
+
27
+ Bike Matrix is a compatibility solution that answers the question, which parts fit this bike?
28
+ We provide the ability for a user to select a bike and see which parts, from your available products, are suitable replacement or upgrades by processing mechanic-led, component-level compatibility assessment on the products being viewed, searched or filtered.
29
+
30
+ The Web Components are pre-built Javascript components that can quickly be placed on your website and can provide you with the list of bikes that we have in our database and, along with images, can allow a user to easily select their bike. We have over 50,000 Bikes by Brand, Make, Model, Spec, Year and Size and are currently working to enrich the data of the remaining 100,000+ bikes in our dataset.
31
+
32
+ We have built up a comprehensive database of components such as Brake Pads, Tyres, Tubes, Brake Rotors, Wheels, Chains, Cassettes, Headsets and many more.
33
+
34
+ As part of the Onboarding process, it is important to talk to us to check that the products on your website that you would like to show compatibility for, are in our database. If the product does not exist in our database just provide us with the information we might need to get the product set up.
35
+
36
+ We use internationally recognised EAN or UPC barcodes, or the Original Manufacturer’s Part Number to identify products being assessed for compatibility. It is imperative that one of these three product identifiers is used. We use this product SKU to determine the Product Category, and therefore the compatibility logic to apply.
37
+
38
+ ![Product Result](https://raw.githubusercontent.com/bikematrix/assets/main/files/product_result.jpg)
39
+
40
+ To check if a product is compatible with a specific Bike we first need to guide the user towards finding the exact bike, via our Bike Selector using the following taxonomy: Brand, Model Family, Model Spec, Bike Spec, Year and Size.
41
+
42
+ * Brand is the Bike Brand that makes the Bike.
43
+ * Model Family refers to the high-level name of the Model within the Brand’s portfolio, such as Domane (Trek), Trance (Giant) or Scultura (Merida).
44
+ * Model Spec (sometimes referred to as Frame Spec) is the name for the different frame specifications within a Model Family. It could be that there is only AL(alloy), or perhaps there is Alloy and Carbon or it could be AL, CF, CF SL and CF SLX (eg Canyon).
45
+ * Bike Spec is the ‘spec level’ of each specific Models and can take many forms and include groupset names. It usually contains a number such as 3, 2, 1, and 0 or 200, 400, 500 or it can have Comp, Expert, Pro labels depending on the Brand and Model Family.
46
+ * Year is an obvious one, but the selection of year can change the list of Bike Spec or Model Spec that were available for a given Model Family.
47
+ * Size will depend on the bike brand model and year and can take several forms, S, M, L in some cases, 15”, 16”, 17” in others. Sometimes it’s Short and Long, or S1, S2, S3, S4 (eg Specialized) and for kids bikes we tend to refer to the wheelsize.
48
+
49
+ ![Bike Selector](https://raw.githubusercontent.com/bikematrix/assets/main/files/bike_selector.jpg)
50
+
51
+ We’ve put considerable effort into designing a Bike Selector that we think guides the user to the correct bike in an easy to understand manner. Unfortunately, some bikes are just confusing, and some customers don’t immediately know which bike they have.
52
+
53
+ ![Bike Selector](https://raw.githubusercontent.com/bikematrix/assets/main/files/bike_selector2.jpg)
54
+
55
+ The other consideration that is very important to us is our Brand Representation. A condition of signing a licence to use Bike Matrix APIs, is the requirement to incorporate our Compatibility Indicators and the “Powered by Bike Matrix” link.
56
+
57
+ The Compatibility Indicators are the graphic representations of Green (Compatible), Amber (Compatible with Conditions) and Red (Not Compatible) on both the Collection or Product Landing Page (PLP), and also on the Product Details Page (PDP). Again, these are all built into the Bike Matrix Web Components.
58
+
59
+ By standardising the look and feel of the compatibility results across all websites, trust is built and confidence is increased, which results in increased conversions. This is also why we recommend locating the Compatibility Indicators close to the Buy Now or Add to Cart buttons, as it will form an important part of the buying journey.
60
+
61
+ ![Compatibility Indicators](https://raw.githubusercontent.com/bikematrix/assets/main/files/compatibility_indicators.jpg)
62
+
63
+ ## Obtaining API Credentials
64
+
65
+ The Web Components require access to the Bike Matrix API. To request access to the Bike Matrix API send us an email at adamb@bikematrix.io and we will create your subscription and provide you with access to our staging APIs allowing you to explore and test functionality. When you’re ready, we can activate your licence and provide access to the entire bike database through the Production API. Depending on your deployment scenario we will provide an API Key or we will add your environments information to our whitelist.
66
+
20
67
  ## Installation
21
68
 
22
69
  You can install Bike Matrix Web Components using either npm or by including it directly via CDN.
@@ -40,10 +87,12 @@ Alternatively, include the script directly in your HTML:
40
87
  ```html
41
88
  <script
42
89
  type="text/javascript"
43
- src="https://cdn.jsdelivr.net/npm/@bikematrix/web-components/dist/bm_core.js"
90
+ src="https://cdn.jsdelivr.net/npm/@bikematrix/web-components@1.1/dist/bm_core.js"
44
91
  ></script>
45
92
  ```
46
93
 
94
+ Note: Replace version `1.1` in the above URL with the latest version number, or the specific version you want to use.
95
+
47
96
  ## Getting Started
48
97
 
49
98
  Follow these steps to quickly integrate BikeMatrix into your website:
@@ -71,10 +120,12 @@ Include the script directly in your HTML:
71
120
  ```html
72
121
  <script
73
122
  type="text/javascript"
74
- src="https://cdn.jsdelivr.net/npm/@bikematrix/web-components/dist/bm_core.js"
123
+ src="https://cdn.jsdelivr.net/npm/@bikematrix/web-components@1.1/dist/bm_core.js"
75
124
  ></script>
76
125
  ```
77
126
 
127
+ Note: Replace version `1.1` in the above URL with the latest version number, or the specific version you want to use.
128
+
78
129
  ### 2. Configure BikeMatrix
79
130
 
80
131
  Add the core configuration block to your HTML:
@@ -1236,9 +1236,9 @@ function Ga(t) {
1236
1236
  return de(t);
1237
1237
  }, []);
1238
1238
  }
1239
- const Gt = de(!1), M = de(null), De = de([]), re = de(!1), Ee = de([]), oe = de(!1), Ka = () => {
1239
+ const Gt = de(!1), M = de(null), Se = de([]), re = de(!1), Ee = de([]), oe = de(!1), Ka = () => {
1240
1240
  Ma(() => {
1241
- M.value = null, De.value = [], re.value = !1, Ee.value = [], oe.value = !1;
1241
+ M.value = null, Se.value = [], re.value = !1, Ee.value = [], oe.value = !1;
1242
1242
  });
1243
1243
  }, zo = "bm_currentBike", Ja = "v2", Ya = "https://cdn.bikematrix.io", Pr = {
1244
1244
  // Shopify specific
@@ -3746,7 +3746,10 @@ class St {
3746
3746
  body: JSON.stringify(r),
3747
3747
  method: "POST",
3748
3748
  headers: {
3749
- "Content-Type": "application/json"
3749
+ "Content-Type": "application/json",
3750
+ ...this._apiKey && {
3751
+ "bm-subscription-key": this._apiKey
3752
+ }
3750
3753
  },
3751
3754
  ...a
3752
3755
  });
@@ -3932,7 +3935,7 @@ const Io = class Me {
3932
3935
  this.currentBike === null ? (e = window.bm_selectBikeButton) == null || e.classList.remove("show-selected") : (r = window.bm_selectBikeButton) == null || r.classList.add("show-selected");
3933
3936
  }
3934
3937
  ChangeBike() {
3935
- this.config.logLevel === "verbose" && console.log("ChangeBike() Method Called"), !(re.value === !0 || oe.value === !0) && (re.value = !0, oe.value = !0, De.value = [], Ee.value = [], console.log("ChangeBike updateBikeSignal..."), this.updateBikeSignal().then(() => {
3938
+ this.config.logLevel === "verbose" && console.log("ChangeBike() Method Called"), !(re.value === !0 || oe.value === !0) && (re.value = !0, oe.value = !0, Se.value = [], Ee.value = [], console.log("ChangeBike updateBikeSignal..."), this.updateBikeSignal().then(() => {
3936
3939
  this.config.logLevel === "verbose" && console.log("Bike Signal Updated: ", JSON.stringify(M.value, null, 2)), this.ResetSelectedBikeIndicator(), this.RefreshCompatibleSkus().then(() => {
3937
3940
  document.dispatchEvent(new Event("RefreshCompatibility", {
3938
3941
  bubbles: !0,
@@ -3977,7 +3980,7 @@ const Io = class Me {
3977
3980
  var a, i;
3978
3981
  var r = JSON.parse(sessionStorage.getItem(e));
3979
3982
  if (r)
3980
- this.config.logLevel === "verbose" && console.log("Refresh Collection SKUs from Session: ", JSON.stringify(r), null, 2), De.value = r;
3983
+ this.config.logLevel === "verbose" && console.log("Refresh Collection SKUs from Session: ", JSON.stringify(r), null, 2), Se.value = r;
3981
3984
  else {
3982
3985
  const n = Object.values(this.config.products || {}).map((p) => p.skus).flat();
3983
3986
  this.config.logLevel === "verbose" && console.log("Refresh Collection SKUs from API. SKUs: ", JSON.stringify(n), null, 2);
@@ -3994,7 +3997,7 @@ const Io = class Me {
3994
3997
  console.log("function RefreshCompatibleSkus() operation aborted");
3995
3998
  return;
3996
3999
  }
3997
- sessionStorage.setItem(e, JSON.stringify(p)), De.value = p;
4000
+ sessionStorage.setItem(e, JSON.stringify(p)), Se.value = p;
3998
4001
  } catch (p) {
3999
4002
  p.name === "AbortError" ? console.log("function RefreshCompatibleSkus() fetch aborted") : console.error("function RefreshCompatibleSkus() fetch error", p);
4000
4003
  } finally {
@@ -5332,7 +5335,7 @@ function Ko({
5332
5335
  })]
5333
5336
  }) : d(q, {});
5334
5337
  }
5335
- const Se = {
5338
+ const Be = {
5336
5339
  unavailable: {
5337
5340
  heading: ""
5338
5341
  },
@@ -5354,7 +5357,7 @@ const Yi = async (t, e, r) => {
5354
5357
  if (!r || !Ee.value) {
5355
5358
  ie = {
5356
5359
  type: "unavailable",
5357
- ...Se.unavailable
5360
+ ...Be.unavailable
5358
5361
  };
5359
5362
  return;
5360
5363
  }
@@ -5367,16 +5370,16 @@ const Yi = async (t, e, r) => {
5367
5370
  const a = o.every((s) => (s == null ? void 0 : s.compatible) === !1), i = o.some((s) => (s == null ? void 0 : s.compatible) === !0 && s.warning === !0), n = o.some((s) => (s == null ? void 0 : s.compatible) === !0);
5368
5371
  o.some((s) => (s == null ? void 0 : s.compatible) === null), i ? ie = {
5369
5372
  type: "warning",
5370
- ...Se.warning
5373
+ ...Be.warning
5371
5374
  } : n ? ie = {
5372
5375
  type: "compatible",
5373
- ...Se.compatible
5376
+ ...Be.compatible
5374
5377
  } : a ? ie = {
5375
5378
  type: "incompatible",
5376
- ...Se.incompatible
5379
+ ...Be.incompatible
5377
5380
  } : ie = {
5378
5381
  type: "unavailable",
5379
- ...Se.unavailable
5382
+ ...Be.unavailable
5380
5383
  };
5381
5384
  }, Wi = function(t, e, r, o, a, i, n) {
5382
5385
  var u;
@@ -5400,7 +5403,7 @@ function Zi({
5400
5403
  const a = window.BikeMatrix, i = a.getConfig(), [n, s] = Q(!1), u = !!a.getActiveSubscription();
5401
5404
  ie = {
5402
5405
  type: "unavailable",
5403
- ...Se.unavailable
5406
+ ...Be.unavailable
5404
5407
  };
5405
5408
  const {
5406
5409
  currentCollectionHandle: l,
@@ -5659,15 +5662,14 @@ function nn({
5659
5662
  i(!1);
5660
5663
  return;
5661
5664
  }
5662
- console.log("CompatibleCollectionSkusSignal.value", De.value);
5663
- const B = rn(De.value).map(x);
5665
+ const B = rn(Se.value).map(x);
5664
5666
  c(B);
5665
5667
  const z = on(y, B);
5666
5668
  l(z), i(!0);
5667
5669
  }, [
5668
5670
  _,
5669
5671
  M.value,
5670
- De.value,
5672
+ Se.value,
5671
5673
  re.value,
5672
5674
  // compatibleProducts,
5673
5675
  y
@@ -5997,7 +5999,7 @@ const Ue = () => {
5997
5999
  for (const o in e)
5998
6000
  o !== "__proto__" && o !== "constructor" && (o in t ? typeof t[o] == "string" || t[o] instanceof String || typeof e[o] == "string" || e[o] instanceof String ? r && (t[o] = e[o]) : Yo(t[o], e[o], r) : t[o] = e[o]);
5999
6001
  return t;
6000
- }, Ae = (t) => t.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
6002
+ }, De = (t) => t.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
6001
6003
  var hn = {
6002
6004
  "&": "&amp;",
6003
6005
  "<": "&lt;",
@@ -6695,7 +6697,7 @@ class Bn {
6695
6697
  maxReplaces: k,
6696
6698
  alwaysFormat: b
6697
6699
  } = e.interpolation;
6698
- this.escape = r !== void 0 ? r : bn, this.escapeValue = o !== void 0 ? o : !0, this.useRawValueToEscape = a !== void 0 ? a : !1, this.prefix = i ? Ae(i) : n || "{{", this.suffix = s ? Ae(s) : u || "}}", this.formatSeparator = l || ",", this.unescapePrefix = p ? "" : c || "-", this.unescapeSuffix = this.unescapePrefix ? "" : p || "", this.nestingPrefix = g ? Ae(g) : f || Ae("$t("), this.nestingSuffix = _ ? Ae(_) : m || Ae(")"), this.nestingOptionsSeparator = y || ",", this.maxReplaces = k || 1e3, this.alwaysFormat = b !== void 0 ? b : !1, this.resetRegExp();
6700
+ this.escape = r !== void 0 ? r : bn, this.escapeValue = o !== void 0 ? o : !0, this.useRawValueToEscape = a !== void 0 ? a : !1, this.prefix = i ? De(i) : n || "{{", this.suffix = s ? De(s) : u || "}}", this.formatSeparator = l || ",", this.unescapePrefix = p ? "" : c || "-", this.unescapeSuffix = this.unescapePrefix ? "" : p || "", this.nestingPrefix = g ? De(g) : f || De("$t("), this.nestingSuffix = _ ? De(_) : m || De(")"), this.nestingOptionsSeparator = y || ",", this.maxReplaces = k || 1e3, this.alwaysFormat = b !== void 0 ? b : !1, this.resetRegExp();
6699
6701
  }
6700
6702
  reset() {
6701
6703
  this.options && this.init(this.options);
@@ -6811,7 +6813,7 @@ const Sn = (t) => {
6811
6813
  formatName: e,
6812
6814
  formatOptions: r
6813
6815
  };
6814
- }, Be = (t) => {
6816
+ }, Ae = (t) => {
6815
6817
  const e = {};
6816
6818
  return (r, o, a) => {
6817
6819
  let i = a;
@@ -6828,32 +6830,32 @@ class En {
6828
6830
  constructor() {
6829
6831
  let e = arguments.length > 0 && arguments[0] !== void 0 ? arguments[0] : {};
6830
6832
  this.logger = ue.create("formatter"), this.options = e, this.formats = {
6831
- number: Be((r, o) => {
6833
+ number: Ae((r, o) => {
6832
6834
  const a = new Intl.NumberFormat(r, {
6833
6835
  ...o
6834
6836
  });
6835
6837
  return (i) => a.format(i);
6836
6838
  }),
6837
- currency: Be((r, o) => {
6839
+ currency: Ae((r, o) => {
6838
6840
  const a = new Intl.NumberFormat(r, {
6839
6841
  ...o,
6840
6842
  style: "currency"
6841
6843
  });
6842
6844
  return (i) => a.format(i);
6843
6845
  }),
6844
- datetime: Be((r, o) => {
6846
+ datetime: Ae((r, o) => {
6845
6847
  const a = new Intl.DateTimeFormat(r, {
6846
6848
  ...o
6847
6849
  });
6848
6850
  return (i) => a.format(i);
6849
6851
  }),
6850
- relativetime: Be((r, o) => {
6852
+ relativetime: Ae((r, o) => {
6851
6853
  const a = new Intl.RelativeTimeFormat(r, {
6852
6854
  ...o
6853
6855
  });
6854
6856
  return (i) => a.format(i, o.range || "day");
6855
6857
  }),
6856
- list: Be((r, o) => {
6858
+ list: Ae((r, o) => {
6857
6859
  const a = new Intl.ListFormat(r, {
6858
6860
  ...o
6859
6861
  });
@@ -6871,7 +6873,7 @@ class En {
6871
6873
  this.formats[e.toLowerCase().trim()] = r;
6872
6874
  }
6873
6875
  addCached(e, r) {
6874
- this.formats[e.toLowerCase().trim()] = Be(r);
6876
+ this.formats[e.toLowerCase().trim()] = Ae(r);
6875
6877
  }
6876
6878
  format(e, r, o) {
6877
6879
  let a = arguments.length > 3 && arguments[3] !== void 0 ? arguments[3] : {};