@morpho-dev/router 0.0.16 → 0.0.18

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 (32) hide show
  1. package/dist/index.browser.d.cts +136 -9
  2. package/dist/index.browser.d.ts +136 -9
  3. package/dist/index.browser.js +377 -9
  4. package/dist/index.browser.js.map +1 -1
  5. package/dist/index.browser.mjs +377 -5
  6. package/dist/index.browser.mjs.map +1 -1
  7. package/dist/index.node.d.cts +108 -726
  8. package/dist/index.node.d.ts +108 -726
  9. package/dist/index.node.js +735 -1215
  10. package/dist/index.node.js.map +1 -1
  11. package/dist/index.node.mjs +734 -1204
  12. package/dist/index.node.mjs.map +1 -1
  13. package/package.json +3 -12
  14. package/dist/drizzle/0000_add-offers-table.sql +0 -37
  15. package/dist/drizzle/0001_create_offer_status_relation.sql +0 -10
  16. package/dist/drizzle/0002_add_created_at_in_offer_status_relation.sql +0 -3
  17. package/dist/drizzle/0003_add-cursor-indices-to-offers.sql +0 -6
  18. package/dist/drizzle/0004_offer-start.sql +0 -1
  19. package/dist/drizzle/0005_rename-price-token-buy.sql +0 -8
  20. package/dist/drizzle/0006_rename-buy.sql +0 -3
  21. package/dist/drizzle/0007_rename-offering.sql +0 -3
  22. package/dist/drizzle/0008_add-consumed-relation.sql +0 -10
  23. package/dist/drizzle/meta/0000_snapshot.json +0 -344
  24. package/dist/drizzle/meta/0001_snapshot.json +0 -426
  25. package/dist/drizzle/meta/0002_snapshot.json +0 -439
  26. package/dist/drizzle/meta/0003_snapshot.json +0 -553
  27. package/dist/drizzle/meta/0004_snapshot.json +0 -559
  28. package/dist/drizzle/meta/0005_snapshot.json +0 -559
  29. package/dist/drizzle/meta/0006_snapshot.json +0 -559
  30. package/dist/drizzle/meta/0007_snapshot.json +0 -559
  31. package/dist/drizzle/meta/0008_snapshot.json +0 -635
  32. package/dist/drizzle/meta/_journal.json +0 -69
@@ -1,9 +1,9 @@
1
- import { Errors, Offer, Format } from '@morpho-dev/mempool';
1
+ import { Errors, Offer, Format, Time, Maturity, LLTV } from '@morpho-dev/mempool';
2
2
  export * from '@morpho-dev/mempool';
3
3
  import { base, mainnet } from 'viem/chains';
4
- import { maxUint256, parseAbi } from 'viem';
5
4
  import { z } from 'zod/v4';
6
5
  import { createDocument } from 'zod-openapi';
6
+ import { maxUint256, parseUnits, parseAbi } from 'viem';
7
7
 
8
8
  var __defProp = Object.defineProperty;
9
9
  var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
@@ -67,7 +67,7 @@ var chains = {
67
67
  }
68
68
  };
69
69
 
70
- // src/core/Client.ts
70
+ // src/core/router/Client.ts
71
71
  var Client_exports = {};
