@coinlist-co/react 0.12.2-rc.7b430dd → 0.12.2-rc.818bed6

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 (31) hide show
  1. package/dist/{chunk-DCW7NQXH.js → chunk-2HCSM3FB.js} +52 -19
  2. package/dist/chunk-2HCSM3FB.js.map +1 -0
  3. package/dist/{chunk-VH34YC3Q.js → chunk-OUFI3D3Q.js} +84 -4
  4. package/dist/chunk-OUFI3D3Q.js.map +1 -0
  5. package/dist/{chunk-MOE5S6CE.js → chunk-YMDYLYL3.js} +954 -441
  6. package/dist/chunk-YMDYLYL3.js.map +1 -0
  7. package/dist/client/index.cjs +12477 -8512
  8. package/dist/client/index.cjs.map +1 -1
  9. package/dist/client/index.d.cts +1965 -229
  10. package/dist/client/index.d.ts +1965 -229
  11. package/dist/client/index.js +9118 -5742
  12. package/dist/client/index.js.map +1 -1
  13. package/dist/server/index.cjs +844 -142
  14. package/dist/server/index.cjs.map +1 -1
  15. package/dist/server/index.d.cts +72 -41
  16. package/dist/server/index.d.ts +72 -41
  17. package/dist/server/index.js +323 -65
  18. package/dist/server/index.js.map +1 -1
  19. package/dist/{tokens-namespace-CIWBtgt2.d.cts → time-DJU6E8KK.d.cts} +943 -192
  20. package/dist/{tokens-namespace-CIWBtgt2.d.ts → time-DJU6E8KK.d.ts} +943 -192
  21. package/dist/{token-registry-snapshot-CqI6dXM_.d.cts → token-registry-snapshot-B0xCp3GD.d.cts} +74 -8
  22. package/dist/{token-registry-snapshot-BNBNuDu1.d.ts → token-registry-snapshot-DGG5N27C.d.ts} +74 -8
  23. package/dist/universal/index.cjs +1036 -439
  24. package/dist/universal/index.cjs.map +1 -1
  25. package/dist/universal/index.d.cts +105 -5
  26. package/dist/universal/index.d.ts +105 -5
  27. package/dist/universal/index.js +48 -2
  28. package/package.json +1 -1
  29. package/dist/chunk-DCW7NQXH.js.map +0 -1
  30. package/dist/chunk-MOE5S6CE.js.map +0 -1
  31. package/dist/chunk-VH34YC3Q.js.map +0 -1
