universal-parcel-scraper 0.132.0-main.1109 → 0.133.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.
Files changed (90) hide show
  1. package/README.md +2 -2
  2. package/data/catalog.json +50 -9
  3. package/data/coverage-summary.json +1 -1
  4. package/data/detection-golden.json +14 -7
  5. package/dist/browser/scraper.js +105 -56
  6. package/dist/carriers/apc-overnight/parser.js +2 -1
  7. package/dist/carriers/asendia/probe.js +2 -1
  8. package/dist/carriers/cdek/parser.js +3 -2
  9. package/dist/carriers/correos-de-mexico/parser.js +2 -1
  10. package/dist/carriers/cyprus-post/parser.js +2 -1
  11. package/dist/carriers/dai-post/parser.js +2 -1
  12. package/dist/carriers/dao/parser.js +3 -2
  13. package/dist/carriers/day-ross/adapter.d.ts +8 -0
  14. package/dist/carriers/day-ross/adapter.js +86 -0
  15. package/dist/carriers/day-ross/carrier.json +42 -8
  16. package/dist/carriers/day-ross/parser.d.ts +8 -0
  17. package/dist/carriers/day-ross/parser.js +85 -0
  18. package/dist/carriers/day-ross/status.d.ts +2 -0
  19. package/dist/carriers/day-ross/status.js +6 -0
  20. package/dist/carriers/day-ross/statuses.json +97 -1
  21. package/dist/carriers/dhl-ecommerce-pl/adapter.js +61 -39
  22. package/dist/carriers/dhl-ecommerce-pl/carrier.json +2 -1
  23. package/dist/carriers/dsv/parser.js +5 -4
  24. package/dist/carriers/dynalogic/parser.js +2 -1
  25. package/dist/carriers/express-one/parser.js +2 -1
  26. package/dist/carriers/fan-courier/parser.js +3 -2
  27. package/dist/carriers/foxpost/parser.js +2 -1
  28. package/dist/carriers/gebrueder-weiss/parser.js +2 -1
  29. package/dist/carriers/gls-it/parser.js +2 -1
  30. package/dist/carriers/go-express/parser.js +2 -1
  31. package/dist/carriers/hrvatska-posta/parser.js +2 -1
  32. package/dist/carriers/instabox/adapter.d.ts +8 -0
  33. package/dist/carriers/instabox/adapter.js +77 -0
  34. package/dist/carriers/instabox/carrier.json +49 -8
  35. package/dist/carriers/instabox/parser.d.ts +7 -0
  36. package/dist/carriers/instabox/parser.js +127 -0
  37. package/dist/carriers/instabox/status.d.ts +2 -0
  38. package/dist/carriers/instabox/status.js +14 -0
  39. package/dist/carriers/instabox/statuses.json +44 -1
  40. package/dist/carriers/japan-post/adapter.js +2 -1
  41. package/dist/carriers/jd-logistics/parser.js +2 -1
  42. package/dist/carriers/kuehne-nagel/parser.js +3 -2
  43. package/dist/carriers/landmark-global/parser.js +2 -1
  44. package/dist/carriers/maltapost/parser.js +2 -1
  45. package/dist/carriers/matkahuolto/parser.js +2 -1
  46. package/dist/carriers/meest/parser.js +3 -2
  47. package/dist/carriers/nova-poshta/parser.js +2 -1
  48. package/dist/carriers/parcelforce/carrier.json +3 -1
  49. package/dist/carriers/passport/parser.js +2 -1
  50. package/dist/carriers/saia/adapter.d.ts +23 -0
  51. package/dist/carriers/saia/adapter.js +151 -0
  52. package/dist/carriers/saia/carrier.json +72 -8
  53. package/dist/carriers/saia/parser.d.ts +26 -0
  54. package/dist/carriers/saia/parser.js +190 -0
  55. package/dist/carriers/saia/status.d.ts +12 -0
  56. package/dist/carriers/saia/status.js +72 -0
  57. package/dist/carriers/saia/statuses.json +20 -1
  58. package/dist/carriers/speedy/parser.js +2 -1
  59. package/dist/carriers/wanbexpress/adapter.d.ts +11 -0
  60. package/dist/carriers/wanbexpress/adapter.js +84 -0
  61. package/dist/carriers/wanbexpress/carrier.json +43 -7
  62. package/dist/carriers/wanbexpress/parser.d.ts +7 -0
  63. package/dist/carriers/wanbexpress/parser.js +71 -0
  64. package/dist/carriers/wanbexpress/status.d.ts +2 -0
  65. package/dist/carriers/wanbexpress/status.js +10 -0
  66. package/dist/carriers/wanbexpress/statuses.json +96 -1
  67. package/dist/carriers/xdp/parser.js +2 -1
  68. package/dist/carriers/xpo-ltl/adapter.d.ts +2 -0
  69. package/dist/carriers/xpo-ltl/adapter.js +21 -7
  70. package/dist/carriers/xpo-ltl/browser.d.ts +5 -0
  71. package/dist/carriers/xpo-ltl/browser.js +119 -0
  72. package/dist/carriers/xpo-ltl/carrier.json +10 -5
  73. package/dist/carriers/yto/parser.js +3 -2
  74. package/dist/carriers/yunda/parser.js +2 -1
  75. package/dist/core/catalog/inputs.js +4 -0
  76. package/dist/core/catalog/statusMaps.js +8 -4
  77. package/dist/core/catalog/types.d.ts +1 -1
  78. package/dist/core/catalog/urls.d.ts +2 -0
  79. package/dist/core/catalog/urls.js +31 -0
  80. package/dist/core/detection/returned.d.ts +2 -0
  81. package/dist/core/detection/returned.js +7 -0
  82. package/dist/data/catalog.json +50 -9
  83. package/dist/generated/catalog.d.ts +37 -9
  84. package/dist/generated/catalog.js +50 -9
  85. package/dist/generated/recognition.js +3 -0
  86. package/dist/generated/registry.js +12 -4
  87. package/dist/index.d.ts +1 -1
  88. package/dist/index.js +1 -1
  89. package/dist/server/openapi.json +1 -1
  90. package/package.json +1 -1