72
72
  __export(Client_exports, {
73
73
  HttpForbiddenError: () => HttpForbiddenError,
@@ -138,6 +138,18 @@ var InvalidRouterOfferError = class extends Errors.BaseError {
138
138
  }
139
139
  };
140
140
 
141
+ // src/utils/index.ts
142
+ var utils_exports = {};
143
+ __export(utils_exports, {
144
+ batch: () => batch,
145
+ decodeCursor: () => decodeCursor,
146
+ encodeCursor: () => encodeCursor,
147
+ poll: () => poll,
148
+ retry: () => retry,
149
+ validateCursor: () => validateCursor,
150
+ wait: () => wait
151
+ });
152
+
141
153
  // src/utils/batch.ts
142
154
  function* batch(array, batchSize) {
143
155
  for (let i = 0; i < array.length; i += batchSize) {
@@ -248,6 +260,20 @@ function poll(fn, { interval }) {
248
260
  return unwatch;
249
261
  }
250
262
 
263
+ // src/utils/retry.ts
264
+ var retry = async (fn, attempts = 3, delayMs = 50) => {
265
+ let lastErr;
266
+ for (let i = 0; i < attempts; i++) {
267
+ try {
268
+ return await fn();
269
+ } catch (err) {
270
+ lastErr = err;
271
+ if (i < attempts - 1) await new Promise((r) => setTimeout(r, delayMs));
272
+ }
273
+ }
274
+ throw lastErr;
275
+ };
276
+
251
277
  // src/core/apiSchema/requests.ts
252
278
  var MAX_LIMIT = 100;
253
279
  var DEFAULT_LIMIT = 20;
@@ -739,7 +765,7 @@ function fromResponse(offerResponse) {
739
765
  };
740
766
  }
741
767
 
742
- // src/core/Client.ts
768
+ // src/core/router/Client.ts
743
769
  function connect(opts) {
744
770
  const u = new URL(opts?.url || "https://router.morpho.dev");
745
771
  if (u.protocol !== "http:" && u.protocol !== "https:") {
@@ -969,6 +995,352 @@ var HttpGetOffersFailedError = class extends Errors.BaseError {
969
995
  }
970
996
  };
971
997
 
998
+ // src/OfferStore/index.ts
999
+ var OfferStore_exports = {};
1000
+ __export(OfferStore_exports, {
1001
+ memory: () => memory
1002
+ });
1003
+ function memory(parameters) {
1004
+ const map = parameters.offers;
1005
+ const filled = parameters.filled;
1006
+ const create = async (parameters2) => {
1007
+ if (map.has(parameters2.offer.hash.toLowerCase())) return parameters2.offer.hash;
1008
+ map.set(parameters2.offer.hash.toLowerCase(), {
1009
+ ...parameters2.offer,
1010
+ status: parameters2.status,
1011
+ metadata: parameters2.metadata
1012
+ });
1013
+ const chainId = parameters2.offer.chainId;
1014
+ const address = parameters2.offer.offering.toLowerCase();
1015
+ const nonce = parameters2.offer.nonce;
1016
+ const filledForChain = filled.get(chainId) || /* @__PURE__ */ new Map();
1017
+ const filledForOffering = filledForChain.get(address) || /* @__PURE__ */ new Map();
1018
+ if (!filledForOffering.has(nonce)) filledForOffering.set(nonce, 0n);
1019
+ filledForChain.set(address, filledForOffering);
1020
+ filled.set(chainId, filledForChain);
1021
+ return Promise.resolve(parameters2.offer.hash);
1022
+ };
1023
+ const sort = (sortBy, sortOrder, a, b) => {
1024
+ sortBy = sortBy || "expiry";
1025
+ sortOrder = sortOrder || "desc";
1026
+ const sortKey = sortBy === "amount" ? "assets" : sortBy;
1027
+ if (a[sortKey] === b[sortKey]) {
1028
+ if (a.hash === b.hash) return 0;
1029
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : b.hash > a.hash ? 1 : -1;
1030
+ }
1031
+ switch (sortBy) {
1032
+ case "rate":
1033
+ if (a.rate === b.rate) {
1034
+ if (a.hash === b.hash) return 0;
1035
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : a.hash > b.hash ? -1 : 1;
1036
+ }
1037
+ return sortOrder === "asc" ? a.rate > b.rate ? 1 : -1 : b.rate > a.rate ? 1 : -1;
1038
+ case "maturity":
1039
+ if (a.maturity === b.maturity) {
1040
+ if (a.hash === b.hash) return 0;
1041
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : a.hash > b.hash ? -1 : 1;
1042
+ }
1043
+ return sortOrder === "asc" ? a.maturity > b.maturity ? 1 : -1 : b.maturity > a.maturity ? 1 : -1;
1044
+ case "expiry":
1045
+ if (a.expiry === b.expiry) {
1046
+ if (a.hash === b.hash) return 0;
1047
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : a.hash > b.hash ? -1 : 1;
1048
+ }
1049
+ return sortOrder === "asc" ? a.expiry > b.expiry ? 1 : -1 : b.expiry > a.expiry ? 1 : -1;
1050
+ case "amount":
1051
+ if (a.assets === b.assets) {
1052
+ if (a.hash === b.hash) return 0;
1053
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : a.hash > b.hash ? -1 : 1;
1054
+ }
1055
+ return sortOrder === "asc" ? a.assets > b.assets ? 1 : -1 : b.assets > a.assets ? 1 : -1;
1056
+ default:
1057
+ if (a.expiry === b.expiry) {
1058
+ if (a.hash === b.hash) return 0;
1059
+ return sortOrder === "asc" ? a.hash > b.hash ? 1 : -1 : a.hash > b.hash ? -1 : 1;
1060
+ }
1061
+ return sortOrder === "asc" ? a.expiry > b.expiry ? 1 : -1 : b.expiry > a.expiry ? 1 : -1;
1062
+ }
1063
+ };
1064
+ return {
1065
+ create,
1066
+ createMany: async (parameters2) => {
1067
+ return Promise.all(
1068
+ parameters2.map((p) => create({ offer: p.offer, status: p.status, metadata: p.metadata }))
1069
+ );
1070
+ },
1071
+ getAll: async (params) => {
1072
+ const { query } = params || {};
1073
+ let {
1074
+ creators,
1075
+ side,
1076
+ chains: chains2,
1077
+ loanTokens,
1078
+ status = ["valid"],
1079
+ callbackAddresses,
1080
+ minAmount,
1081
+ maxAmount,
1082
+ minRate,
1083
+ maxRate,
1084
+ minMaturity,
1085
+ maxMaturity,
1086
+ minExpiry,
1087
+ maxExpiry,
1088
+ collateralAssets,
1089
+ collateralOracles,
1090
+ collateralTuple,
1091
+ minLltv,
1092
+ maxLltv,
1093
+ sortBy = "expiry",
1094
+ sortOrder = "desc",
1095
+ cursor: queryCursor,
1096
+ limit = 20
1097
+ } = query || {};
1098
+ const now = Time.now();
1099
+ const buy = side === "buy";
1100
+ let offers = Array.from(map.values()).map((o) => ({
1101
+ ...o,
1102
+ consumed: filled.get(o.chainId)?.get(o.offering.toLowerCase())?.get(o.nonce) || 0n
1103
+ })).filter((o) => o.consumed < o.assets);
1104
+ const cursor = decodeCursor(queryCursor);
1105
+ if (cursor) {
1106
+ if (cursor.sort !== sortBy || cursor.dir !== sortOrder) {
1107
+ throw new Error("Cursor does not match the current sort parameters");
1108
+ }
1109
+ switch (cursor.sort) {
1110
+ case "rate":
1111
+ offers = offers.filter(
1112
+ (o) => (sortOrder === "asc" ? o.rate >= BigInt(cursor.rate) : o.rate <= BigInt(cursor.rate)) && (o.rate !== BigInt(cursor.rate) || (sortOrder === "asc" ? o.hash > cursor.hash : o.hash < cursor.hash))
1113
+ );
1114
+ break;
1115
+ case "maturity":
1116
+ offers = offers.filter(
1117
+ (o) => (sortOrder === "asc" ? o.maturity >= BigInt(cursor.maturity) : o.maturity <= BigInt(cursor.maturity)) && (o.maturity !== Maturity.from(cursor.maturity) || (sortOrder === "asc" ? o.hash > cursor.hash : o.hash < cursor.hash))
1118
+ );
1119
+ break;
1120
+ case "expiry":
1121
+ offers = offers.filter(
1122
+ (o) => (sortOrder === "asc" ? o.expiry >= cursor.expiry : o.expiry <= cursor.expiry) && (o.expiry !== cursor.expiry || (sortOrder === "asc" ? o.hash > cursor.hash : o.hash < cursor.hash))
1123
+ );
1124
+ break;
1125
+ case "amount":
1126
+ offers = offers.filter(
1127
+ (o) => (sortOrder === "asc" ? o.assets >= BigInt(cursor.assets) : o.assets <= BigInt(cursor.assets)) && (o.assets !== BigInt(cursor.assets) || (sortOrder === "asc" ? o.hash > cursor.hash : o.hash < cursor.hash))
1128
+ );
1129
+ break;
1130
+ default:
1131
+ throw new Error("Invalid sort parameter");
1132
+ }
1133
+ offers = offers.filter((o) => o.hash !== cursor.hash);
1134
+ }
1135
+ creators && (creators = creators.map((c) => c.toLowerCase()));
1136
+ loanTokens && (loanTokens = loanTokens.map((lt) => lt.toLowerCase()));
1137
+ collateralAssets && (collateralAssets = collateralAssets.map((ca) => ca.toLowerCase()));
1138
+ collateralOracles && (collateralOracles = collateralOracles.map((co) => co.toLowerCase()));
1139
+ collateralTuple && (collateralTuple = collateralTuple.map((ct) => ({
1140
+ asset: ct.asset.toLowerCase(),
1141
+ oracle: ct.oracle?.toLowerCase()
1142
+ })));
1143
+ offers = offers.filter((o) => o.expiry >= now);
1144
+ creators && (offers = offers.filter((o) => creators.includes(o.offering.toLowerCase())));
1145
+ side && (offers = offers.filter((o) => o.buy === buy));
1146
+ chains2 && (offers = offers.filter((o) => chains2.includes(Number(o.chainId))));
1147
+ loanTokens && (offers = offers.filter((o) => loanTokens.includes(o.loanToken.toLowerCase())));
1148
+ status && (offers = offers.filter((o) => status.includes(o.status)));
1149
+ callbackAddresses && (offers = offers.filter(
1150
+ (o) => callbackAddresses.includes(o.callback.address.toLowerCase())
1151
+ ));
1152
+ minAmount && (offers = offers.filter((o) => o.assets >= minAmount));
1153
+ maxAmount && (offers = offers.filter((o) => o.assets <= maxAmount));
1154
+ minRate && (offers = offers.filter((o) => o.rate >= minRate));
1155
+ maxRate && (offers = offers.filter((o) => o.rate <= maxRate));
1156
+ minMaturity && (offers = offers.filter((o) => o.maturity >= minMaturity));
1157
+ maxMaturity && (offers = offers.filter((o) => o.maturity <= maxMaturity));
1158
+ minExpiry && (offers = offers.filter((o) => o.expiry >= minExpiry));
1159
+ maxExpiry && (offers = offers.filter((o) => o.expiry <= maxExpiry));
1160
+ collateralAssets && (offers = offers.filter(
1161
+ (o) => o.collaterals.some((c) => collateralAssets.includes(c.asset.toLowerCase()))
1162
+ ));
1163
+ collateralOracles && (offers = offers.filter(
1164
+ (o) => o.collaterals.some((c) => collateralOracles.includes(c.oracle.toLowerCase()))
1165
+ ));
1166
+ collateralTuple && (offers = offers.filter(
1167
+ (o) => o.collaterals.some(
1168
+ (c) => collateralTuple.some(
1169
+ (ct) => c.asset.toLowerCase() === ct.asset.toLowerCase() && (ct.oracle ? c.oracle.toLowerCase() === ct.oracle.toLowerCase() : true) && (ct.lltv ? c.lltv === LLTV.from(BigInt(ct.lltv)) : true)
1170
+ )
1171
+ )
1172
+ ));
1173
+ minLltv && (offers = offers.filter(
1174
+ (o) => o.collaterals.every((c) => c.lltv >= LLTV.from(parseUnits(minLltv.toString(), 16)))
1175
+ ));
1176
+ maxLltv && (offers = offers.filter(
1177
+ (o) => o.collaterals.every((c) => c.lltv <= LLTV.from(parseUnits(maxLltv.toString(), 16)))
1178
+ ));
1179
+ offers = offers.sort((a, b) => sort(sortBy, sortOrder, a, b));
1180
+ let nextCursor = null;
1181
+ if (offers.length > limit) {
1182
+ const last = offers[limit - 1];
1183
+ const base = {
1184
+ sort: sortBy,
1185
+ dir: sortOrder,
1186
+ hash: last.hash
1187
+ };
1188
+ switch (sortBy) {
1189
+ case "rate":
1190
+ base.rate = last.rate.toString();
1191
+ break;
1192
+ case "amount":
1193
+ base.assets = last.assets.toString();
1194
+ break;
1195
+ case "maturity":
1196
+ base.maturity = last.maturity;
1197
+ break;
1198
+ default:
1199
+ base.expiry = last.expiry;
1200
+ }
1201
+ nextCursor = encodeCursor(base);
1202
+ }
1203
+ offers = offers.slice(0, limit);
1204
+ return {
1205
+ offers,
1206
+ nextCursor
1207
+ };
1208
+ },
1209
+ findMatchingOffers: async (params) => {
1210
+ const {
1211
+ side,
1212
+ chainId,
1213
+ rate,
1214
+ collaterals = [],
1215
+ maturity,
1216
+ minMaturity,
1217
+ maxMaturity,
1218
+ loanToken,
1219
+ creator,
1220
+ status,
1221
+ cursor: queryCursor,
1222
+ limit = 20
1223
+ } = params;
1224
+ const now = Time.now();
1225
+ const buy = side !== "buy";
1226
+ const sortOrder = buy ? "asc" : "desc";
1227
+ let offers = Array.from(map.values()).map((o) => ({
1228
+ ...o,
1229
+ consumed: filled.get(o.chainId)?.get(o.offering.toLowerCase())?.get(o.nonce) || 0n
1230
+ })).filter((o) => o.consumed < o.assets);
1231
+ const cursor = decodeCursor(queryCursor);
1232
+ if (cursor) {
1233
+ if (cursor.sort !== "rate" || cursor.dir !== sortOrder) {
1234
+ throw new Error("Cursor does not match the current sort parameters");
1235
+ }
1236
+ offers = offers.filter(
1237
+ (o) => sortOrder === "asc" ? o.rate >= BigInt(cursor.rate) : o.rate <= BigInt(cursor.rate)
1238
+ );
1239
+ offers = offers.filter((o) => o.hash !== cursor.hash);
1240
+ }
1241
+ offers = offers.filter((o) => o.buy === buy);
1242
+ offers = offers.filter((o) => o.chainId === BigInt(chainId));
1243
+ offers = offers.filter((o) => o.expiry >= now);
1244
+ rate && (offers = offers.filter((o) => buy ? o.rate >= rate : o.rate <= rate));
1245
+ collaterals.length > 0 && (offers = offers.filter(
1246
+ (o) => buy ? collaterals.every((c) => {
1247
+ return o.collaterals.some(
1248
+ (oc) => oc.asset.toLowerCase() === c.asset.toLowerCase() && oc.oracle.toLowerCase() === c.oracle.toLowerCase() && oc.lltv === c.lltv
1249
+ );
1250
+ }) : o.collaterals.every((oc) => {
1251
+ return collaterals.some(
1252
+ (c) => oc.asset.toLowerCase() === c.asset.toLowerCase() && oc.oracle.toLowerCase() === c.oracle.toLowerCase() && oc.lltv === c.lltv
1253
+ );
1254
+ })
1255
+ ));
1256
+ maturity && (offers = offers.filter((o) => o.maturity === maturity));
1257
+ minMaturity && (offers = offers.filter((o) => o.maturity >= minMaturity));
1258
+ maxMaturity && (offers = offers.filter((o) => o.maturity <= maxMaturity));
1259
+ loanToken && (offers = offers.filter((o) => o.loanToken.toLowerCase() === loanToken.toLowerCase()));
1260
+ creator && (offers = offers.filter((o) => o.offering.toLowerCase() === creator.toLowerCase()));
1261
+ status && (offers = offers.filter((o) => status.includes(o.status)));
1262
+ const byGroup = /* @__PURE__ */ new Map();
1263
+ for (const offer of offers) {
1264
+ const groupKey = `${offer.chainId}-${offer.offering.toLowerCase()}-${offer.nonce}-${offer.buy}`;
1265
+ const current = byGroup.get(groupKey);
1266
+ if (!current) {
1267
+ byGroup.set(groupKey, offer);
1268
+ continue;
1269
+ }
1270
+ const remainingCandidate = offer.assets - offer.consumed;
1271
+ const remainingCurrent = current.assets - current.consumed;
1272
+ let candidateIsBetter = false;
1273
+ if (offer.buy) {
1274
+ if (offer.rate !== current.rate) candidateIsBetter = offer.rate < current.rate;
1275
+ else if (remainingCandidate !== remainingCurrent)
1276
+ candidateIsBetter = remainingCandidate > remainingCurrent;
1277
+ else if (offer.maturity !== current.maturity)
1278
+ candidateIsBetter = offer.maturity > current.maturity;
1279
+ else candidateIsBetter = offer.hash < current.hash;
1280
+ } else {
1281
+ if (offer.rate !== current.rate) candidateIsBetter = offer.rate > current.rate;
1282
+ else if (remainingCandidate !== remainingCurrent)
1283
+ candidateIsBetter = remainingCandidate > remainingCurrent;
1284
+ else if (offer.maturity !== current.maturity)
1285
+ candidateIsBetter = offer.maturity > current.maturity;
1286
+ else candidateIsBetter = offer.hash < current.hash;
1287
+ }
1288
+ if (candidateIsBetter) byGroup.set(groupKey, offer);
1289
+ }
1290
+ offers = Array.from(byGroup.values());
1291
+ offers = offers.sort((a, b) => sort("rate", sortOrder, a, b));
1292
+ let nextCursor = null;
1293
+ if (offers.length > limit) {
1294
+ const last = offers[limit - 1];
1295
+ nextCursor = encodeCursor({
1296
+ sort: "rate",
1297
+ dir: sortOrder,
1298
+ hash: last.hash,
1299
+ rate: last.rate.toString()
1300
+ });
1301
+ }
1302
+ offers = offers.slice(0, limit);
1303
+ return {
1304
+ offers,
1305
+ nextCursor
1306
+ };
1307
+ },
1308
+ delete: async (hash) => {
1309
+ if (!map.has(hash.toLowerCase())) return false;
1310
+ map.delete(hash.toLowerCase());
1311
+ return true;
1312
+ },
1313
+ deleteMany: async (hashes) => {
1314
+ let deleted = 0;
1315
+ for (const hash of hashes) {
1316
+ if (map.has(hash.toLowerCase())) {
1317
+ map.delete(hash.toLowerCase());
1318
+ deleted++;
1319
+ }
1320
+ }
1321
+ return deleted;
1322
+ },
1323
+ updateStatus: async (parameters2) => {
1324
+ if (!map.has(parameters2.offerHash.toLowerCase())) return;
1325
+ map.set(parameters2.offerHash.toLowerCase(), {
1326
+ ...map.get(parameters2.offerHash.toLowerCase()),
1327
+ status: parameters2.status,
1328
+ metadata: parameters2.metadata
1329
+ });
1330
+ },
1331
+ updateConsumedAmount: async (parameters2) => {
1332
+ const chainId = parameters2.chainId;
1333
+ const address = parameters2.offering.toLowerCase();
1334
+ const nonce = parameters2.nonce;
1335
+ const filledForChain = filled.get(chainId) || /* @__PURE__ */ new Map();
1336
+ const filledForOffering = filledForChain.get(address) || /* @__PURE__ */ new Map();
1337
+ filledForOffering.set(nonce, parameters2.consumed);
1338
+ filledForChain.set(address, filledForOffering);
1339
+ filled.set(chainId, filledForChain);
1340
+ }
1341
+ };
1342
+ }
1343
+
972
1344
  // src/RouterEvent.ts
973
1345
  var RouterEvent_exports = {};
974
1346
  __export(RouterEvent_exports, {
@@ -1203,6 +1575,6 @@ function morpho(parameters) {
1203
1575
  ];
1204
1576
  }
1205
1577
 
1206
- export { Chain_exports as Chain, Client_exports as Router, RouterEvent_exports as RouterEvent, RouterOffer_exports as RouterOffer, Validation_exports as Validation, ValidationRule_exports as ValidationRule, batch, decodeCursor, encodeCursor, poll, validateCursor, wait };
1578
+ export { Chain_exports as Chain, OfferStore_exports as OfferStore, Client_exports as Router, RouterEvent_exports as RouterEvent, RouterOffer_exports as RouterOffer, utils_exports as Utils, Validation_exports as Validation, ValidationRule_exports as ValidationRule };
1207
1579
  //# sourceMappingURL=index.browser.mjs.map
1208
1580
  //# sourceMappingURL=index.browser.mjs.map