@@ -27,11 +27,24 @@ __export(universal_exports, {
27
27
  AssetIconUrl: () => AssetIconUrl,
28
28
  AssetId: () => AssetId,
29
29
  AssetSymbol: () => AssetSymbol,
30
+ AsyncOfferDetail: () => AsyncOfferDetail,
30
31
  AuthorizationCode: () => AuthorizationCode,
31
32
  BPS_DENOM: () => BPS_DENOM,
32
33
  Blockchain: () => Blockchain,
33
34
  BlockchainAmount: () => BlockchainAmount,
34
35
  Bps: () => Bps,
36
+ CENTRIFUGE_INDICATIVE_QUOTE_AMOUNT: () => CENTRIFUGE_INDICATIVE_QUOTE_AMOUNT,
37
+ CENTRIFUGE_POLL_INTERVAL_MS: () => CENTRIFUGE_POLL_INTERVAL_MS,
38
+ CentrifugeNamespaceImpl: () => CentrifugeNamespaceImpl,
39
+ CentrifugeVaultBuyTransaction: () => CentrifugeVaultBuyTransaction,
40
+ CentrifugeVaultClaimProceedsTransaction: () => CentrifugeVaultClaimProceedsTransaction,
41
+ CentrifugeVaultClaimTransaction: () => CentrifugeVaultClaimTransaction,
42
+ CentrifugeVaultLeg: () => CentrifugeVaultLeg,
43
+ CentrifugeVaultLegId: () => CentrifugeVaultLegId,
44
+ CentrifugeVaultPosition: () => CentrifugeVaultPosition,
45
+ CentrifugeVaultQuote: () => CentrifugeVaultQuote,
46
+ CentrifugeVaultRedeemPosition: () => CentrifugeVaultRedeemPosition,
47
+ CentrifugeVaultStatus: () => CentrifugeVaultStatus,
35
48
  Chain: () => Chain,
36
49
  ClientCredentialsOAuth: () => ClientCredentialsOAuth,
37
50
  ClientId: () => ClientId,
@@ -51,6 +64,7 @@ __export(universal_exports, {
51
64
  DocumentSubmission: () => DocumentSubmission,
52
65
  ERC20_ABI: () => ERC20_ABI,
53
66
  ETHEREUM_CHAINS: () => ETHEREUM_CHAINS,
67
+ EpochMillis: () => EpochMillis,
54
68
  Erc20NamespaceImpl: () => Erc20NamespaceImpl,
55
69
  EthereumChain: () => EthereumChain,
56
70
  EvmContractAddress: () => EvmContractAddress,
@@ -71,11 +85,13 @@ __export(universal_exports, {
71
85
  MAX_UINT_256: () => MAX_UINT_256,
72
86
  MathError: () => MathError,
73
87
  Milestone: () => Milestone,
88
+ Millis: () => Millis,
74
89
  NA_AMOUNT_ASSET_UI: () => NA_AMOUNT_ASSET_UI,
75
90
  NotAuthenticatedError: () => NotAuthenticatedError,
76
91
  NotImplementedError: () => NotImplementedError,
77
92
  OAuthRefreshToken: () => OAuthRefreshToken,
78
93
  OAuthSession: () => OAuthSession,
94
+ ONDO_NOT_TRADABLE_CODE: () => ONDO_NOT_TRADABLE_CODE,
79
95
  ONDO_POLL_INTERVAL_MS: () => ONDO_POLL_INTERVAL_MS,
80
96
  ONDO_QUOTE_MAX_TTL_MS: () => ONDO_QUOTE_MAX_TTL_MS,
81
97
  ONDO_SETTLEMENT_ASSET: () => ONDO_SETTLEMENT_ASSET,
@@ -92,6 +108,7 @@ __export(universal_exports, {
92
108
  OfferSlug: () => OfferSlug,
93
109
  OfferSwapContract: () => OfferSwapContract,
94
110
  OfferToken: () => OfferToken,
111
+ OfferVaultContract: () => OfferVaultContract,
95
112
  OffersNamespaceImpl: () => OffersNamespaceImpl,
96
113
  OndoBuyTransaction: () => OndoBuyTransaction,
97
114
  OndoNamespaceImpl: () => OndoNamespaceImpl,
@@ -123,6 +140,7 @@ __export(universal_exports, {
123
140
  SUPERSTATE_SWAP_CONTRACT_ADDRESS_SEPOLIA: () => SUPERSTATE_SWAP_CONTRACT_ADDRESS_SEPOLIA,
124
141
  SWAP_LEVEL: () => SWAP_LEVEL,
125
142
  SWAP_POLL_INTERVAL_MS: () => SWAP_POLL_INTERVAL_MS,
143
+ Seconds: () => Seconds,
126
144
  ShortenedWalletAddress: () => ShortenedWalletAddress,
127
145
  SolanaChain: () => SolanaChain,
128
146
  StablecoinSymbol: () => StablecoinSymbol,
@@ -149,6 +167,7 @@ __export(universal_exports, {
149
167
  ValidationError: () => ValidationError,
150
168
  WalletAddress: () => WalletAddress,
151
169
  WalletOwnershipChallenge: () => WalletOwnershipChallenge,
170
+ WalletSelection: () => WalletSelection,
152
171
  WalletsNamespaceImpl: () => WalletsNamespaceImpl,
153
172
  apiErrorCode: () => apiErrorCode,
154
173
  applyBps: () => applyBps,
@@ -166,18 +185,22 @@ __export(universal_exports, {
166
185
  formatBpsAsPercent: () => formatBpsAsPercent,
167
186
  formatCompactAmount: () => formatCompactAmount,
168
187
  formatRawAmount: () => formatRawAmount,
188
+ formatShareAmount: () => formatShareAmount,
169
189
  formattedPricePerShare: () => formattedPricePerShare,
170
190
  formattedUsdPrice: () => formattedUsdPrice,
171
191
  generatePKCEParams: () => generatePKCEParams,
172
192
  getChainId: () => getChainId,
173
193
  getNetworkName: () => getNetworkName,
174
194
  isChain: () => isChain,
195
+ isExpired: () => isExpired,
175
196
  isOfferType: () => isOfferType,
197
+ isOndoNotTradableError: () => isOndoNotTradableError,
176
198
  isSwapAvailable: () => isSwapAvailable,
177
199
  offerDisplayTokens: () => offerDisplayTokens,
178
200
  ondoQuoteOfferDeadline: () => ondoQuoteOfferDeadline,
179
201
  parseBlockchainAmount: () => parseBlockchainAmount,
180
202
  parseUint256: () => parseUint256,
203
+ resolveCentrifugeVaults: () => resolveCentrifugeVaults,
181
204
  shortenAddress: () => shortenAddress,
182
205
  superstateSwapContractAddress: () => superstateSwapContractAddress,
183
206
  swapSpender: () => swapSpender,
@@ -187,6 +210,15 @@ __export(universal_exports, {
187
210
  });
188
211
  module.exports = __toCommonJS(universal_exports);
189
212
 
213
+ // src/universal/api/internal-access-token-source.ts
214
+ var SentWith = {
215
+ userToken: (token) => ({
216
+ type: "user-token",
217
+ token
218
+ }),
219
+ noUserToken: { type: "no-user-token" }
220
+ };
221
+
190
222
  // src/universal/api/http-attributes.ts
191
223
  var empty = {};
192
224
  var concat = (left, right) => ({
@@ -214,6 +246,10 @@ var retryAttempt = (attempt) => ({
214
246
  var renewAttempted = (value) => ({
215
247
  renewAttempted: value
216
248
  });
249
+ var notRetryable = () => ({ retryable: false });
250
+ var sentWith = (token) => ({
251
+ sentWith: token
252
+ });
217
253
  var requestId = (id) => ({ requestId: id });
218
254
  var getRequestId = (attrs) => attrs?.requestId ?? null;
219
255
  var isProtected = (attrs) => attrs?.protected === true;
@@ -221,6 +257,8 @@ var needUserAgent = (attrs) => attrs?.userAgent === true;
221
257
  var isIdempotent = (attrs) => attrs?.idempotencyKey === true;
222
258
  var getRetryAttempt = (attrs) => attrs?.retryAttempt ?? 0;
223
259
  var wasRenewAttempted = (attrs) => attrs?.renewAttempted === true;
260
+ var isRetryable = (attrs) => attrs?.retryable !== false;
261
+ var getSentWith = (attrs) => attrs?.sentWith === void 0 ? SentWith.noUserToken : SentWith.userToken(attrs.sentWith);
224
262
  var getClientCredentials = (attrs) => attrs?.clientCredentials;
225
263
  var Attributes = {
226
264
  empty,
@@ -236,6 +274,10 @@ var Attributes = {
236
274
  getRetryAttempt,
237
275
  renewAttempted,
238
276
  wasRenewAttempted,
277
+ notRetryable,
278
+ isRetryable,
279
+ sentWith,
280
+ getSentWith,
239
281
  clientCredentials,
240
282
  getClientCredentials,
241
283
  requestId,
@@ -430,50 +472,6 @@ async function generatePKCEParams(config) {
430
472
  };
431
473
  }
432
474
 
433
- // src/universal/types/pagination.ts
434
- var Cursor = (value) => value;
435
- var PaginatedResponse = {
436
- fromDto: (dto, itemMapper) => PaginatedResponse.fromDtoPage(dto, (items) => items.map(itemMapper)),
437
- /**
438
- * For a mapper that decides the page as a whole - one that drops items it
439
- * cannot map, such as `Offer.listFromDto` - rather than item by item. The
440
- * cursors are the wire's either way: dropping an item changes what the
441
- * page holds, not where the next page starts.
442
- */
443
- fromDtoPage: (dto, pageMapper) => ({
444
- data: pageMapper(dto.data),
445
- startingAfter: dto.starting_after ? Cursor(dto.starting_after) : null,
446
- startingBefore: dto.starting_before ? Cursor(dto.starting_before) : null
447
- })
448
- };
449
- var PaginationParams = {
450
- toQueryParams: (params) => {
451
- const queryParams = {};
452
- if (params.after) {
453
- queryParams.starting_after = params.after;
454
- }
455
- if (params.before) {
456
- queryParams.starting_before = params.before;
457
- }
458
- if (params.limit) {
459
- queryParams.limit = params.limit;
460
- }
461
- return queryParams;
462
- }
463
- };
464
-
465
- // src/universal/types/asset.ts
466
- var AssetId = (value) => value;
467
- var AssetCode = (value) => value;
468
- var Asset = {
469
- fromDto: (dto) => ({
470
- id: AssetId(dto.id),
471
- code: AssetCode(dto.code),
472
- name: dto.name,
473
- fractionalDigits: dto.fractional_digits
474
- })
475
- };
476
-
477
475
  // src/universal/types/errors.ts
478
476
  var NotImplementedError = class extends Error {
479
477
  constructor(message = "Not implemented yet") {
@@ -506,39 +504,8 @@ var MathError = class extends Error {
506
504
  }
507
505
  };
508
506
 
509
- // src/universal/core/shared/utils/wire.ts
510
- function unknownTypeError(dto, model) {
511
- const type = dto.type;
512
- throw new ValidationError(
513
- `${model}.type: unknown type ${JSON.stringify(type)}`
514
- );
515
- }
516
- function requiredString(value, field) {
517
- const text = notBlankStringOrNull(value);
518
- if (text === null) {
519
- throw new ValidationError(
520
- `${field}: expected a non-blank string, got ${typeof value === "string" ? "a blank string" : String(value)}`
521
- );
522
- }
523
- return text;
524
- }
525
- function requiredDate(value, field) {
526
- const date = typeof value === "string" ? new Date(value) : null;
527
- if (date === null || Number.isNaN(date.getTime())) {
528
- throw new ValidationError(
529
- `${field}: expected a date, got ${JSON.stringify(value)}`
530
- );
531
- }
532
- return date;
533
- }
534
- function requiredArray(value, field) {
535
- if (!Array.isArray(value)) {
536
- throw new ValidationError(
537
- `${field}: expected an array, got ${typeof value}`
538
- );
539
- }
540
- return value;
541
- }
507
+ // src/universal/core/shared/blockchain/math.ts
508
+ var import_viem = require("viem");
542
509
 
543
510
  // src/universal/types/blockchain/core.ts
544
511
  var ETHEREUM_CHAINS = {
@@ -637,73 +604,769 @@ var StablecoinSymbol = (value) => value;
637
604
  var KnownAssetSymbol = StablecoinSymbol;
638
605
  var Bps = (value) => value;
639
606
 
640
- // src/universal/types/offer.ts
641
- var OfferId = (value) => value;
642
- var OfferSlug = (value) => value;
643
- var OFFER_TYPES = {
644
- "coinlist::token_sale": true,
645
- "superstate::swap": true,
646
- "ondo::swap": true
607
+ // src/universal/core/shared/blockchain/math.ts
608
+ function blockchainAmountFromRawOrThrow({
609
+ label,
610
+ raw,
611
+ decimals
612
+ }) {
613
+ const trimmed = raw.trim();
614
+ if (trimmed === "") {
615
+ throw new ValidationError(`${label}: not a uint256 integer ("${raw}")`);
616
+ }
617
+ let value;
618
+ try {
619
+ value = BigInt(trimmed);
620
+ } catch {
621
+ throw new ValidationError(`${label}: not a uint256 integer ("${raw}")`);
622
+ }
623
+ try {
624
+ return BlockchainAmount({ raw: assertUint256(value), decimals });
625
+ } catch {
626
+ throw new ValidationError(`${label}: out of uint256 bounds (${value})`);
627
+ }
628
+ }
629
+ function parseBlockchainAmount(amount, decimals) {
630
+ const trimmed = amount.trim();
631
+ if (trimmed === "") return { valid: false, reason: { type: "empty" } };
632
+ if (trimmed.startsWith("-")) {
633
+ return { valid: false, reason: { type: "negative" } };
634
+ }
635
+ if (/[eE]/.test(trimmed)) {
636
+ return { valid: false, reason: { type: "invalid-format" } };
637
+ }
638
+ if (trimmed === ".") {
639
+ return { valid: false, reason: { type: "invalid-format" } };
640
+ }
641
+ const normalised = trimmed.replace(/^\./, "0.").replace(/\.$/, "");
642
+ if (!/^\d+(\.\d+)?$/.test(normalised)) {
643
+ return { valid: false, reason: { type: "invalid-format" } };
644
+ }
645
+ const [, fraction = ""] = normalised.split(".");
646
+ if (fraction.length > decimals) {
647
+ return {
648
+ valid: false,
649
+ reason: { type: "too-many-decimals", maxDecimals: decimals }
650
+ };
651
+ }
652
+ try {
653
+ const raw = (0, import_viem.parseUnits)(normalised, decimals);
654
+ if (raw > MAX_UINT_256) {
655
+ return { valid: false, reason: { type: "overflow" } };
656
+ }
657
+ return {
658
+ valid: true,
659
+ amount: BlockchainAmount({ raw, decimals })
660
+ };
661
+ } catch {
662
+ return { valid: false, reason: { type: "invalid-format" } };
663
+ }
664
+ }
665
+
666
+ // src/universal/core/shared/utils/wire.ts
667
+ function unknownTypeError(dto, model) {
668
+ const type = dto.type;
669
+ throw new ValidationError(
670
+ `${model}.type: unknown type ${JSON.stringify(type)}`
671
+ );
672
+ }
673
+ function requiredString(value, field) {
674
+ const text = notBlankStringOrNull(value);
675
+ if (text === null) {
676
+ throw new ValidationError(
677
+ `${field}: expected a non-blank string, got ${typeof value === "string" ? "a blank string" : String(value)}`
678
+ );
679
+ }
680
+ return text;
681
+ }
682
+ function requiredDate(value, field) {
683
+ const date = typeof value === "string" ? new Date(value) : null;
684
+ if (date === null || Number.isNaN(date.getTime())) {
685
+ throw new ValidationError(
686
+ `${field}: expected a date, got ${JSON.stringify(value)}`
687
+ );
688
+ }
689
+ return date;
690
+ }
691
+ function dateOrNull(value, field) {
692
+ return value === null ? null : requiredDate(value, field);
693
+ }
694
+ function decimalOrNull(value) {
695
+ return value === null ? null : DecimalString(value);
696
+ }
697
+ function requiredArray(value, field) {
698
+ if (!Array.isArray(value)) {
699
+ throw new ValidationError(
700
+ `${field}: expected an array, got ${typeof value}`
701
+ );
702
+ }
703
+ return value;
704
+ }
705
+
706
+ // src/universal/types/providers/centrifuge/centrifuge.ts
707
+ var CentrifugeVaultQuote = {
708
+ fromDto: (dto) => {
709
+ const spendDecimals = AssetDecimals(dto.spend_input_decimals);
710
+ const shareDecimals = AssetDecimals(dto.share_decimals);
711
+ return {
712
+ chain: EthereumChain(dto.chain),
713
+ symbol: AssetSymbol(dto.symbol),
714
+ spendInputAmount: blockchainAmountFromRawOrThrow({
715
+ label: "spend_input_amount",
716
+ raw: dto.spend_input_amount,
717
+ decimals: spendDecimals
718
+ }),
719
+ estimatedShares: blockchainAmountFromRawOrThrow({
720
+ label: "estimated_shares",
721
+ raw: dto.estimated_shares,
722
+ decimals: shareDecimals
723
+ }),
724
+ indicativePrice: decimalOrNull(dto.indicative_price),
725
+ minimumInputAmount: dto.minimum_input_amount === null ? null : blockchainAmountFromRawOrThrow({
726
+ label: "minimum_input_amount",
727
+ raw: dto.minimum_input_amount,
728
+ decimals: spendDecimals
729
+ }),
730
+ orderability: parseOrderability(
731
+ dto.can_order,
732
+ dto.reasons,
733
+ "CentrifugeVaultQuote"
734
+ )
735
+ };
736
+ }
647
737
  };
648
- var isOfferType = (value) => Object.keys(OFFER_TYPES).includes(value);
649
- var OfferEditorial = {
650
- /**
651
- * `model` prefixes the field in the error (`'Offer'`, `'OfferDetail'`), so
652
- * the same three checks name the payload that failed them.
653
- */
654
- fromDto: (dto, model) => ({
655
- tagline: requiredString(dto.tagline, `${model}.tagline`),
656
- bannerUrl: requiredString(dto.banner_url, `${model}.banner_url`),
657
- startsAt: requiredDate(dto.starts_at, `${model}.starts_at`)
738
+ var CentrifugeVaultStatus = {
739
+ fromDto: (dto) => ({
740
+ chain: EthereumChain(dto.chain),
741
+ symbol: AssetSymbol(dto.symbol),
742
+ vaultAddress: EvmContractAddress(dto.vault_address),
743
+ linked: dto.linked,
744
+ permissioned: dto.permissioned,
745
+ membershipValidUntil: dateOrNull(
746
+ dto.membership_valid_until,
747
+ "CentrifugeVaultStatus.membership_valid_until"
748
+ ),
749
+ halted: dto.halted,
750
+ priceUpdatedAt: dateOrNull(
751
+ dto.price_updated_at,
752
+ "CentrifugeVaultStatus.price_updated_at"
753
+ ),
754
+ orderability: parseOrderability(
755
+ dto.can_order,
756
+ dto.reasons,
757
+ "CentrifugeVaultStatus"
758
+ ),
759
+ asOf: requiredDate(dto.as_of, "CentrifugeVaultStatus.as_of")
658
760
  })
659
761
  };
660
- var Offer = {
762
+ var CentrifugeVaultBuyTransaction = {
661
763
  fromDto: (dto) => {
662
- const tokens = requiredArray(dto.tokens, "Offer.tokens");
663
- const base2 = {
664
- id: OfferId(dto.id),
665
- slug: OfferSlug(dto.slug),
666
- endsAt: dto.ends_at ? new Date(dto.ends_at) : null,
667
- tokens: OfferToken.listFromDto(tokens)
668
- };
669
- switch (dto.type) {
670
- case "coinlist::token_sale":
671
- return {
672
- ...base2,
673
- ...OfferEditorial.fromDto(dto, "Offer"),
674
- type: dto.type,
675
- logoUrl: requiredString(dto.logo_url, "Offer.logo_url")
676
- };
677
- case "superstate::swap":
678
- return {
679
- ...base2,
680
- ...OfferEditorial.fromDto(dto, "Offer"),
681
- type: dto.type,
682
- logoUrl: notBlankStringOrNull(dto.logo_url)
683
- };
684
- // `tagline`, `banner_url` and `starts_at` arrive as `null` and are left
685
- // on the wire: copying them would hand every consumer a `startsAt` that
686
- // is 1970 for one variant and a date for the others.
687
- case "ondo::swap":
688
- return {
689
- ...base2,
690
- type: dto.type,
691
- logoUrl: notBlankStringOrNull(dto.logo_url)
692
- };
693
- default:
694
- return unknownTypeError(dto, "Offer");
764
+ const spendInputAmount = blockchainAmountFromRawOrThrow({
765
+ label: "spend_input_amount",
766
+ raw: dto.spend_input_amount,
767
+ decimals: AssetDecimals(dto.spend_input_decimals)
768
+ });
769
+ if (spendInputAmount.raw <= 0n) {
770
+ throw new ValidationError(
771
+ `spend_input_amount: must be greater than zero ("${dto.spend_input_amount}") - a deposit of nothing is not a request`
772
+ );
695
773
  }
696
- },
697
- /**
698
- * Maps a page of offers, dropping every offer whose `type` this SDK does not
699
- * name. The same reasoning as {@link OfferToken.listFromDto}: a plain `.map`
700
- * would throw out of `fromDto` and, through `PaginatedResponse.fromDto`,
701
- * reject the whole page, so one offer of an unknown type would blank the
702
- * grid for every offer beside it. A single offer fetched by id still
703
- * throws, because there is nothing beside it to keep.
704
- */
705
- listFromDto: (dtos) => dtos.filter((dto) => isOfferType(dto.type)).map(Offer.fromDto)
706
- };
774
+ return {
775
+ ...parseTransactionCore(dto, "CentrifugeVaultBuyTransaction"),
776
+ spendInputAmount,
777
+ estimatedShares: blockchainAmountFromRawOrThrow({
778
+ label: "estimated_shares",
779
+ raw: dto.estimated_shares,
780
+ decimals: AssetDecimals(dto.share_decimals)
781
+ })
782
+ };
783
+ }
784
+ };
785
+ var CentrifugeVaultClaimTransaction = {
786
+ fromDto: (dto) => ({
787
+ ...parseTransactionCore(dto, "CentrifugeVaultClaimTransaction"),
788
+ claimableShares: blockchainAmountFromRawOrThrow({
789
+ label: "claimable_shares",
790
+ raw: dto.claimable_shares,
791
+ decimals: AssetDecimals(dto.share_decimals)
792
+ })
793
+ })
794
+ };
795
+ var CentrifugeVaultPosition = {
796
+ fromDto: (dto) => {
797
+ const assetDecimals = AssetDecimals(dto.asset_decimals);
798
+ const shareDecimals = AssetDecimals(dto.share_decimals);
799
+ const asset = (label, raw) => blockchainAmountFromRawOrThrow({ label, raw, decimals: assetDecimals });
800
+ const shares = (label, raw) => blockchainAmountFromRawOrThrow({ label, raw, decimals: shareDecimals });
801
+ return {
802
+ chain: EthereumChain(dto.chain),
803
+ symbol: AssetSymbol(dto.symbol),
804
+ walletAddress: EvmWalletAddress(dto.wallet_address),
805
+ status: dto.status,
806
+ requested: asset("requested", dto.requested),
807
+ pending: asset("pending", dto.pending),
808
+ filledAssets: asset("filled_assets", dto.filled_assets),
809
+ earnedShares: shares("earned_shares", dto.earned_shares),
810
+ claimedShares: shares("claimed_shares", dto.claimed_shares),
811
+ claimableShares: shares("claimable_shares", dto.claimable_shares),
812
+ shareBalance: shares("share_balance", dto.share_balance),
813
+ averagePrice: decimalOrNull(dto.average_price),
814
+ frozen: dto.frozen,
815
+ asOf: requiredDate(dto.as_of, "CentrifugeVaultPosition.as_of")
816
+ };
817
+ }
818
+ };
819
+ var CentrifugeVaultRedeemPosition = {
820
+ fromDto: (dto) => ({
821
+ chain: EthereumChain(dto.chain),
822
+ symbol: AssetSymbol(dto.symbol),
823
+ walletAddress: EvmWalletAddress(dto.wallet_address),
824
+ status: dto.status,
825
+ pending: blockchainAmountFromRawOrThrow({
826
+ label: "pending",
827
+ raw: dto.pending,
828
+ decimals: AssetDecimals(dto.share_decimals)
829
+ }),
830
+ claimableAssets: blockchainAmountFromRawOrThrow({
831
+ label: "claimable_assets",
832
+ raw: dto.claimable_assets,
833
+ decimals: AssetDecimals(dto.asset_decimals)
834
+ }),
835
+ frozen: dto.frozen,
836
+ asOf: requiredDate(dto.as_of, "CentrifugeVaultRedeemPosition.as_of")
837
+ })
838
+ };
839
+ var CentrifugeVaultLeg = {
840
+ /**
841
+ * What a claim on the leg would collect: shares for `invest`, the funding
842
+ * token for `redeem`.
843
+ */
844
+ claimable: (leg) => {
845
+ switch (leg.direction) {
846
+ case "invest":
847
+ return leg.position.claimableShares;
848
+ case "redeem":
849
+ return leg.position.claimableAssets;
850
+ default: {
851
+ const exhaustive = leg;
852
+ return exhaustive;
853
+ }
854
+ }
855
+ },
856
+ /** Whether the leg has anything queued or anything ready to claim. */
857
+ isActive: (leg) => leg.position.pending.raw > 0n || CentrifugeVaultLeg.claimable(leg).raw > 0n
858
+ };
859
+ var CentrifugeVaultLegId = {
860
+ /** Addresses compare case-insensitively: frontline echoes them lower case. */
861
+ of: (leg) => [
862
+ leg.direction,
863
+ leg.position.chain,
864
+ leg.position.walletAddress.toLowerCase()
865
+ ].join(":")
866
+ };
867
+ var CentrifugeVaultClaimProceedsTransaction = {
868
+ fromDto: (dto) => ({
869
+ ...parseTransactionCore(dto, "CentrifugeVaultClaimProceedsTransaction"),
870
+ claimableAssets: blockchainAmountFromRawOrThrow({
871
+ label: "claimable_assets",
872
+ raw: dto.claimable_assets,
873
+ decimals: AssetDecimals(dto.asset_decimals)
874
+ })
875
+ })
876
+ };
877
+ function parseOrderability(canOrder, reasons, model) {
878
+ const [first, ...rest] = reasons;
879
+ if (canOrder) {
880
+ if (first !== void 0) {
881
+ throw new ValidationError(
882
+ `${model}.reasons: expected none when can_order is true, got ${JSON.stringify(reasons)}`
883
+ );
884
+ }
885
+ return { type: "orderable" };
886
+ }
887
+ if (first === void 0) {
888
+ throw new ValidationError(
889
+ `${model}.reasons: expected at least one when can_order is false`
890
+ );
891
+ }
892
+ return { type: "blocked", reasons: [first, ...rest] };
893
+ }
894
+ function parseTransactionCore(dto, model) {
895
+ return {
896
+ tx: {
897
+ to: EvmContractAddress(dto.to),
898
+ data: HexEncodedTransactionData(dto.data)
899
+ },
900
+ expiresAt: dateOrNull(dto.expires_at, `${model}.expires_at`)
901
+ };
902
+ }
903
+
904
+ // src/universal/api/frontline/providers/centrifuge/centrifuge.ts
905
+ async function getCentrifugeVaultQuote(api, params) {
906
+ const dto = await api.send({
907
+ method: "GET",
908
+ url: "/v1/centrifuge/vault/quote",
909
+ queryParams: {
910
+ symbol: params.symbol,
911
+ chain: params.chain,
912
+ amount: params.amount.raw.toString()
913
+ },
914
+ attributes: Attributes.protected()
915
+ });
916
+ return CentrifugeVaultQuote.fromDto(dto);
917
+ }
918
+ async function getCentrifugeVaultStatus(api, params) {
919
+ const dto = await api.send({
920
+ method: "GET",
921
+ url: "/v1/centrifuge/vault/status",
922
+ queryParams: {
923
+ symbol: params.symbol,
924
+ chain: params.chain
925
+ },
926
+ attributes: Attributes.protected()
927
+ });
928
+ return CentrifugeVaultStatus.fromDto(dto);
929
+ }
930
+ async function buildCentrifugeVaultBuy(api, params) {
931
+ const dto = await api.send({
932
+ method: "POST",
933
+ url: "/v1/centrifuge/vault/invest",
934
+ body: {
935
+ ...walletFields(params),
936
+ amount: params.amount.raw.toString()
937
+ },
938
+ attributes: Attributes.protected()
939
+ });
940
+ if (dto.spend_input_decimals !== params.amount.decimals) {
941
+ throw new ValidationError(
942
+ `spend_input_decimals: the request was priced in ${dto.spend_input_decimals} decimals but the deposit was sized in ${params.amount.decimals}`
943
+ );
944
+ }
945
+ return CentrifugeVaultBuyTransaction.fromDto(dto);
946
+ }
947
+ async function getCentrifugeVaultPosition(api, params) {
948
+ const dto = await api.send({
949
+ method: "GET",
950
+ url: "/v1/centrifuge/vault/position",
951
+ queryParams: walletFields(params),
952
+ attributes: Attributes.protected()
953
+ });
954
+ return CentrifugeVaultPosition.fromDto(dto);
955
+ }
956
+ async function getCentrifugeVaultRedeemPosition(api, params) {
957
+ const dto = await api.send({
958
+ method: "GET",
959
+ url: "/v1/centrifuge/vault/redeem-position",
960
+ queryParams: walletFields(params),
961
+ attributes: Attributes.protected()
962
+ });
963
+ return CentrifugeVaultRedeemPosition.fromDto(dto);
964
+ }
965
+ async function createCentrifugeVaultClaim(api, params) {
966
+ const dto = await api.send({
967
+ method: "POST",
968
+ url: "/v1/centrifuge/vault/claim",
969
+ body: walletFields(params),
970
+ attributes: Attributes.protected()
971
+ });
972
+ return CentrifugeVaultClaimTransaction.fromDto(dto);
973
+ }
974
+ async function createCentrifugeVaultClaimProceeds(api, params) {
975
+ const dto = await api.send({
976
+ method: "POST",
977
+ url: "/v1/centrifuge/vault/claim-proceeds",
978
+ body: walletFields(params),
979
+ attributes: Attributes.protected()
980
+ });
981
+ return CentrifugeVaultClaimProceedsTransaction.fromDto(dto);
982
+ }
983
+ function walletFields(params) {
984
+ return {
985
+ symbol: params.symbol,
986
+ chain: params.chain,
987
+ wallet_address: params.walletAddress
988
+ };
989
+ }
990
+
991
+ // src/universal/core/shared/observability/log-cause.ts
992
+ var import_viem2 = require("viem");
993
+ function classifyLogCause(error) {
994
+ if (error instanceof HttpError) {
995
+ return httpCause(error);
996
+ }
997
+ if (error instanceof ValidationError) {
998
+ return { type: "validation", message: error.message };
999
+ }
1000
+ if (error instanceof InvariantError) {
1001
+ return { type: "invariant", message: error.message };
1002
+ }
1003
+ if (error instanceof MathError) {
1004
+ return { type: "math", message: error.message };
1005
+ }
1006
+ if (error instanceof NotAuthenticatedError) {
1007
+ return { type: "not-authenticated" };
1008
+ }
1009
+ if (error instanceof NotImplementedError) {
1010
+ return { type: "not-implemented" };
1011
+ }
1012
+ if (error instanceof import_viem2.BaseError) {
1013
+ const http = error.walk((e) => e instanceof HttpError);
1014
+ if (http instanceof HttpError) {
1015
+ return httpCause(http);
1016
+ }
1017
+ return { type: "rpc", reason: rpcFailureReason(error) };
1018
+ }
1019
+ return { type: "generic-error", name: errorName(error) };
1020
+ }
1021
+ function rpcFailureReason(error) {
1022
+ if (error.walk((e) => e instanceof import_viem2.ContractFunctionRevertedError)) {
1023
+ return "reverted";
1024
+ }
1025
+ if (error.walk((e) => e instanceof import_viem2.RpcError)) {
1026
+ return "node-rejected";
1027
+ }
1028
+ if (error.walk(
1029
+ (e) => e instanceof import_viem2.HttpRequestError || e instanceof import_viem2.WebSocketRequestError || e instanceof import_viem2.SocketClosedError || e instanceof import_viem2.TimeoutError
1030
+ )) {
1031
+ return "transport";
1032
+ }
1033
+ if (error instanceof import_viem2.ContractFunctionExecutionError) {
1034
+ return "malformed-response";
1035
+ }
1036
+ return "unknown";
1037
+ }
1038
+ function describeErrorUnredacted(error) {
1039
+ if (error instanceof HttpError) {
1040
+ return describeHttpErrorRedacted(error);
1041
+ }
1042
+ if (error instanceof Error) {
1043
+ return `${error.name}: ${error.message}`;
1044
+ }
1045
+ return `thrown non-error: ${stringifyUnredacted(error)}`;
1046
+ }
1047
+ function stringifyUnredacted(value) {
1048
+ if (value === void 0) return "";
1049
+ try {
1050
+ return JSON.stringify(
1051
+ value,
1052
+ (_key, item) => typeof item === "bigint" ? `${item}` : item
1053
+ ) ?? String(value);
1054
+ } catch (_) {
1055
+ return "<unserializable>";
1056
+ }
1057
+ }
1058
+ function describeHttpErrorRedacted(error) {
1059
+ const code = apiErrorCode(error);
1060
+ const status = error.response.status;
1061
+ return code === null ? `HttpError ${status}` : `HttpError ${status} (${code})`;
1062
+ }
1063
+ function errorName(error) {
1064
+ return error instanceof Error ? error.name : `non-error ${typeof error}`;
1065
+ }
1066
+ function httpCause(error) {
1067
+ return {
1068
+ type: "http",
1069
+ requestId: error.requestId,
1070
+ status: error.response.status,
1071
+ code: apiErrorCode(error),
1072
+ eventId: apiErrorEventId(error)
1073
+ };
1074
+ }
1075
+ function apiErrorEventId(error) {
1076
+ const body = error.response.body;
1077
+ if (typeof body !== "object" || body === null) return null;
1078
+ const eventId = body.event_id;
1079
+ return typeof eventId === "string" ? eventId : null;
1080
+ }
1081
+
1082
+ // src/universal/core/shared/observability/internal-logger.ts
1083
+ function internalLogger(logger, scope) {
1084
+ return logger ? scopedLogger(logger, scope, {}) : noopInternalLogger;
1085
+ }
1086
+ var LEVEL_RANK = {
1087
+ none: 0,
1088
+ error: 1,
1089
+ warn: 2,
1090
+ info: 3,
1091
+ debug: 4
1092
+ };
1093
+ function scopedLogger(logger, scope, bindings) {
1094
+ const admits = (level) => LEVEL_RANK[logger.level()] >= LEVEL_RANK[level];
1095
+ const safe = (event) => ({
1096
+ msg: event.msg,
1097
+ scope,
1098
+ bindings,
1099
+ fields: event.fields ?? {},
1100
+ ...event.cause === void 0 ? {} : { cause: event.cause }
1101
+ });
1102
+ const unredacted = (event) => ({
1103
+ msg: event.msg,
1104
+ scope,
1105
+ bindings,
1106
+ fields: event.fields ?? {}
1107
+ });
1108
+ const self = {
1109
+ child: (binding) => scopedLogger(logger, scope, { ...bindings, ...binding }),
1110
+ debug: (event) => {
1111
+ if (admits("debug")) logger.debug(() => unredacted(event()));
1112
+ },
1113
+ info: (event) => {
1114
+ if (admits("info")) logger.info(() => safe(event()));
1115
+ },
1116
+ warn: (event) => {
1117
+ if (admits("warn")) logger.warn(() => safe(event()));
1118
+ },
1119
+ error: (event) => {
1120
+ if (admits("error")) logger.error(() => safe(event()));
1121
+ },
1122
+ failure: (event, error) => {
1123
+ if (admits("debug"))
1124
+ logger.debug(() => unredacted(verbatim(event(), error)));
1125
+ if (admits("error")) logger.error(() => safe(classified(event(), error)));
1126
+ },
1127
+ warning: (event, error) => {
1128
+ if (admits("debug"))
1129
+ logger.debug(() => unredacted(verbatim(event(), error)));
1130
+ if (admits("warn")) logger.warn(() => safe(classified(event(), error)));
1131
+ },
1132
+ wrap: async (op, params, run) => {
1133
+ const opLog = self.child({ op });
1134
+ opLog.debug(() => ({ msg: "call", fields: { params } }));
1135
+ try {
1136
+ return await run();
1137
+ } catch (error) {
1138
+ opLog.failure(() => ({ msg: "call failed" }), error);
1139
+ throw error;
1140
+ }
1141
+ }
1142
+ };
1143
+ return self;
1144
+ }
1145
+ function verbatim(event, error) {
1146
+ return {
1147
+ msg: event.msg,
1148
+ fields: { ...event.fields, error: describeErrorUnredacted(error) }
1149
+ };
1150
+ }
1151
+ function classified(event, error) {
1152
+ return { ...event, cause: event.cause ?? classifyLogCause(error) };
1153
+ }
1154
+ var noopInternalLogger = {
1155
+ child: () => noopInternalLogger,
1156
+ debug: () => void 0,
1157
+ info: () => void 0,
1158
+ warn: () => void 0,
1159
+ error: () => void 0,
1160
+ failure: () => void 0,
1161
+ warning: () => void 0,
1162
+ wrap: (_op, _params, run) => run()
1163
+ };
1164
+
1165
+ // src/universal/core/checkout/centrifuge/centrifuge-namespace.ts
1166
+ var CentrifugeNamespaceImpl = class {
1167
+ constructor(ctx) {
1168
+ this.ctx = ctx;
1169
+ this.log = internalLogger(ctx.logger, "CENTRIFUGE");
1170
+ }
1171
+ async getQuote(params) {
1172
+ return this.log.wrap("getQuote", params, async () => {
1173
+ await this.ctx.ensureUserAuthenticated();
1174
+ return getCentrifugeVaultQuote(this.ctx.api, params);
1175
+ });
1176
+ }
1177
+ async getVaultStatus(params) {
1178
+ return this.log.wrap("getVaultStatus", params, async () => {
1179
+ await this.ctx.ensureUserAuthenticated();
1180
+ return getCentrifugeVaultStatus(this.ctx.api, params);
1181
+ });
1182
+ }
1183
+ async getPosition(params) {
1184
+ return this.log.wrap("getPosition", params, async () => {
1185
+ await this.ctx.ensureUserAuthenticated();
1186
+ return getCentrifugeVaultPosition(this.ctx.api, params);
1187
+ });
1188
+ }
1189
+ async getRedeemPosition(params) {
1190
+ return this.log.wrap("getRedeemPosition", params, async () => {
1191
+ await this.ctx.ensureUserAuthenticated();
1192
+ return getCentrifugeVaultRedeemPosition(this.ctx.api, params);
1193
+ });
1194
+ }
1195
+ async createClaim(params) {
1196
+ return this.log.wrap("createClaim", params, async () => {
1197
+ await this.ctx.ensureUserAuthenticated();
1198
+ return createCentrifugeVaultClaim(this.ctx.api, params);
1199
+ });
1200
+ }
1201
+ async createClaimProceeds(params) {
1202
+ return this.log.wrap("createClaimProceeds", params, async () => {
1203
+ await this.ctx.ensureUserAuthenticated();
1204
+ return createCentrifugeVaultClaimProceeds(this.ctx.api, params);
1205
+ });
1206
+ }
1207
+ async buildBuyTransaction(params) {
1208
+ return this.log.wrap("buildBuyTransaction", params, async () => {
1209
+ await this.ctx.ensureUserAuthenticated();
1210
+ return buildCentrifugeVaultBuy(this.ctx.api, params);
1211
+ });
1212
+ }
1213
+ };
1214
+
1215
+ // src/universal/core/checkout/centrifuge/constants.ts
1216
+ var CENTRIFUGE_POLL_INTERVAL_MS = 15e3;
1217
+ var CENTRIFUGE_INDICATIVE_QUOTE_AMOUNT = BlockchainAmount({
1218
+ raw: 100000000n,
1219
+ decimals: STABLE_DECIMALS
1220
+ });
1221
+
1222
+ // src/universal/core/checkout/centrifuge/vaults.ts
1223
+ function resolveCentrifugeVaults(offer, lookup) {
1224
+ return offer.vaultContracts.map((contract) => {
1225
+ const { chain } = contract;
1226
+ if (!isEthereumChain(chain)) {
1227
+ return { type: "unresolved", chain, missing: "evm-chain" };
1228
+ }
1229
+ const onChain = (role) => offer.tokens.filter(
1230
+ (token) => token.role === role && token.chain === chain
1231
+ );
1232
+ const share = firstKnown(onChain("vault"), lookup);
1233
+ if (share === null) {
1234
+ return { type: "unresolved", chain, missing: "share-token" };
1235
+ }
1236
+ const funding = firstKnown(onChain("funding"), lookup);
1237
+ if (funding === null) {
1238
+ return { type: "unresolved", chain, missing: "funding-token" };
1239
+ }
1240
+ return {
1241
+ type: "resolved",
1242
+ vault: { chain, proxy: contract.address, share, funding }
1243
+ };
1244
+ });
1245
+ }
1246
+ function firstKnown(tokens, lookup) {
1247
+ for (const token of tokens) {
1248
+ const metadata = lookup(token);
1249
+ if (metadata !== null) return metadata;
1250
+ }
1251
+ return null;
1252
+ }
1253
+ function isEthereumChain(chain) {
1254
+ return chain in ETHEREUM_CHAINS;
1255
+ }
1256
+
1257
+ // src/universal/types/pagination.ts
1258
+ var Cursor = (value) => value;
1259
+ var PaginatedResponse = {
1260
+ fromDto: (dto, itemMapper) => PaginatedResponse.fromDtoPage(dto, (items) => items.map(itemMapper)),
1261
+ /**
1262
+ * For a mapper that decides the page as a whole - one that drops items it
1263
+ * cannot map, such as `Offer.listFromDto` - rather than item by item. The
1264
+ * cursors are the wire's either way: dropping an item changes what the
1265
+ * page holds, not where the next page starts.
1266
+ */
1267
+ fromDtoPage: (dto, pageMapper) => ({
1268
+ data: pageMapper(dto.data),
1269
+ startingAfter: dto.starting_after ? Cursor(dto.starting_after) : null,
1270
+ startingBefore: dto.starting_before ? Cursor(dto.starting_before) : null
1271
+ })
1272
+ };
1273
+ var PaginationParams = {
1274
+ toQueryParams: (params) => {
1275
+ const queryParams = {};
1276
+ if (params.after) {
1277
+ queryParams.starting_after = params.after;
1278
+ }
1279
+ if (params.before) {
1280
+ queryParams.starting_before = params.before;
1281
+ }
1282
+ if (params.limit) {
1283
+ queryParams.limit = params.limit;
1284
+ }
1285
+ return queryParams;
1286
+ }
1287
+ };
1288
+
1289
+ // src/universal/types/asset.ts
1290
+ var AssetId = (value) => value;
1291
+ var AssetCode = (value) => value;
1292
+ var Asset = {
1293
+ fromDto: (dto) => ({
1294
+ id: AssetId(dto.id),
1295
+ code: AssetCode(dto.code),
1296
+ name: dto.name,
1297
+ fractionalDigits: dto.fractional_digits
1298
+ })
1299
+ };
1300
+
1301
+ // src/universal/types/offer.ts
1302
+ var OfferId = (value) => value;
1303
+ var OfferSlug = (value) => value;
1304
+ var OFFER_TYPES = {
1305
+ "coinlist::token_sale": true,
1306
+ "superstate::swap": true,
1307
+ "ondo::swap": true,
1308
+ "centrifuge::vault": true
1309
+ };
1310
+ var isOfferType = (value) => Object.keys(OFFER_TYPES).includes(value);
1311
+ var OfferEditorial = {
1312
+ /**
1313
+ * `model` prefixes the field in the error (`'Offer'`, `'OfferDetail'`), so
1314
+ * the same three checks name the payload that failed them.
1315
+ */
1316
+ fromDto: (dto, model) => ({
1317
+ tagline: requiredString(dto.tagline, `${model}.tagline`),
1318
+ bannerUrl: requiredString(dto.banner_url, `${model}.banner_url`),
1319
+ startsAt: requiredDate(dto.starts_at, `${model}.starts_at`)
1320
+ })
1321
+ };
1322
+ var Offer = {
1323
+ fromDto: (dto) => {
1324
+ const tokens = requiredArray(dto.tokens, "Offer.tokens");
1325
+ const base2 = {
1326
+ id: OfferId(dto.id),
1327
+ slug: OfferSlug(dto.slug),
1328
+ endsAt: dto.ends_at ? new Date(dto.ends_at) : null,
1329
+ tokens: OfferToken.listFromDto(tokens)
1330
+ };
1331
+ switch (dto.type) {
1332
+ case "coinlist::token_sale":
1333
+ return {
1334
+ ...base2,
1335
+ ...OfferEditorial.fromDto(dto, "Offer"),
1336
+ type: dto.type,
1337
+ logoUrl: requiredString(dto.logo_url, "Offer.logo_url")
1338
+ };
1339
+ case "superstate::swap":
1340
+ return {
1341
+ ...base2,
1342
+ ...OfferEditorial.fromDto(dto, "Offer"),
1343
+ type: dto.type,
1344
+ logoUrl: notBlankStringOrNull(dto.logo_url)
1345
+ };
1346
+ // `tagline`, `banner_url` and `starts_at` arrive as `null` and are left
1347
+ // on the wire: copying them would hand every consumer a `startsAt` that
1348
+ // is 1970 for one variant and a date for the others.
1349
+ case "ondo::swap":
1350
+ case "centrifuge::vault":
1351
+ return {
1352
+ ...base2,
1353
+ type: dto.type,
1354
+ logoUrl: notBlankStringOrNull(dto.logo_url)
1355
+ };
1356
+ default:
1357
+ return unknownTypeError(dto, "Offer");
1358
+ }
1359
+ },
1360
+ /**
1361
+ * Maps a page of offers, dropping every offer whose `type` this SDK does not
1362
+ * name. The same reasoning as {@link OfferToken.listFromDto}: a plain `.map`
1363
+ * would throw out of `fromDto` and, through `PaginatedResponse.fromDto`,
1364
+ * reject the whole page, so one offer of an unknown type would blank the
1365
+ * grid for every offer beside it. A single offer fetched by id still
1366
+ * throws, because there is nothing beside it to keep.
1367
+ */
1368
+ listFromDto: (dtos) => dtos.filter((dto) => isOfferType(dto.type)).map(Offer.fromDto)
1369
+ };
707
1370
  var OfferToken = {
708
1371
  fromDto: (dto) => ({
709
1372
  role: dto.role,
@@ -729,6 +1392,30 @@ var Ticker = (value) => value;
729
1392
  var Isin = (value) => value;
730
1393
 
731
1394
  // src/universal/types/offer-detail.ts
1395
+ var AsyncOfferDetail = {
1396
+ /**
1397
+ * Narrows an offer fetched generically, e.g. on an offer page, to one with
1398
+ * something to claim.
1399
+ *
1400
+ * An exhaustive `switch` rather than a list of async types, so a new offer
1401
+ * type is a compile error here until someone decides whether it settles
1402
+ * later.
1403
+ */
1404
+ is: (offer) => {
1405
+ switch (offer.type) {
1406
+ case "centrifuge::vault":
1407
+ return true;
1408
+ case "ondo::swap":
1409
+ case "superstate::swap":
1410
+ case "coinlist::token_sale":
1411
+ return false;
1412
+ default: {
1413
+ const exhaustive = offer;
1414
+ return exhaustive;
1415
+ }
1416
+ }
1417
+ }
1418
+ };
732
1419
  var OfferOptionId = (value) => value;
733
1420
  var OfferOptionSlug = (value) => value;
734
1421
  var OfferSwapContract = {
@@ -737,6 +1424,19 @@ var OfferSwapContract = {
737
1424
  address: EvmContractAddress(dto.address)
738
1425
  })
739
1426
  };
1427
+ var OfferVaultContract = {
1428
+ fromDto: (dto) => ({
1429
+ chain: Chain(dto.chain),
1430
+ address: EvmContractAddress(dto.address)
1431
+ }),
1432
+ /**
1433
+ * Drops every proxy on a chain this SDK does not name, as
1434
+ * `OfferToken.listFromDto` does: frontline publishes the full offer-token
1435
+ * chain list, which runs ahead of {@link Chain}, and one unmodelled chain
1436
+ * should not throw away the proxies the SDK can use.
1437
+ */
1438
+ listFromDto: (dtos) => dtos.filter((dto) => isChain(dto.chain)).map(OfferVaultContract.fromDto)
1439
+ };
740
1440
  var OfferDetail = {
741
1441
  fromDto: (dto) => {
742
1442
  const fundingAssets = requiredArray(
@@ -799,6 +1499,18 @@ var OfferDetail = {
799
1499
  "OfferDetail.swap_contracts"
800
1500
  ).map(OfferSwapContract.fromDto)
801
1501
  };
1502
+ // No editorial, as for Ondo. `[]` is fine and a missing key is not, for
1503
+ // the same reason as `swap_contracts`: this is the spender a user
1504
+ // approves.
1505
+ case "centrifuge::vault":
1506
+ return {
1507
+ ...base2,
1508
+ type: dto.type,
1509
+ logoUrl: notBlankStringOrNull(dto.logo_url),
1510
+ vaultContracts: OfferVaultContract.listFromDto(
1511
+ requiredArray(dto.vault_contracts, "OfferDetail.vault_contracts")
1512
+ )
1513
+ };
802
1514
  default:
803
1515
  return unknownTypeError(dto, "OfferDetail");
804
1516
  }
@@ -856,246 +1568,72 @@ var ParticipationsPaginationParams = {
856
1568
  }
857
1569
  return queryParams;
858
1570
  }
859
- };
860
- var Participation = {
861
- /** Maps API DTO shape into the SDK participation domain model. */
862
- fromDto: (dto) => {
863
- const walletAddress = notBlankStringOrNull(dto.wallet_address);
864
- return {
865
- id: ParticipationId(dto.id),
866
- offerId: OfferId(dto.offer_id),
867
- offerOptionId: OfferOptionId(dto.offer_option_id),
868
- status: dto.status,
869
- amount: dto.amount,
870
- displayAmount: dto.amount_string,
871
- asset: Asset.fromDto(dto.asset),
872
- chain: Blockchain(dto.chain),
873
- insertedAt: dto.inserted_at ? new Date(dto.inserted_at) : null,
874
- updatedAt: dto.updated_at ? new Date(dto.updated_at) : null,
875
- walletAddress: walletAddress ? WalletAddress(walletAddress) : null
876
- };
877
- }
878
- };
879
- var CreateParticipationParams = {
880
- /** Maps participation creation params into API DTO payload. */
881
- toDto: (params) => ({
882
- offer_id: params.offerId,
883
- offer_option_id: params.offerOptionId,
884
- chain: params.chain,
885
- wallet_address: params.walletAddress,
886
- amount: params.amount,
887
- asset_id: params.assetId,
888
- approval_transaction_hash: params.approvalTransactionHash
889
- })
890
- };
891
-
892
- // src/universal/api/frontline/providers/coin-list/token-sale.ts
893
- async function fetchParticipations(api, offerId) {
894
- return fetchAllPages(
895
- (params) => fetchParticipationsPage(api, params),
896
- { offerId }
897
- );
898
- }
899
- async function fetchParticipationsPage(api, params) {
900
- const pageDto = await api.send({
901
- method: "GET",
902
- url: "/v1/participations",
903
- queryParams: ParticipationsPaginationParams.toQueryParams(params),
904
- attributes: Attributes.protected()
905
- });
906
- return PaginatedResponse.fromDto(pageDto, Participation.fromDto);
907
- }
908
- async function fetchParticipation(api, id) {
909
- const dto = await api.send({
910
- method: "GET",
911
- url: `/v1/participations/${id}`,
912
- attributes: Attributes.protected()
913
- });
914
- return Participation.fromDto(dto);
915
- }
916
- async function createParticipation(api, params) {
917
- const dto = await api.send({
918
- method: "POST",
919
- url: "/v1/participations",
920
- body: CreateParticipationParams.toDto(params),
921
- attributes: Attributes.protected()
922
- });
923
- return Participation.fromDto(dto);
924
- }
925
-
926
- // src/universal/core/shared/observability/log-cause.ts
927
- var import_viem = require("viem");
928
- function classifyLogCause(error) {
929
- if (error instanceof HttpError) {
930
- return httpCause(error);
931
- }
932
- if (error instanceof ValidationError) {
933
- return { type: "validation", message: error.message };
934
- }
935
- if (error instanceof InvariantError) {
936
- return { type: "invariant", message: error.message };
937
- }
938
- if (error instanceof MathError) {
939
- return { type: "math", message: error.message };
940
- }
941
- if (error instanceof NotAuthenticatedError) {
942
- return { type: "not-authenticated" };
943
- }
944
- if (error instanceof NotImplementedError) {
945
- return { type: "not-implemented" };
946
- }
947
- if (error instanceof import_viem.BaseError) {
948
- const http = error.walk((e) => e instanceof HttpError);
949
- if (http instanceof HttpError) {
950
- return httpCause(http);
951
- }
952
- return { type: "rpc", reason: rpcFailureReason(error) };
953
- }
954
- return { type: "generic-error", name: errorName(error) };
955
- }
956
- function rpcFailureReason(error) {
957
- if (error.walk((e) => e instanceof import_viem.ContractFunctionRevertedError)) {
958
- return "reverted";
959
- }
960
- if (error.walk((e) => e instanceof import_viem.RpcError)) {
961
- return "node-rejected";
962
- }
963
- if (error.walk(
964
- (e) => e instanceof import_viem.HttpRequestError || e instanceof import_viem.WebSocketRequestError || e instanceof import_viem.SocketClosedError || e instanceof import_viem.TimeoutError
965
- )) {
966
- return "transport";
967
- }
968
- if (error instanceof import_viem.ContractFunctionExecutionError) {
969
- return "malformed-response";
970
- }
971
- return "unknown";
972
- }
973
- function describeErrorUnredacted(error) {
974
- if (error instanceof HttpError) {
975
- return describeHttpErrorRedacted(error);
976
- }
977
- if (error instanceof Error) {
978
- return `${error.name}: ${error.message}`;
979
- }
980
- return `thrown non-error: ${stringifyUnredacted(error)}`;
981
- }
982
- function stringifyUnredacted(value) {
983
- if (value === void 0) return "";
984
- try {
985
- return JSON.stringify(
986
- value,
987
- (_key, item) => typeof item === "bigint" ? `${item}` : item
988
- ) ?? String(value);
989
- } catch (_) {
990
- return "<unserializable>";
1571
+ };
1572
+ var Participation = {
1573
+ /** Maps API DTO shape into the SDK participation domain model. */
1574
+ fromDto: (dto) => {
1575
+ const walletAddress = notBlankStringOrNull(dto.wallet_address);
1576
+ return {
1577
+ id: ParticipationId(dto.id),
1578
+ offerId: OfferId(dto.offer_id),
1579
+ offerOptionId: OfferOptionId(dto.offer_option_id),
1580
+ status: dto.status,
1581
+ amount: dto.amount,
1582
+ displayAmount: dto.amount_string,
1583
+ asset: Asset.fromDto(dto.asset),
1584
+ chain: Blockchain(dto.chain),
1585
+ insertedAt: dto.inserted_at ? new Date(dto.inserted_at) : null,
1586
+ updatedAt: dto.updated_at ? new Date(dto.updated_at) : null,
1587
+ walletAddress: walletAddress ? WalletAddress(walletAddress) : null
1588
+ };
991
1589
  }
992
- }
993
- function describeHttpErrorRedacted(error) {
994
- const code = apiErrorCode(error);
995
- const status = error.response.status;
996
- return code === null ? `HttpError ${status}` : `HttpError ${status} (${code})`;
997
- }
998
- function errorName(error) {
999
- return error instanceof Error ? error.name : `non-error ${typeof error}`;
1000
- }
1001
- function httpCause(error) {
1002
- return {
1003
- type: "http",
1004
- requestId: error.requestId,
1005
- status: error.response.status,
1006
- code: apiErrorCode(error),
1007
- eventId: apiErrorEventId(error)
1008
- };
1009
- }
1010
- function apiErrorEventId(error) {
1011
- const body = error.response.body;
1012
- if (typeof body !== "object" || body === null) return null;
1013
- const eventId = body.event_id;
1014
- return typeof eventId === "string" ? eventId : null;
1015
- }
1590
+ };
1591
+ var CreateParticipationParams = {
1592
+ /** Maps participation creation params into API DTO payload. */
1593
+ toDto: (params) => ({
1594
+ offer_id: params.offerId,
1595
+ offer_option_id: params.offerOptionId,
1596
+ chain: params.chain,
1597
+ wallet_address: params.walletAddress,
1598
+ amount: params.amount,
1599
+ asset_id: params.assetId,
1600
+ approval_transaction_hash: params.approvalTransactionHash
1601
+ })
1602
+ };
1016
1603
 
1017
- // src/universal/core/shared/observability/internal-logger.ts
1018
- function internalLogger(logger, scope) {
1019
- return logger ? scopedLogger(logger, scope, {}) : noopInternalLogger;
1604
+ // src/universal/api/frontline/providers/coin-list/token-sale.ts
1605
+ async function fetchParticipations(api, offerId) {
1606
+ return fetchAllPages(
1607
+ (params) => fetchParticipationsPage(api, params),
1608
+ { offerId }
1609
+ );
1020
1610
  }
1021
- var LEVEL_RANK = {
1022
- none: 0,
1023
- error: 1,
1024
- warn: 2,
1025
- info: 3,
1026
- debug: 4
1027
- };
1028
- function scopedLogger(logger, scope, bindings) {
1029
- const admits = (level) => LEVEL_RANK[logger.level()] >= LEVEL_RANK[level];
1030
- const safe = (event) => ({
1031
- msg: event.msg,
1032
- scope,
1033
- bindings,
1034
- fields: event.fields ?? {},
1035
- ...event.cause === void 0 ? {} : { cause: event.cause }
1036
- });
1037
- const unredacted = (event) => ({
1038
- msg: event.msg,
1039
- scope,
1040
- bindings,
1041
- fields: event.fields ?? {}
1611
+ async function fetchParticipationsPage(api, params) {
1612
+ const pageDto = await api.send({
1613
+ method: "GET",
1614
+ url: "/v1/participations",
1615
+ queryParams: ParticipationsPaginationParams.toQueryParams(params),
1616
+ attributes: Attributes.protected()
1042
1617
  });
1043
- const self = {
1044
- child: (binding) => scopedLogger(logger, scope, { ...bindings, ...binding }),
1045
- debug: (event) => {
1046
- if (admits("debug")) logger.debug(() => unredacted(event()));
1047
- },
1048
- info: (event) => {
1049
- if (admits("info")) logger.info(() => safe(event()));
1050
- },
1051
- warn: (event) => {
1052
- if (admits("warn")) logger.warn(() => safe(event()));
1053
- },
1054
- error: (event) => {
1055
- if (admits("error")) logger.error(() => safe(event()));
1056
- },
1057
- failure: (event, error) => {
1058
- if (admits("debug"))
1059
- logger.debug(() => unredacted(verbatim(event(), error)));
1060
- if (admits("error")) logger.error(() => safe(classified(event(), error)));
1061
- },
1062
- warning: (event, error) => {
1063
- if (admits("debug"))
1064
- logger.debug(() => unredacted(verbatim(event(), error)));
1065
- if (admits("warn")) logger.warn(() => safe(classified(event(), error)));
1066
- },
1067
- wrap: async (op, params, run) => {
1068
- const opLog = self.child({ op });
1069
- opLog.debug(() => ({ msg: "call", fields: { params } }));
1070
- try {
1071
- return await run();
1072
- } catch (error) {
1073
- opLog.failure(() => ({ msg: "call failed" }), error);
1074
- throw error;
1075
- }
1076
- }
1077
- };
1078
- return self;
1618
+ return PaginatedResponse.fromDto(pageDto, Participation.fromDto);
1079
1619
  }
1080
- function verbatim(event, error) {
1081
- return {
1082
- msg: event.msg,
1083
- fields: { ...event.fields, error: describeErrorUnredacted(error) }
1084
- };
1620
+ async function fetchParticipation(api, id) {
1621
+ const dto = await api.send({
1622
+ method: "GET",
1623
+ url: `/v1/participations/${id}`,
1624
+ attributes: Attributes.protected()
1625
+ });
1626
+ return Participation.fromDto(dto);
1085
1627
  }
1086
- function classified(event, error) {
1087
- return { ...event, cause: event.cause ?? classifyLogCause(error) };
1628
+ async function createParticipation(api, params) {
1629
+ const dto = await api.send({
1630
+ method: "POST",
1631
+ url: "/v1/participations",
1632
+ body: CreateParticipationParams.toDto(params),
1633
+ attributes: Attributes.protected()
1634
+ });
1635
+ return Participation.fromDto(dto);
1088
1636
  }
1089
- var noopInternalLogger = {
1090
- child: () => noopInternalLogger,
1091
- debug: () => void 0,
1092
- info: () => void 0,
1093
- warn: () => void 0,
1094
- error: () => void 0,
1095
- failure: () => void 0,
1096
- warning: () => void 0,
1097
- wrap: (_op, _params, run) => run()
1098
- };
1099
1637
 
1100
1638
  // src/universal/core/checkout/coin-list/token-sale-namespace.ts
1101
1639
  var CoinListTokenSaleNamespaceImpl = class {
@@ -1245,8 +1783,14 @@ function assertPriceFits(raw) {
1245
1783
  }
1246
1784
  }
1247
1785
 
1786
+ // src/universal/core/checkout/ondo/not-tradable.ts
1787
+ var ONDO_NOT_TRADABLE_CODE = "not_tradable";
1788
+ function isOndoNotTradableError(error) {
1789
+ return apiErrorCode(error) === ONDO_NOT_TRADABLE_CODE;
1790
+ }
1791
+
1248
1792
  // src/universal/core/shared/blockchain/formatters.ts
1249
- var import_viem2 = require("viem");
1793
+ var import_viem3 = require("viem");
1250
1794
 
1251
1795
  // src/universal/types/blockchain/ui.ts
1252
1796
  var FormattedAmountUi = (value) => value;
@@ -1265,7 +1809,11 @@ function formatAmount(amount, locale, options) {
1265
1809
  const decimal = formatRawAmount(amount);
1266
1810
  let [integerPart, fractionPart = ""] = decimal.split(".");
1267
1811
  const maxFractionDigits = options?.maxFractionDigits;
1268
- const minFractionDigits = maxFractionDigits !== void 0 ? Math.min(maxFractionDigits, amount.decimals) : Math.min(2, amount.decimals);
1812
+ const minFractionDigits = Math.min(
1813
+ options?.minFractionDigits ?? (maxFractionDigits !== void 0 ? maxFractionDigits : 2),
1814
+ maxFractionDigits ?? amount.decimals,
1815
+ amount.decimals
1816
+ );
1269
1817
  if (maxFractionDigits !== void 0 && fractionPart.length > maxFractionDigits) {
1270
1818
  ({ integerPart, fractionPart } = roundFractionHalfUp(
1271
1819
  integerPart,
@@ -1273,7 +1821,8 @@ function formatAmount(amount, locale, options) {
1273
1821
  maxFractionDigits
1274
1822
  ));
1275
1823
  }
1276
- const fraction = minFractionDigits === 0 ? "" : fractionPart.padEnd(minFractionDigits, "0");
1824
+ const trimmed = fractionPart.replace(/0+$/, "");
1825
+ const fraction = trimmed.padEnd(minFractionDigits, "0");
1277
1826
  const integerFormatted = BigInt(integerPart).toLocaleString(locale);
1278
1827
  if (minFractionDigits === 0 && fraction === "") {
1279
1828
  return FormattedAmountUi(integerFormatted);
@@ -1312,7 +1861,7 @@ function roundFractionHalfUp(integerPart, fractionPart, maxFractionDigits) {
1312
1861
  };
1313
1862
  }
1314
1863
  function formatRawAmount(amount) {
1315
- return (0, import_viem2.formatUnits)(amount.raw, amount.decimals);
1864
+ return (0, import_viem3.formatUnits)(amount.raw, amount.decimals);
1316
1865
  }
1317
1866
  function formatCompactAmount(amount, locale) {
1318
1867
  const value = Number(formatRawAmount(amount));
@@ -1342,6 +1891,14 @@ function assetAmount(amount, symbol) {
1342
1891
  return FormattedAmountAssetUi(`${amount} ${symbol}`);
1343
1892
  }
1344
1893
  var NA_AMOUNT_ASSET_UI = FormattedAmountAssetUi("-");
1894
+ var SHARE_MAX_FRACTION_DIGITS = AssetDecimals(6);
1895
+ var SHARE_MIN_FRACTION_DIGITS = AssetDecimals(2);
1896
+ function formatShareAmount(amount, locale) {
1897
+ return formatAmount(amount, locale, {
1898
+ maxFractionDigits: SHARE_MAX_FRACTION_DIGITS,
1899
+ minFractionDigits: SHARE_MIN_FRACTION_DIGITS
1900
+ });
1901
+ }
1345
1902
  var USD_FRACTION_DIGITS = AssetDecimals(2);
1346
1903
  function formattedUsdPrice(amount, locale) {
1347
1904
  if (!amount) return NA_AMOUNT_ASSET_UI;
@@ -1408,66 +1965,6 @@ function explorerBaseUrl(chain) {
1408
1965
  }
1409
1966
  }
1410
1967
 
1411
- // src/universal/core/shared/blockchain/math.ts
1412
- var import_viem3 = require("viem");
1413
- function blockchainAmountFromRawOrThrow({
1414
- label,
1415
- raw,
1416
- decimals
1417
- }) {
1418
- const trimmed = raw.trim();
1419
- if (trimmed === "") {
1420
- throw new ValidationError(`${label}: not a uint256 integer ("${raw}")`);
1421
- }
1422
- let value;
1423
- try {
1424
- value = BigInt(trimmed);
1425
- } catch {
1426
- throw new ValidationError(`${label}: not a uint256 integer ("${raw}")`);
1427
- }
1428
- try {
1429
- return BlockchainAmount({ raw: assertUint256(value), decimals });
1430
- } catch {
1431
- throw new ValidationError(`${label}: out of uint256 bounds (${value})`);
1432
- }
1433
- }
1434
- function parseBlockchainAmount(amount, decimals) {
1435
- const trimmed = amount.trim();
1436
- if (trimmed === "") return { valid: false, reason: { type: "empty" } };
1437
- if (trimmed.startsWith("-")) {
1438
- return { valid: false, reason: { type: "negative" } };
1439
- }
1440
- if (/[eE]/.test(trimmed)) {
1441
- return { valid: false, reason: { type: "invalid-format" } };
1442
- }
1443
- if (trimmed === ".") {
1444
- return { valid: false, reason: { type: "invalid-format" } };
1445
- }
1446
- const normalised = trimmed.replace(/^\./, "0.").replace(/\.$/, "");
1447
- if (!/^\d+(\.\d+)?$/.test(normalised)) {
1448
- return { valid: false, reason: { type: "invalid-format" } };
1449
- }
1450
- const [, fraction = ""] = normalised.split(".");
1451
- if (fraction.length > decimals) {
1452
- return {
1453
- valid: false,
1454
- reason: { type: "too-many-decimals", maxDecimals: decimals }
1455
- };
1456
- }
1457
- try {
1458
- const raw = (0, import_viem3.parseUnits)(normalised, decimals);
1459
- if (raw > MAX_UINT_256) {
1460
- return { valid: false, reason: { type: "overflow" } };
1461
- }
1462
- return {
1463
- valid: true,
1464
- amount: BlockchainAmount({ raw, decimals })
1465
- };
1466
- } catch {
1467
- return { valid: false, reason: { type: "invalid-format" } };
1468
- }
1469
- }
1470
-
1471
1968
  // src/universal/types/providers/ondo/ondo.ts
1472
1969
  var OndoTradingStatus = {
1473
1970
  fromDto: (dto) => {
@@ -1483,7 +1980,6 @@ var OndoTradingStatus = {
1483
1980
  };
1484
1981
  }
1485
1982
  };
1486
- var decimalOrNull = (value) => value === null ? null : DecimalString(value);
1487
1983
  var OndoQuote = {
1488
1984
  fromDto: (dto) => {
1489
1985
  const assetDecimals = AssetDecimals(dto.asset_decimals);
@@ -3314,7 +3810,9 @@ var TokenRegistrySnapshot = {
3314
3810
  }
3315
3811
  };
3316
3812
  function offerDisplayTokens(offer) {
3317
- const swaps = offer.tokens.filter((token) => token.role === "swap");
3813
+ const swaps = offer.tokens.filter(
3814
+ (token) => token.role === "swap" || token.role === "vault"
3815
+ );
3318
3816
  const distributions = offer.tokens.filter(
3319
3817
  (token) => token.role === "distribution"
3320
3818
  );
@@ -3355,11 +3853,18 @@ var HttpClient = class {
3355
3853
  );
3356
3854
  let response = await this.executeRequest(preparedRequest);
3357
3855
  for (const middleware of this.middleware.afterRequest ?? []) {
3856
+ let retried = false;
3358
3857
  response = await middleware({
3359
3858
  request: preparedRequest,
3360
3859
  response,
3361
- retry: (nextRequest = preparedRequest) => this.runRequestWithAfterMiddleware(nextRequest)
3860
+ retry: (nextRequest = preparedRequest) => {
3861
+ retried = true;
3862
+ return this.runRequestWithAfterMiddleware(nextRequest);
3863
+ }
3362
3864
  });
3865
+ if (retried) {
3866
+ return response;
3867
+ }
3363
3868
  }
3364
3869
  return response;
3365
3870
  }
@@ -3833,6 +4338,27 @@ var RedactedWalletError = {
3833
4338
  fromWalletError: (error) => error.type === "unknown" ? { type: "unknown" } : error
3834
4339
  };
3835
4340
 
4341
+ // src/universal/types/blockchain/wallet-selection.ts
4342
+ var WalletSelection = {
4343
+ /**
4344
+ * Every wallet in display order - embedded first, then the external one -
4345
+ * each address once. Addresses compare case-insensitively, so a host that
4346
+ * hands the same wallet over as both embedded and external sees it once.
4347
+ */
4348
+ all: (selection) => {
4349
+ const seen = /* @__PURE__ */ new Set();
4350
+ return [
4351
+ ...selection.embedded,
4352
+ ...selection.external === null ? [] : [selection.external]
4353
+ ].filter((wallet) => {
4354
+ const key = wallet.address.toLowerCase();
4355
+ if (seen.has(key)) return false;
4356
+ seen.add(key);
4357
+ return true;
4358
+ });
4359
+ }
4360
+ };
4361
+
3836
4362
  // src/universal/types/oauth-session.ts
3837
4363
  var ClientCredentialsOAuth = (value) => value;
3838
4364
  var OAuthRefreshToken = (value) => value;
@@ -3849,6 +4375,54 @@ var OAuthSession = {
3849
4375
  }
3850
4376
  };
3851
4377
 
4378
+ // src/universal/types/time.ts
4379
+ var MAX_EPOCH_MILLIS = 864e13;
4380
+ var EpochMillis = {
4381
+ /**
4382
+ * @throws {@link ValidationError} unless `value` is an integer a `Date` can
4383
+ * represent: at most {@link MAX_EPOCH_MILLIS} either side of the epoch.
4384
+ */
4385
+ of: (value) => {
4386
+ if (!Number.isInteger(value) || Math.abs(value) > MAX_EPOCH_MILLIS) {
4387
+ throw new ValidationError(
4388
+ `EpochMillis must be an integer within \xB1${MAX_EPOCH_MILLIS}, got ${value}`
4389
+ );
4390
+ }
4391
+ return value;
4392
+ },
4393
+ /** The wall clock. Code that needs the time takes a `TimeEff` instead. */
4394
+ now: () => EpochMillis.of(Date.now()),
4395
+ /** @throws {@link ValidationError} for an invalid `Date`. */
4396
+ fromDate: (date) => EpochMillis.of(date.getTime()),
4397
+ /** How long after `from` the instant `to` is; negative if it is before. */
4398
+ elapsed: (from, to) => Millis.of(to - from),
4399
+ plus: (at, duration) => EpochMillis.of(at + duration)
4400
+ };
4401
+ var Millis = {
4402
+ of: (value) => value
4403
+ };
4404
+ var Seconds = {
4405
+ /**
4406
+ * @throws {@link ValidationError} unless `value` is a non-negative integer.
4407
+ */
4408
+ of: (value) => {
4409
+ if (!Number.isInteger(value) || value < 0) {
4410
+ throw new ValidationError(
4411
+ `Seconds must be a non-negative integer, got ${value}`
4412
+ );
4413
+ }
4414
+ return value;
4415
+ },
4416
+ toMillis: (value) => Millis.of(value * 1e3)
4417
+ };
4418
+ function isExpired({
4419
+ expiresAt,
4420
+ now,
4421
+ buffer = Millis.of(0)
4422
+ }) {
4423
+ return now >= expiresAt - buffer;
4424
+ }
4425
+
3852
4426
  // src/universal/types/user.ts
3853
4427
  var UserId = (value) => value;
3854
4428
  var UserEmail = (value) => value;
@@ -3867,11 +4441,24 @@ var User = {
3867
4441
  AssetIconUrl,
3868
4442
  AssetId,
3869
4443
  AssetSymbol,
4444
+ AsyncOfferDetail,
3870
4445
  AuthorizationCode,
3871
4446
  BPS_DENOM,
3872
4447
  Blockchain,
3873
4448
  BlockchainAmount,
3874
4449
  Bps,
4450
+ CENTRIFUGE_INDICATIVE_QUOTE_AMOUNT,
4451
+ CENTRIFUGE_POLL_INTERVAL_MS,
4452
+ CentrifugeNamespaceImpl,
4453
+ CentrifugeVaultBuyTransaction,
4454
+ CentrifugeVaultClaimProceedsTransaction,
4455
+ CentrifugeVaultClaimTransaction,
4456
+ CentrifugeVaultLeg,
4457
+ CentrifugeVaultLegId,
4458
+ CentrifugeVaultPosition,
4459
+ CentrifugeVaultQuote,
4460
+ CentrifugeVaultRedeemPosition,
4461
+ CentrifugeVaultStatus,
3875
4462
  Chain,
3876
4463
  ClientCredentialsOAuth,
3877
4464
  ClientId,
@@ -3891,6 +4478,7 @@ var User = {
3891
4478
  DocumentSubmission,
3892
4479
  ERC20_ABI,
3893
4480
  ETHEREUM_CHAINS,
4481
+ EpochMillis,
3894
4482
  Erc20NamespaceImpl,
3895
4483
  EthereumChain,
3896
4484
  EvmContractAddress,
@@ -3911,11 +4499,13 @@ var User = {
3911
4499
  MAX_UINT_256,
3912
4500
  MathError,
3913
4501
  Milestone,
4502
+ Millis,
3914
4503
  NA_AMOUNT_ASSET_UI,
3915
4504
  NotAuthenticatedError,
3916
4505
  NotImplementedError,
3917
4506
  OAuthRefreshToken,
3918
4507
  OAuthSession,
4508
+ ONDO_NOT_TRADABLE_CODE,
3919
4509
  ONDO_POLL_INTERVAL_MS,
3920
4510
  ONDO_QUOTE_MAX_TTL_MS,
3921
4511
  ONDO_SETTLEMENT_ASSET,
@@ -3932,6 +4522,7 @@ var User = {
3932
4522
  OfferSlug,
3933
4523
  OfferSwapContract,
3934
4524
  OfferToken,
4525
+ OfferVaultContract,
3935
4526
  OffersNamespaceImpl,
3936
4527
  OndoBuyTransaction,
3937
4528
  OndoNamespaceImpl,
@@ -3963,6 +4554,7 @@ var User = {
3963
4554
  SUPERSTATE_SWAP_CONTRACT_ADDRESS_SEPOLIA,
3964
4555
  SWAP_LEVEL,
3965
4556
  SWAP_POLL_INTERVAL_MS,
4557
+ Seconds,
3966
4558
  ShortenedWalletAddress,
3967
4559
  SolanaChain,
3968
4560
  StablecoinSymbol,
@@ -3989,6 +4581,7 @@ var User = {
3989
4581
  ValidationError,
3990
4582
  WalletAddress,
3991
4583
  WalletOwnershipChallenge,
4584
+ WalletSelection,
3992
4585
  WalletsNamespaceImpl,
3993
4586
  apiErrorCode,
3994
4587
  applyBps,
@@ -4006,18 +4599,22 @@ var User = {
4006
4599
  formatBpsAsPercent,
4007
4600
  formatCompactAmount,
4008
4601
  formatRawAmount,
4602
+ formatShareAmount,
4009
4603
  formattedPricePerShare,
4010
4604
  formattedUsdPrice,
4011
4605
  generatePKCEParams,
4012
4606
  getChainId,
4013
4607
  getNetworkName,
4014
4608
  isChain,
4609
+ isExpired,
4015
4610
  isOfferType,
4611
+ isOndoNotTradableError,
4016
4612
  isSwapAvailable,
4017
4613
  offerDisplayTokens,
4018
4614
  ondoQuoteOfferDeadline,
4019
4615
  parseBlockchainAmount,
4020
4616
  parseUint256,
4617
+ resolveCentrifugeVaults,
4021
4618
  shortenAddress,
4022
4619
  superstateSwapContractAddress,
4023
4620
  swapSpender,