package/README.md CHANGED
@@ -13,7 +13,7 @@ The engine behind [Peek](https://peektracker.com) ([GitHub](https://github.com/p
13
13
  [![License: Apache-2.0](https://img.shields.io/badge/core-Apache--2.0-blue.svg)](LICENSE)
14
14
 
15
15
  <!-- GENERATED:summary -->
16
- **3,500+ carriers** through **193 dedicated adapters** and **5 universal fallbacks**
16
+ **3,500+ carriers** through **197 dedicated adapters** and **5 universal fallbacks**
17
17
 
18
18
  <sub>210 catalog entries · 66 countries represented</sub>
19
19
  <!-- /GENERATED:summary -->
@@ -155,7 +155,7 @@ createTracker({ providers: ['ParcelsApp', 'Ship24', '17TRACK', 'Postal Ninja', '
155
155
  <!-- GENERATED:stages -->
156
156
  <img src="docs/assets/stages.svg" alt="DHL: Die Sendung wurde in das Zustellfahrzeug geladen.; Mondial Relay: En cours de livraison; Correios Brazil: Objeto saiu para entrega ao destinatário; Correos Express: EN REPARTO; Yamato Transport: 配達中; La Poste / Colissimo: DISTOU. All are filed under out_for_delivery." width="760">
157
157
 
158
- The carrier folders record 5,803 such statuses, each filed under one stage.
158
+ The carrier folders record 5,854 such statuses, each filed under one stage.
159
159
  <!-- /GENERATED:stages -->
160
160
 
161
161
  Wording nobody recorded yet goes through a classifier that reads seven European languages.
package/data/catalog.json CHANGED
@@ -2024,6 +2024,9 @@
2024
2024
  "parcelforce": {
2025
2025
  "displayName": "Parcelforce Worldwide",
2026
2026
  "color": "#9d0f11",
2027
+ "aliases": [
2028
+ "Parcelforce"
2029
+ ],
2027
2030
  "countries": [
2028
2031
  "GB"
2029
2032
  ],
@@ -5465,9 +5468,12 @@
5465
5468
  "timezone": "America/Moncton",
5466
5469
  "tracking": {
5467
5470
  "mode": "automatic",
5468
- "adapter": "universal"
5471
+ "adapter": "day-ross",
5472
+ "recognitionRank": 38,
5473
+ "localClocks": true
5469
5474
  },
5470
- "canaryUrl": "https://dayross.com/",
5475
+ "canaryUrl": "https://dayross.com/track-shipments",
5476
+ "trackingSearchUrl": "https://dayross.com/track-shipments",
5471
5477
  "linkRules": [],
5472
5478
  "detectionRules": [
5473
5479
  {
@@ -6988,11 +6994,31 @@
6988
6994
  "timezone": "Europe/Stockholm",
6989
6995
  "tracking": {
6990
6996
  "mode": "automatic",
6991
- "adapter": "universal"
6997
+ "adapter": "instabox",
6998
+ "requirements": [
6999
+ {
7000
+ "field": "trackingUrl",
7001
+ "validator": "instaboxCapabilityUrl",
7002
+ "optional": true,
7003
+ "label": "Instabox notification URL",
7004
+ "type": "url",
7005
+ "placeholder": "https://track.instabox.com/…",
7006
+ "help": "The complete notification link opens your parcel history. Without it, other sources are asked."
7007
+ }
7008
+ ]
6992
7009
  },
6993
- "canaryUrl": "https://track.instabox.com/en",
7010
+ "canaryUrl": "https://track.instabox.com/",
6994
7011
  "trackingSearchUrl": "https://track.instabox.com/en",
6995
- "linkRules": [],
7012
+ "linkRules": [
7013
+ {
7014
+ "domains": [
7015
+ "track.instabox.com"
7016
+ ],
7017
+ "pathPattern": "^/[a-z]{2}(?:-[A-Z]{2})?/[A-Za-z0-9]{4,40}(?:/locker-to-locker-recipient)?/?$",
7018
+ "path": "^/[a-z]{2}(?:-[A-Z]{2})?/([A-Za-z0-9]{4,40})(?:/locker-to-locker-recipient)?/?$",
7019
+ "keepsCapabilityUrl": true
7020
+ }
7021
+ ],
6996
7022
  "detectionRules": []
6997
7023
  },
6998
7024
  "intelcom": {
@@ -8243,10 +8269,12 @@
8243
8269
  "timezone": "America/New_York",
8244
8270
  "tracking": {
8245
8271
  "mode": "automatic",
8246
- "adapter": "universal"
8272
+ "adapter": "saia",
8273
+ "recognitionRank": 12,
8274
+ "localClocks": true
8247
8275
  },
8248
8276
  "canaryUrl": "https://www.saia.com/track",
8249
- "trackingUrlTemplate": "https://www.saia.com/track?pro={trackingNumber}",
8277
+ "trackingUrlTemplate": "https://www.saia.com/track/details;pro={trackingNumber}",
8250
8278
  "trackingSearchUrl": "https://www.saia.com/track",
8251
8279
  "linkRules": [
8252
8280
  {
@@ -8257,6 +8285,16 @@
8257
8285
  "params": [
8258
8286
  "pro"
8259
8287
  ]
8288
+ },
8289
+ {
8290
+ "domains": [
8291
+ "saia.com"
8292
+ ],
8293
+ "pathPattern": "^/track/details(?:/|;|$)",
8294
+ "path": "^/track/details;pro=(\\d+)",
8295
+ "params": [
8296
+ "pro"
8297
+ ]
8260
8298
  }
8261
8299
  ],
8262
8300
  "detectionRules": []
@@ -8728,9 +8766,11 @@
8728
8766
  "timezone": "Asia/Shanghai",
8729
8767
  "tracking": {
8730
8768
  "mode": "automatic",
8731
- "adapter": "universal"
8769
+ "adapter": "wanbexpress",
8770
+ "recognitionRank": 33,
8771
+ "browserRecognitionRank": 33
8732
8772
  },
8733
- "canaryUrl": "https://www.wanbexpress.com/",
8773
+ "canaryUrl": "https://tracking.wanbexpress.com/",
8734
8774
  "linkRules": [],
8735
8775
  "detectionRules": [
8736
8776
  {
@@ -8856,6 +8896,7 @@
8856
8896
  "mode": "automatic",
8857
8897
  "adapter": "xpo-ltl",
8858
8898
  "recognitionRank": 25,
8899
+ "browserRecognitionRank": 25,
8859
8900
  "localClocks": true
8860
8901
  },
8861
8902
  "canaryUrl": "https://www.xpo.com/",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "catalog": 210,
3
- "activeAdapters": 193,
3
+ "activeAdapters": 197,
4
4
  "countries": 66,
5
5
  "referenceCarriers": 100,
6
6
  "comparison": {
@@ -33006,7 +33006,8 @@
33006
33006
  "day-ross"
33007
33007
  ],
33008
33008
  "asked": [
33009
- "australia-post"
33009
+ "australia-post",
33010
+ "day-ross"
33010
33011
  ]
33011
33012
  },
33012
33013
  {
@@ -33037,7 +33038,8 @@
33037
33038
  "day-ross"
33038
33039
  ],
33039
33040
  "asked": [
33040
- "australia-post"
33041
+ "australia-post",
33042
+ "day-ross"
33041
33043
  ]
33042
33044
  },
33043
33045
  {
@@ -35872,7 +35874,8 @@
35872
35874
  "day-ross"
35873
35875
  ],
35874
35876
  "asked": [
35875
- "australia-post"
35877
+ "australia-post",
35878
+ "day-ross"
35876
35879
  ]
35877
35880
  },
35878
35881
  {
@@ -35884,7 +35887,8 @@
35884
35887
  "day-ross"
35885
35888
  ],
35886
35889
  "asked": [
35887
- "australia-post"
35890
+ "australia-post",
35891
+ "day-ross"
35888
35892
  ]
35889
35893
  },
35890
35894
  {
@@ -35896,7 +35900,8 @@
35896
35900
  "day-ross"
35897
35901
  ],
35898
35902
  "asked": [
35899
- "australia-post"
35903
+ "australia-post",
35904
+ "day-ross"
35900
35905
  ]
35901
35906
  },
35902
35907
  {
@@ -37615,7 +37620,8 @@
37615
37620
  "day-ross"
37616
37621
  ],
37617
37622
  "asked": [
37618
- "australia-post"
37623
+ "australia-post",
37624
+ "day-ross"
37619
37625
  ]
37620
37626
  },
37621
37627
  {
@@ -37627,7 +37633,8 @@
37627
37633
  "day-ross"
37628
37634
  ],
37629
37635
  "asked": [
37630
- "australia-post"
37636
+ "australia-post",
37637
+ "day-ross"
37631
37638
  ]
37632
37639
  },
37633
37640
  {
@@ -1771,6 +1771,7 @@ var De = {
1771
1771
  parcelforce: {
1772
1772
  displayName: "Parcelforce Worldwide",
1773
1773
  color: "#9d0f11",
1774
+ aliases: ["Parcelforce"],
1774
1775
  countries: ["GB"],
1775
1776
  selectable: !0,
1776
1777
  timezone: "UTC",
@@ -4437,9 +4438,12 @@ var De = {
4437
4438
  timezone: "America/Moncton",
4438
4439
  tracking: {
4439
4440
  mode: "automatic",
4440
- adapter: "universal"
4441
+ adapter: "day-ross",
4442
+ recognitionRank: 38,
4443
+ localClocks: !0
4441
4444
  },
4442
- canaryUrl: "https://dayross.com/",
4445
+ canaryUrl: "https://dayross.com/track-shipments",
4446
+ trackingSearchUrl: "https://dayross.com/track-shipments",
4443
4447
  linkRules: [],
4444
4448
  detectionRules: [{
4445
4449
  pattern: "^(?:MRO|MTN|SMI|SML|XTO)\\d{7}$",
@@ -5565,11 +5569,25 @@ var De = {
5565
5569
  timezone: "Europe/Stockholm",
5566
5570
  tracking: {
5567
5571
  mode: "automatic",
5568
- adapter: "universal"
5572
+ adapter: "instabox",
5573
+ requirements: [{
5574
+ field: "trackingUrl",
5575
+ validator: "instaboxCapabilityUrl",
5576
+ optional: !0,
5577
+ label: "Instabox notification URL",
5578
+ type: "url",
5579
+ placeholder: "https://track.instabox.com/…",
5580
+ help: "The complete notification link opens your parcel history. Without it, other sources are asked."
5581
+ }]
5569
5582
  },
5570
- canaryUrl: "https://track.instabox.com/en",
5583
+ canaryUrl: "https://track.instabox.com/",
5571
5584
  trackingSearchUrl: "https://track.instabox.com/en",
5572
- linkRules: [],
5585
+ linkRules: [{
5586
+ domains: ["track.instabox.com"],
5587
+ pathPattern: "^/[a-z]{2}(?:-[A-Z]{2})?/[A-Za-z0-9]{4,40}(?:/locker-to-locker-recipient)?/?$",
5588
+ path: "^/[a-z]{2}(?:-[A-Z]{2})?/([A-Za-z0-9]{4,40})(?:/locker-to-locker-recipient)?/?$",
5589
+ keepsCapabilityUrl: !0
5590
+ }],
5573
5591
  detectionRules: []
5574
5592
  },
5575
5593
  intelcom: {
@@ -6508,15 +6526,22 @@ var De = {
6508
6526
  timezone: "America/New_York",
6509
6527
  tracking: {
6510
6528
  mode: "automatic",
6511
- adapter: "universal"
6529
+ adapter: "saia",
6530
+ recognitionRank: 12,
6531
+ localClocks: !0
6512
6532
  },
6513
6533
  canaryUrl: "https://www.saia.com/track",
6514
- trackingUrlTemplate: "https://www.saia.com/track?pro={trackingNumber}",
6534
+ trackingUrlTemplate: "https://www.saia.com/track/details;pro={trackingNumber}",
6515
6535
  trackingSearchUrl: "https://www.saia.com/track",
6516
6536
  linkRules: [{
6517
6537
  domains: ["saia.com"],
6518
6538
  pathPattern: "^/track/?$",
6519
6539
  params: ["pro"]
6540
+ }, {
6541
+ domains: ["saia.com"],
6542
+ pathPattern: "^/track/details(?:/|;|$)",
6543
+ path: "^/track/details;pro=(\\d+)",
6544
+ params: ["pro"]
6520
6545
  }],
6521
6546
  detectionRules: []
6522
6547
  },
@@ -6859,9 +6884,11 @@ var De = {
6859
6884
  timezone: "Asia/Shanghai",
6860
6885
  tracking: {
6861
6886
  mode: "automatic",
6862
- adapter: "universal"
6887
+ adapter: "wanbexpress",
6888
+ recognitionRank: 33,
6889
+ browserRecognitionRank: 33
6863
6890
  },
6864
- canaryUrl: "https://www.wanbexpress.com/",
6891
+ canaryUrl: "https://tracking.wanbexpress.com/",
6865
6892
  linkRules: [],
6866
6893
  detectionRules: [{
6867
6894
  pattern: "^WNB[A-Z]{2}\\d{10}YQ$",
@@ -6957,6 +6984,7 @@ var De = {
6957
6984
  mode: "automatic",
6958
6985
  adapter: "xpo-ltl",
6959
6986
  recognitionRank: 25,
6987
+ browserRecognitionRank: 25,
6960
6988
  localClocks: !0
6961
6989
  },
6962
6990
  canaryUrl: "https://www.xpo.com/",
@@ -12475,6 +12503,7 @@ var Qc = {
12475
12503
  "cyprus-post": 60,
12476
12504
  "dai-post": 62,
12477
12505
  dao: 515,
12506
+ "day-ross": 38,
12478
12507
  delhivery: 600,
12479
12508
  "dhl-ecommerce": 670,
12480
12509
  "dhl-ecommerce-es": 630,
@@ -12547,6 +12576,7 @@ var Qc = {
12547
12576
  redpack: 15,
12548
12577
  "relais-colis": 690,
12549
12578
  "rl-carriers": 5,
12579
+ saia: 12,
12550
12580
  sameday: 370,
12551
12581
  seur: 870,
12552
12582
  "slovak-parcel-service": 180,
@@ -12563,6 +12593,7 @@ var Qc = {
12563
12593
  uniuni: 770,
12564
12594
  venipak: 240,
12565
12595
  "vinted-go": 410,
12596
+ wanbexpress: 33,
12566
12597
  whistl: 320,
12567
12598
  "xpo-ltl": 25,
12568
12599
  "yurtici-kargo": 430,
@@ -12689,7 +12720,7 @@ function cl(e, t = /* @__PURE__ */ new Date()) {
12689
12720
  }
12690
12721
  //#endregion
12691
12722
  //#region core/catalog/urls.ts
12692
- var ll = "trackandtrace.planzergroup.com", ul = /^\/shared\/sendungen\/([^/]+)\/?$/, dl = /^[A-Za-z0-9_-]{32,256}$/, fl = "customeriberia.dachser.com", pl = "/customerarea/utilidades/seguimiento-publico/detalle", ml = /^[A-Za-z0-9_-]{4,256}$/, hl = /[\x00-\x1f\x7f]/, gl = /* @__PURE__ */ new Set([
12723
+ var ll = "trackandtrace.planzergroup.com", ul = /^\/shared\/sendungen\/([^/]+)\/?$/, dl = /^[A-Za-z0-9_-]{32,256}$/, fl = "customeriberia.dachser.com", pl = "/customerarea/utilidades/seguimiento-publico/detalle", ml = /^\/[a-z]{2}(?:-[A-Z]{2})?\/([A-Z0-9]{4,40})(?:\/locker-to-locker-recipient)?\/?$/i, hl = /^[A-Za-z0-9_-]{4,256}$/, gl = /[\x00-\x1f\x7f]/, _l = /* @__PURE__ */ new Set([
12693
12724
  "hash",
12694
12725
  "cliente",
12695
12726
  "numeroUnico",
@@ -12704,7 +12735,22 @@ var ll = "trackandtrace.planzergroup.com", ul = /^\/shared\/sendungen\/([^/]+)\/
12704
12735
  "origen",
12705
12736
  "usuario"
12706
12737
  ]);
12707
- function _l(e, n) {
12738
+ function vl(e, n) {
12739
+ let r;
12740
+ try {
12741
+ r = new URL(e.trim());
12742
+ } catch {
12743
+ throw TypeError("Paste the complete Instabox notification URL");
12744
+ }
12745
+ if (e.length > 4096 || r.protocol !== "https:" || r.hostname !== "track.instabox.com" || r.username || r.password || r.port && r.port !== "443" || r.hash) throw TypeError("Instabox notification links must use https://track.instabox.com");
12746
+ let i = ml.exec(r.pathname);
12747
+ if (!i || i[1].toUpperCase() !== t(n)) throw TypeError("The Instabox URL must name this complete parcel identifier");
12748
+ let a = [...r.searchParams].filter(([e]) => e === "authCode" || e === "c");
12749
+ if (a.length !== 1 || !/^[A-Za-z0-9_-]{16,160}$/.test(a[0][1])) throw TypeError("The Instabox notification URL must include its verification code");
12750
+ for (let [e, t] of r.searchParams) if (!["authCode", "c"].includes(e) && (!/^utm_(?:source|medium|campaign|content|term)$/.test(e) || t.length > 256)) throw TypeError("The Instabox URL contains an unsupported parameter");
12751
+ return r.pathname = r.pathname.replace(i[1], t(n)), r.search = new URLSearchParams([a[0]]).toString(), r.toString();
12752
+ }
12753
+ function yl(e, n) {
12708
12754
  let r = e.trim();
12709
12755
  if (r.length < 1 || r.length > 4096) throw TypeError("Paste the complete Planzer tracking URL");
12710
12756
  let i;
@@ -12727,7 +12773,7 @@ function _l(e, n) {
12727
12773
  if (s.length !== 1 || !dl.test(s[0])) throw TypeError("The Planzer URL must include its accessKey");
12728
12774
  return i.toString();
12729
12775
  }
12730
- function vl(e, n) {
12776
+ function bl(e, n) {
12731
12777
  let r = e.trim();
12732
12778
  if (r.length < 1 || r.length > 4096) throw TypeError("Paste the complete Dachser tracking URL");
12733
12779
  let i;
@@ -12746,25 +12792,25 @@ function vl(e, n) {
12746
12792
  if (a !== pl && a !== `${pl}/`) throw TypeError("Paste a Dachser public shipment detail URL");
12747
12793
  let o = /* @__PURE__ */ new Map();
12748
12794
  for (let [e, t] of i.searchParams) {
12749
- if (!gl.has(e)) throw TypeError("The Dachser URL contains an unsupported parameter");
12795
+ if (!_l.has(e)) throw TypeError("The Dachser URL contains an unsupported parameter");
12750
12796
  if (o.has(e)) throw TypeError("The Dachser URL contains a duplicate parameter");
12751
- if (!t || t.length > 256 || hl.test(t)) throw TypeError("The Dachser URL contains an invalid parameter");
12797
+ if (!t || t.length > 256 || gl.test(t)) throw TypeError("The Dachser URL contains an invalid parameter");
12752
12798
  o.set(e, t);
12753
12799
  }
12754
12800
  let s = o.get("numeroUnico");
12755
12801
  if (!s) throw TypeError("The Dachser URL must include its shipment number");
12756
12802
  if (t(s) !== t(n)) throw TypeError("The Dachser URL belongs to a different tracking number");
12757
- let c = o.get("hash"), l = o.get("clave"), u = o.get("fecha"), d = !!(c && ml.test(c)), f = !!(l && u && ml.test(l) && /^\d{8}$/.test(u));
12803
+ let c = o.get("hash"), l = o.get("clave"), u = o.get("fecha"), d = !!(c && hl.test(c)), f = !!(l && u && hl.test(l) && /^\d{8}$/.test(u));
12758
12804
  if (!d && !f) throw TypeError("The Dachser URL must include its access parameters");
12759
12805
  return i.protocol = "https:", i.hostname = fl, i.port = "", i.toString();
12760
12806
  }
12761
12807
  //#endregion
12762
12808
  //#region core/catalog/postcode.ts
12763
- var yl = /^(?=.{3,12}$)(?=.*\d)[A-Z0-9]+(?:[ -][A-Z0-9]+)*$/;
12764
- function bl(e) {
12809
+ var xl = /^(?=.{3,12}$)(?=.*\d)[A-Z0-9]+(?:[ -][A-Z0-9]+)*$/;
12810
+ function Sl(e) {
12765
12811
  return e.trim().toUpperCase().replace(/\s+/g, " ");
12766
12812
  }
12767
- function xl(e) {
12813
+ function Cl(e) {
12768
12814
  let t = e.toUpperCase().replace(/\s+/g, "");
12769
12815
  if (/^(?:0[1-9]|[1-8]\d|9[0-5]|97|98)\d{3}$/.test(t)) return t;
12770
12816
  let n = /^(?:(BE?|LU?)-?)?([1-9]\d{3})$/.exec(t);
@@ -12772,17 +12818,17 @@ function xl(e) {
12772
12818
  }
12773
12819
  //#endregion
12774
12820
  //#region core/catalog/inputs.ts
12775
- function Sl(e, t) {
12821
+ function wl(e, t) {
12776
12822
  return e === "mondial-relay" && /^(?:\d{10}|\d{12}|\d{26})$/.test(t);
12777
12823
  }
12778
- function Cl(e, t, n, r) {
12824
+ function Tl(e, t, n, r) {
12779
12825
  let i = {
12780
12826
  trackingUrl: n.trim() || null,
12781
12827
  postcode: r.trim() || null
12782
12828
  };
12783
12829
  if (e === "mondial-relay" && /^\d{26}$/.test(t) && !we(t)) throw TypeError("Invalid Mondial Relay barcode");
12784
12830
  let a = new Map(Be(e, t).map((e) => [e.field, e]));
12785
- Sl(e, t) && i.postcode && a.set("postcode", {
12831
+ wl(e, t) && i.postcode && a.set("postcode", {
12786
12832
  field: "postcode",
12787
12833
  validator: "internationalPostcode"
12788
12834
  });
@@ -12795,9 +12841,12 @@ function Cl(e, t, n, r) {
12795
12841
  }
12796
12842
  switch (r.validator) {
12797
12843
  case "planzerSharedUrl":
12798
- i[n] = _l(a, t);
12844
+ i[n] = yl(a, t);
12799
12845
  break;
12800
12846
  case "dachserCapabilityUrl":
12847
+ i[n] = bl(a, t);
12848
+ break;
12849
+ case "instaboxCapabilityUrl":
12801
12850
  i[n] = vl(a, t);
12802
12851
  break;
12803
12852
  case "swissPostcode":
@@ -12811,8 +12860,8 @@ function Cl(e, t, n, r) {
12811
12860
  if (!/^\d{4,5}$/.test(a)) throw TypeError(`${g(e).displayName} requires a four- or five-digit delivery postcode`);
12812
12861
  break;
12813
12862
  case "internationalPostcode":
12814
- if (!yl.test(bl(a))) throw TypeError(`${g(e).displayName} requires a valid delivery postcode`);
12815
- i[n] = bl(a);
12863
+ if (!xl.test(Sl(a))) throw TypeError(`${g(e).displayName} requires a valid delivery postcode`);
12864
+ i[n] = Sl(a);
12816
12865
  break;
12817
12866
  case "paackPostcode": {
12818
12867
  let e = a.toLocaleUpperCase("en-US");
@@ -12821,7 +12870,7 @@ function Cl(e, t, n, r) {
12821
12870
  break;
12822
12871
  }
12823
12872
  case "colisPrivePostcode": {
12824
- let t = xl(a);
12873
+ let t = Cl(a);
12825
12874
  if (!t) throw TypeError(`${g(e).displayName} requires a French, Belgian or Luxembourg delivery postcode`);
12826
12875
  i[n] = t;
12827
12876
  break;
@@ -12831,12 +12880,12 @@ function Cl(e, t, n, r) {
12831
12880
  }
12832
12881
  return i;
12833
12882
  }
12834
- function wl(e) {
12835
- let t = bl(e);
12836
- if (!yl.test(t)) throw TypeError("A valid delivery postcode is required");
12883
+ function El(e) {
12884
+ let t = Sl(e);
12885
+ if (!xl.test(t)) throw TypeError("A valid delivery postcode is required");
12837
12886
  return t;
12838
12887
  }
12839
- var Tl = { carriers: [
12888
+ var Dl = { carriers: [
12840
12889
  {
12841
12890
  carrier: "dhl",
12842
12891
  direct: "Yes",
@@ -16812,80 +16861,80 @@ var Tl = { carriers: [
16812
16861
  }
16813
16862
  }]
16814
16863
  }
16815
- ] }, El = [
16864
+ ] }, Ol = [
16816
16865
  "Ship24",
16817
16866
  "ParcelsApp",
16818
16867
  "17TRACK",
16819
16868
  "Postal Ninja",
16820
16869
  "UPU"
16821
- ], Dl = /* @__PURE__ */ new Set([
16870
+ ], kl = /* @__PURE__ */ new Set([
16822
16871
  "no_history",
16823
16872
  "summary_only",
16824
16873
  "undated",
16825
16874
  "sign_in",
16826
16875
  "postcode_prompt"
16827
- ]), Ol = Tl.carriers, kl = new Map(Ol.map((e) => [e.carrier, e]));
16828
- function Al(e) {
16876
+ ]), Al = Dl.carriers, jl = new Map(Al.map((e) => [e.carrier, e]));
16877
+ function Ml(e) {
16829
16878
  return typeof e == "number" || e === "history" || typeof e == "object" && !!e;
16830
16879
  }
16831
- function jl(e, t) {
16832
- let n = t.filter((t) => t.results[e] !== void 0), r = n.some((t) => !t.stale && (Dl.has(t.results[e]) || t.results[e] === "wrong_carrier") && Object.entries(t.results).some(([t, n]) => t !== e && t !== "UPU" && Al(n)));
16833
- return n.some((t) => Al(t.results[e])) ? n.some((t) => typeof t.results[e] == "object") || r ? "partial" : "full" : n.some((t) => ["wrong_carrier", "refused"].includes(t.results[e])) ? "excluded" : n.some((t) => !t.stale && Dl.has(t.results[e])) ? "empty" : "unknown";
16880
+ function Nl(e, t) {
16881
+ let n = t.filter((t) => t.results[e] !== void 0), r = n.some((t) => !t.stale && (kl.has(t.results[e]) || t.results[e] === "wrong_carrier") && Object.entries(t.results).some(([t, n]) => t !== e && t !== "UPU" && Ml(n)));
16882
+ return n.some((t) => Ml(t.results[e])) ? n.some((t) => typeof t.results[e] == "object") || r ? "partial" : "full" : n.some((t) => ["wrong_carrier", "refused"].includes(t.results[e])) ? "excluded" : n.some((t) => !t.stale && kl.has(t.results[e])) ? "empty" : "unknown";
16834
16883
  }
16835
- function Ml(e) {
16836
- let t = e ? kl.get(e) : void 0;
16837
- return t ? Object.fromEntries(El.map((e) => [e, jl(e, t.references)])) : null;
16884
+ function Pl(e) {
16885
+ let t = e ? jl.get(e) : void 0;
16886
+ return t ? Object.fromEntries(Ol.map((e) => [e, Nl(e, t.references)])) : null;
16838
16887
  }
16839
16888
  //#endregion
16840
16889
  //#region providers/plan.ts
16841
- var Nl = [
16890
+ var Fl = [
16842
16891
  "ParcelsApp",
16843
16892
  "Ship24",
16844
16893
  "17TRACK",
16845
16894
  "UPU"
16846
- ], Pl = /* @__PURE__ */ new Set(["17TRACK", "Postal Ninja"]);
16847
- function Fl(e) {
16895
+ ], Il = /* @__PURE__ */ new Set(["17TRACK", "Postal Ninja"]);
16896
+ function Ll(e) {
16848
16897
  return e === "ParcelsApp" ? 45e3 : e === "UPU" ? 8e3 : 3e4;
16849
16898
  }
16850
- function Il(e) {
16899
+ function Rl(e) {
16851
16900
  return e && /^\d{10}$/.test(t(e)) ? "Ship24" : e && /^[CL][A-Z]\d{9}CN$/.test(t(e)) && v(e) ? "17TRACK" : void 0;
16852
16901
  }
16853
- var Ll = {
16902
+ var zl = {
16854
16903
  full: 0,
16855
16904
  partial: 1,
16856
16905
  unknown: 2,
16857
16906
  empty: 3,
16858
16907
  excluded: 4
16859
16908
  };
16860
- function Rl(e, t) {
16861
- let n = Ll[e?.[t] ?? "unknown"];
16862
- return t === "UPU" ? Ll.unknown : t === "Postal Ninja" ? Math.max(n, Ll.empty) : n;
16863
- }
16864
- var zl = (e) => e === "UPU" ? 2 : +(e === "Postal Ninja");
16865
16909
  function Bl(e, t) {
16910
+ let n = zl[e?.[t] ?? "unknown"];
16911
+ return t === "UPU" ? zl.unknown : t === "Postal Ninja" ? Math.max(n, zl.empty) : n;
16912
+ }
16913
+ var Vl = (e) => e === "UPU" ? 2 : +(e === "Postal Ninja");
16914
+ function Hl(e, t) {
16866
16915
  let n = (e) => e !== "UPU" && t?.[e] === "excluded";
16867
- return (e.some((e) => e !== "UPU" && !n(e)) ? e.filter((e) => !n(e)) : [...e]).sort((n, r) => zl(n) - zl(r) || Rl(t, n) - Rl(t, r) || Number(Pl.has(n)) - Number(Pl.has(r)) || e.indexOf(n) - e.indexOf(r));
16916
+ return (e.some((e) => e !== "UPU" && !n(e)) ? e.filter((e) => !n(e)) : [...e]).sort((n, r) => Vl(n) - Vl(r) || Bl(t, n) - Bl(t, r) || Number(Il.has(n)) - Number(Il.has(r)) || e.indexOf(n) - e.indexOf(r));
16868
16917
  }
16869
- function Vl(e = {}) {
16918
+ function Ul(e = {}) {
16870
16919
  let { trackingNumber: t, enablePostalNinja: n = !1 } = e, r = (n ? [
16871
16920
  "ParcelsApp",
16872
16921
  "Ship24",
16873
16922
  "17TRACK",
16874
16923
  "Postal Ninja",
16875
16924
  "UPU"
16876
- ] : [...Nl]).filter((e) => e !== "UPU" || t === void 0 || v(t)), i = (e.carriers ?? []).find((e) => Ml(e)) ?? null, a = Ml(i), o = Bl(r, a), s = Il(t);
16925
+ ] : [...Fl]).filter((e) => e !== "UPU" || t === void 0 || v(t)), i = (e.carriers ?? []).find((e) => Pl(e)) ?? null, a = Pl(i), o = Hl(r, a), s = Rl(t);
16877
16926
  return {
16878
16927
  sources: s ? [s, ...o.filter((e) => e !== s)] : o,
16879
16928
  carrier: i,
16880
16929
  tier: (e) => a?.[e] ?? "unknown",
16881
- rank: (e) => Rl(a, e)
16930
+ rank: (e) => Bl(a, e)
16882
16931
  };
16883
16932
  }
16884
- function Hl(e = !1, t) {
16885
- return Vl({
16933
+ function Wl(e = !1, t) {
16934
+ return Ul({
16886
16935
  trackingNumber: t,
16887
16936
  enablePostalNinja: e
16888
16937
  }).sources;
16889
16938
  }
16890
16939
  //#endregion
16891
- export { je as AMAZON_NUMBER_PATTERN, He as AUTOMATIC_CARRIER_IDS, Pl as BROWSER_SOURCES, te as BudgetExceededError, _ as CARRIERS, De as CARRIER_CATALOG, h as CARRIER_DEFINITIONS, Oe as CARRIER_IDS, Ue as CARRIER_NAMES, a as CarrierError, l as ChallengeError, Ho as EXPLICIT_OFFSET_PATTERN, s as IndeterminateError, p as InputRequiredError, m as InvalidInputError, $c as MAX_RECOGNITIONS, d as MaintenanceError, c as NoHistoryError, o as NotFoundError, u as RateLimitedError, Ze as SELECTABLE_CARRIERS, Ae as STAGES, f as SchemaError, zt as TRACKING_CANDIDATE_PATTERNS, We as TRACKING_LINK_RULES, ee as TransportError, Nl as UNIVERSAL_SOURCES, re as UpstreamHttpError, ie as UpstreamNetworkError, Be as activeRequirements, Pe as amazonMarketplace, Fe as amazonOrdersUrl, Ie as amazonShippingOrigin, Le as amazonShippingUrl, gs as calendarDay, us as canadaProvinceTimeZone, ze as carrierAdapter, g as carrierDefinition, oe as carrierErrorKind, Xe as carrierInfo, Ge as carrierLinkRules, Qe as carrierRequirements, Re as carrierTimezone, Pt as checksumRejections, mc as classifyStage, lc as classifyWording, is as countryCode, as as countryTimeZone, Mc as deliveryHandoff, Ft as detectCarrier, y as detectCarrierMatch, ms as epochMillisTime, hs as epochSecondsTime, ce as errorTypeOf, Es as eventPoint, Wo as explicitOffsetTime, Zc as failureHint, Xc as failureKind, Yc as fillPartialAnswer, Q as firstOccurrence, r as formatTrackingNumber, jc as hasDirectHandoffAdapter, hc as inferStage, Me as isAmazonTrackingNumber, Jc as isPartialAnswer, n as isPlanzerSharedTrackingNumber, it as isValidCorreosSpainCheckLetter, me as isValidDhlExpressWaybill, st as isValidDpdParcelNumber, gt as isValidGlsParcelNumber, _t as isValidHermesParcelNumber, we as isValidMondialRelayBarcode, Se as isValidPocztaPolskaBarcode, v as isValidS10TrackingNumber, Ce as isValidSscc, ge as isValidTntConsignmentNumber, Dt as isValidUspsPackageBarcode, Ko as isoTime, Ut as keywordNumberInText, cc as languageStageStatus, tt as localizedCarrierUrl, Ke as matchesDomain, Jo as mislabeledLocalTime, Yo as mislabeledWallTime, Cl as normalizeCarrierInputs, Ds as normalizeCarrierResult, wl as normalizeDeliveryPostcode, t as normalizeTrackingNumber, Bl as orderUniversalSources, Xt as parseTrackingInput, Il as priorityUniversalSource, nl as recognitionCandidates, el as recognitionNumberShape, il as recognizeAll, Bt as recognizedNumberInText, ps as regionHasTown, Ve as requiredRequirements, $e as requirementSatisfied, Ne as requiresAmazonAccount, _c as resolveResult, pc as resultHasUpdate, fc as resultStage, se as retryAfterMsOf, Qo as settleGuessedClocks, cl as settleRecognition, Xo as sharedClockZone, gc as stageSource, xt as supportsSwissPostHandoff, os as timeZoneCountry, ds as townKey, sc as trackingLanguageStage, Je as trackingLink, qe as trackingNumberForLink, et as tracksAutomatically, Vl as universalPlan, Fl as universalSourceBudget, Hl as universalSources, cs as usStateTimeZone, Et as uspsPackageIdentifier, Lt as validTrackingNumber, vl as validateDachserTrackingUrl, _l as validatePlanzerSharedUrl, uc as wordingStage, Go as zonedTime };
16940
+ export { je as AMAZON_NUMBER_PATTERN, He as AUTOMATIC_CARRIER_IDS, Il as BROWSER_SOURCES, te as BudgetExceededError, _ as CARRIERS, De as CARRIER_CATALOG, h as CARRIER_DEFINITIONS, Oe as CARRIER_IDS, Ue as CARRIER_NAMES, a as CarrierError, l as ChallengeError, Ho as EXPLICIT_OFFSET_PATTERN, s as IndeterminateError, p as InputRequiredError, m as InvalidInputError, $c as MAX_RECOGNITIONS, d as MaintenanceError, c as NoHistoryError, o as NotFoundError, u as RateLimitedError, Ze as SELECTABLE_CARRIERS, Ae as STAGES, f as SchemaError, zt as TRACKING_CANDIDATE_PATTERNS, We as TRACKING_LINK_RULES, ee as TransportError, Fl as UNIVERSAL_SOURCES, re as UpstreamHttpError, ie as UpstreamNetworkError, Be as activeRequirements, Pe as amazonMarketplace, Fe as amazonOrdersUrl, Ie as amazonShippingOrigin, Le as amazonShippingUrl, gs as calendarDay, us as canadaProvinceTimeZone, ze as carrierAdapter, g as carrierDefinition, oe as carrierErrorKind, Xe as carrierInfo, Ge as carrierLinkRules, Qe as carrierRequirements, Re as carrierTimezone, Pt as checksumRejections, mc as classifyStage, lc as classifyWording, is as countryCode, as as countryTimeZone, Mc as deliveryHandoff, Ft as detectCarrier, y as detectCarrierMatch, ms as epochMillisTime, hs as epochSecondsTime, ce as errorTypeOf, Es as eventPoint, Wo as explicitOffsetTime, Zc as failureHint, Xc as failureKind, Yc as fillPartialAnswer, Q as firstOccurrence, r as formatTrackingNumber, jc as hasDirectHandoffAdapter, hc as inferStage, Me as isAmazonTrackingNumber, Jc as isPartialAnswer, n as isPlanzerSharedTrackingNumber, it as isValidCorreosSpainCheckLetter, me as isValidDhlExpressWaybill, st as isValidDpdParcelNumber, gt as isValidGlsParcelNumber, _t as isValidHermesParcelNumber, we as isValidMondialRelayBarcode, Se as isValidPocztaPolskaBarcode, v as isValidS10TrackingNumber, Ce as isValidSscc, ge as isValidTntConsignmentNumber, Dt as isValidUspsPackageBarcode, Ko as isoTime, Ut as keywordNumberInText, cc as languageStageStatus, tt as localizedCarrierUrl, Ke as matchesDomain, Jo as mislabeledLocalTime, Yo as mislabeledWallTime, Tl as normalizeCarrierInputs, Ds as normalizeCarrierResult, El as normalizeDeliveryPostcode, t as normalizeTrackingNumber, Hl as orderUniversalSources, Xt as parseTrackingInput, Rl as priorityUniversalSource, nl as recognitionCandidates, el as recognitionNumberShape, il as recognizeAll, Bt as recognizedNumberInText, ps as regionHasTown, Ve as requiredRequirements, $e as requirementSatisfied, Ne as requiresAmazonAccount, _c as resolveResult, pc as resultHasUpdate, fc as resultStage, se as retryAfterMsOf, Qo as settleGuessedClocks, cl as settleRecognition, Xo as sharedClockZone, gc as stageSource, xt as supportsSwissPostHandoff, os as timeZoneCountry, ds as townKey, sc as trackingLanguageStage, Je as trackingLink, qe as trackingNumberForLink, et as tracksAutomatically, Ul as universalPlan, Ll as universalSourceBudget, Wl as universalSources, cs as usStateTimeZone, Et as uspsPackageIdentifier, Lt as validTrackingNumber, bl as validateDachserTrackingUrl, vl as validateInstaboxTrackingUrl, yl as validatePlanzerSharedUrl, uc as wordingStage, Go as zonedTime };
@@ -1,3 +1,4 @@
1
+ import { returnedTrackingNumber } from '../../core/detection/returned.js';
1
2
  import { load } from 'cheerio';
2
3
  import { DateTime } from 'luxon';
3
4
  import { normalizeTrackingNumber } from '../../core/detection/index.js';
@@ -54,7 +55,7 @@ function searchPage($, html, number) {
54
55
  const notice = notices.length === 1 ? clean(notices.text(), 200) : '';
55
56
  // The page puts the identifier it was asked for back into its search field.
56
57
  const fields = $('input#ConsignmentNumber');
57
- const echoed = fields.length === 1 ? normalizeTrackingNumber(clean(fields.attr('value'), 80)) : '';
58
+ const echoed = fields.length === 1 ? returnedTrackingNumber(fields.attr('value')) : '';
58
59
  if (notice === NOT_FOUND || notice === INVALID) {
59
60
  if (echoed !== number)
60
61
  throw new SchemaError(PROVIDER, 'APC Overnight answered for a different number');
@@ -21,6 +21,7 @@
21
21
  * event from an explicit allowlist (time, harmonized wording, scanning
22
22
  * location, harmonized code) and copies nothing else.
23
23
  */
24
+ import { returnedTrackingNumber } from '../../core/detection/returned.js';
24
25
  import { createHash } from 'node:crypto';
25
26
  import { load } from 'cheerio';
26
27
  import { DateTime } from 'luxon';
@@ -140,7 +141,7 @@ function parseTenantConfig(payload) {
140
141
  function responseIdentifier(parcel) {
141
142
  for (const value of [parcel.tracking_id, parcel.upper_tracking_id]) {
142
143
  try {
143
- return normalizeAsendiaTrackingNumber(cleanScalar(value, 64));
144
+ return normalizeAsendiaTrackingNumber(returnedTrackingNumber(value, true));
144
145
  }
145
146
  catch {
146
147
  // Try the alternate provider field.
@@ -1,3 +1,4 @@
1
+ import { returnedTrackingNumber } from '../../core/detection/returned.js';
1
2
  import { normalizeTrackingNumber } from '../../core/detection/index.js';
2
3
  import { IndeterminateError, InvalidInputError, NoHistoryError, SchemaError } from '../../core/errors/index.js';
3
4
  import { languageStageStatus } from '../../core/status/index.js';
@@ -71,8 +72,8 @@ export function parseCdek(payload, raw) {
71
72
  const data = payload.data;
72
73
  if (!isRecord(data))
73
74
  throw new SchemaError(PROVIDER, 'CDEK did not return an order');
74
- const order = normalizeTrackingNumber(clean(data.orderNumber, 40));
75
- const outer = payload.orderNumber === undefined ? order : normalizeTrackingNumber(clean(payload.orderNumber, 40));
75
+ const order = returnedTrackingNumber(data.orderNumber);
76
+ const outer = payload.orderNumber === undefined ? order : returnedTrackingNumber(payload.orderNumber);
76
77
  if (!ISSUED.test(order) || outer !== order)
77
78
  throw new SchemaError(PROVIDER, 'CDEK returned an order without its number');
78
79
  // CDEK finds an order by a number it links to it and answers with the order's own number.
@@ -1,3 +1,4 @@
1
+ import { returnedTrackingNumber } from '../../core/detection/returned.js';
1
2
  import { load } from 'cheerio';
2
3
  import { isValidS10TrackingNumber, normalizeTrackingNumber } from '../../core/detection/index.js';
3
4
  import { ChallengeError, IndeterminateError, InvalidInputError, SchemaError } from '../../core/errors/index.js';
@@ -125,7 +126,7 @@ export function readCorreosDeMexicoPage(html, rawNumber, askedYear) {
125
126
  const guia = form.find('input#Guia[name="Guia"]');
126
127
  if (guia.length !== 1)
127
128
  throw new SchemaError(PROVIDER, 'Correos de México tracking form changed');
128
- if (normalizeTrackingNumber(clean(guia.attr('value'), 80)) !== number) {
129
+ if (returnedTrackingNumber(guia.attr('value')) !== number) {
129
130
  throw new SchemaError(PROVIDER, 'Correos de México answered for a different number');
130
131
  }
131
132
  const options = form.find('select#Periodo[name="Periodo"] > option');