@molpha/sdk 0.2.0-dev-20260913100330 → 0.2.0-dev-20261001125531

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { Address } from '@solana/kit';
2
2
  import { Wallet, Idl, AnchorProvider } from '@anchor-lang/core';
3
- import { U as UpstreamQuote, A as APIConfig, a as AssetDomain, b as UpstreamTerms, E as EvmSigner, R as RegistrySelectionConfig, S as Signer, N as NodeKeyVerifier, c as Node, d as NodesInfo, e as SourcePaymentOptions, D as DataUpdateResult, f as SolanaAccountMeta, g as SolanaConnection, h as SolanaAddress, i as NodeKeyVerifierArgs, M as MolphaWallet } from './wallet-DwdBZgl1.js';
4
- export { j as EncKeyBundle, k as RegistryInfo, l as SchnorrSignature, m as gatewaySignerFromWallet, s as signerFromKeypair } from './wallet-DwdBZgl1.js';
3
+ import { U as UpstreamQuote, A as APIConfig, a as AssetDomain, b as UpstreamTerms, E as EvmSigner, R as RegistrySelectionConfig, S as Signer, N as NodeKeyVerifier, c as Node, d as NodesInfo, e as SourcePaymentOptions, f as Attestation, g as SolanaAccountMeta, h as SolanaConnection, i as SolanaAddress, j as NodeKeyVerifierArgs, k as AggregationConfig, M as MolphaWallet } from './wallet-HfGXPpOp.js';
4
+ export { l as AttestationPayload, m as EncKeyBundle, n as NumericConfig, o as RegistryInfo, p as SchnorrSignature, q as gatewaySignerFromWallet, s as signerFromKeypair } from './wallet-HfGXPpOp.js';
5
5
  import BN from 'bn.js';
6
6
 
7
7
  /**
@@ -105,7 +105,11 @@ interface RequestSignedDataOptions {
105
105
  * same config (including `{{secret.*}}` placeholders) every time.
106
106
  */
107
107
  apiConfig: APIConfig;
108
- /** Requested quorum (u8, ≥ the protocol `min_signers`). */
108
+ /**
109
+ * Requested quorum (u8, ≥ the protocol `min_signers`). Median tolerance mode
110
+ * (`apiConfig.aggregation`) additionally requires `>= 3`; lower values are rejected
111
+ * before any request is made.
112
+ */
109
113
  signaturesRequired: number;
110
114
  /**
111
115
  * Solana pubkey (base58) of the subscription owner.
@@ -270,7 +274,7 @@ declare class MolphaGateway {
270
274
  * fund it; without that, such a source throws
271
275
  * {@link UpstreamPaymentRequiredError} carrying the gateway's quote.
272
276
  */
273
- requestSignedData(opts: RequestSignedDataOptions): Promise<DataUpdateResult>;
277
+ requestSignedData(opts: RequestSignedDataOptions): Promise<Attestation>;
274
278
  /**
275
279
  * Resolve the round inputs, fetching only the fields absent from `cached`.
276
280
  * Registry version, redundancy buffer and node count are treated as a unit (one
@@ -286,8 +290,31 @@ declare class MolphaGateway {
286
290
  private fetchWithTimeout;
287
291
  }
288
292
 
293
+ /** Affine coalition key, 32-byte big-endian coordinates (`CoalitionKey` in the program IDL). */
294
+ interface CoalitionKey {
295
+ x: Uint8Array;
296
+ y: Uint8Array;
297
+ }
298
+ /** A signer's public key: SEC1 compressed / uncompressed (bytes or hex), or affine `(x, y)`. */
299
+ type Secp256k1KeyInput = Uint8Array | string | {
300
+ x: Uint8Array | string;
301
+ y: Uint8Array | string;
302
+ };
303
+ /**
304
+ * Affine sum of `keys` as a {@link CoalitionKey}.
305
+ *
306
+ * @throws {Error} on an empty set, an invalid point, or a sum at infinity (the verifier
307
+ * rejects both of the latter as `InvalidAggregateSignature`).
308
+ */
309
+ declare function computeCoalitionKey(keys: Iterable<Secp256k1KeyInput>): CoalitionKey;
310
+
289
311
  /**
290
312
  * Account views and remaining-accounts construction for `submit_attestation`.
313
+ *
314
+ * `submit_attestation` (program 3d01170, `utils/attestation.rs::verify_attestation_core`)
315
+ * takes exactly one `Node` account per set signer bit, read-only, in ascending bit order
316
+ * (`remaining_accounts.len() == popcount(signersBitmap)`); the verifier requires
317
+ * `account == registry.nodes[bit]` and reads each signer's secp256k1 key from it.
291
318
  */
292
319
 
293
320
  /** On-chain `RegistryState` (Anchor camelCase): pointer to the current immutable snapshot. */
@@ -307,6 +334,8 @@ interface RegistryView {
307
334
  nodes: Address[];
308
335
  /** Unix seconds until which this superseded snapshot still verifies; `0n` while current. */
309
336
  graceActiveUntil: bigint;
337
+ /** Inclusive creation time (unix seconds): a version cannot verify a round dated before it existed. */
338
+ activeFrom: bigint;
310
339
  }
311
340
  /** Set-bit indices of a 32-byte big-endian bitmap (full 256-bit scan). */
312
341
  declare function bitmapToIndices(signersBitmapHex: string): number[];
@@ -342,7 +371,7 @@ declare function planIdFromVariant(variant: Record<string, unknown>): PlanId;
342
371
  * `MolphaSolanaClient` — consumer on-chain surface only (subscribe, extend,
343
372
  * submitAttestation, readFeed/readPlan/readSubscription/readRegistry,
344
373
  * getRegistrySelectionConfig, verifyNodeKeysForPrivateApi). Built from an Anchor
345
- * `Program` over the vendored IDL.
374
+ * `Program` over the vendored IDL (program `3d01170`, "Epoch settlements").
346
375
  */
347
376
 
348
377
  type Commitment$1 = NonNullable<ConstructorParameters<typeof AnchorProvider>[2]>["commitment"];
@@ -362,16 +391,17 @@ interface PlanInfo {
362
391
  privateApiEnabled: boolean;
363
392
  isActive: boolean;
364
393
  }
394
+ /**
395
+ * On-chain `Subscription`. The program no longer tracks usage: `used_rounds`,
396
+ * `prepaid_usdc` and the locked `price` were removed (round quota is counted by the
397
+ * gateway's off-chain outbox), so there is no on-chain "rounds used" figure to read.
398
+ */
365
399
  interface SubscriptionInfo {
366
400
  owner: Address;
367
401
  planType: PlanType;
368
- /** USDC base units prepaid on the subscription vault. */
369
- prepaidUsdc: bigint;
370
- /** Locked subscription price in USDC base units for the current period. */
371
- price: bigint;
372
402
  /** Unix timestamp (seconds) until which the subscription is valid. */
373
403
  validUntil: bigint;
374
- usedRounds: bigint;
404
+ /** Round quota per plan snapshot — enforced by the gateway at admission, not on chain. */
375
405
  maxRounds: bigint;
376
406
  delegateCount: number;
377
407
  maxDelegates: number;
@@ -382,15 +412,22 @@ interface SubmitResult {
382
412
  /** Feed PDA written by this submit (`["molpha_feed", sourceId, [signaturesRequired], submitter]`). */
383
413
  feed: Address;
384
414
  }
415
+ /**
416
+ * On-chain `Feed` (Anchor-decoded). `value` is always the signed
417
+ * `AttestationPayload.value` (32 bytes): the oracle value itself when `valueKind` is
418
+ * `value`, or `keccak256(rawValue)` when it is `hash` (the preimage travelled in the
419
+ * submitting instruction). For a tolerance-mode source it is a two's-complement `int256`
420
+ * (see `decodeInt256` / `formatInt256Decimal`).
421
+ */
385
422
  interface FeedAccount {
386
423
  sourceId: number[];
387
- /** Stored payload: raw value (`valueKind.value`) or keccak digest (`valueKind.hash`), ≤ 32 bytes. */
388
424
  value: Uint8Array | number[];
389
425
  valueKind: {
390
426
  value: Record<string, never>;
391
427
  } | {
392
428
  hash: Record<string, never>;
393
429
  };
430
+ submitter: Address;
394
431
  /** u64 unix seconds. */
395
432
  canonicalTimestamp: BN;
396
433
  signaturesRequired: number;
@@ -400,14 +437,39 @@ interface FeedAccount {
400
437
  }
401
438
  /** Anchor-encoded `SubmitAttestationArgs` (camelCase field names). */
402
439
  interface SubmitAttestationArgs {
403
- sourceId: number[];
404
- registryVersion: number;
405
- value: number[];
406
- canonicalTimestamp: BN;
407
- signaturesRequired: number;
408
- aggSigS: number[];
409
- commitment: number[];
410
- signersBitmap: number[];
440
+ attestation: {
441
+ payload: {
442
+ value: number[];
443
+ sourceId: number[];
444
+ registryVersion: number;
445
+ signaturesRequired: number;
446
+ canonicalTimestamp: BN;
447
+ };
448
+ signature: {
449
+ aggSigS: number[];
450
+ commitment: number[];
451
+ signersBitmap: number[];
452
+ };
453
+ };
454
+ /** Optional preimage when `payload.value` is `keccak256(rawValue)`. */
455
+ rawValue: Uint8Array | null;
456
+ coalitionKey: {
457
+ x: number[];
458
+ y: number[];
459
+ };
460
+ }
461
+ interface SubmitAttestationOptions {
462
+ computeUnitLimit?: number;
463
+ /**
464
+ * Precomputed signer coalition key. When omitted, the client fetches signer `Node`
465
+ * accounts and sums their secp256k1 keys ({@link computeCoalitionKey}).
466
+ */
467
+ coalitionKey?: CoalitionKey;
468
+ /**
469
+ * Optional value preimage (maximum 256 bytes). Its keccak256 digest must equal
470
+ * `attestation.payload.value`; the program stores that digest with `valueKind.hash`.
471
+ */
472
+ rawValue?: Uint8Array;
411
473
  }
412
474
  interface CreateClientOpts {
413
475
  connection: SolanaConnection;
@@ -474,17 +536,21 @@ declare class MolphaSolanaClient {
474
536
  private confirmPlanPrice;
475
537
  /**
476
538
  * Submit a gateway attestation via `submit_attestation`. The feed account for
477
- * `(sourceId, signaturesRequired, submitter)` is created on first use. Signer
478
- * `Node` accounts are resolved from the registry snapshot the round was signed
479
- * against and passed as remaining accounts.
480
- */
481
- submitAttestation(result: DataUpdateResult, opts?: {
482
- computeUnitLimit?: number;
483
- }): Promise<SubmitResult>;
484
- /** @deprecated Renamed to {@link submitAttestation}. */
485
- submitDataUpdate(result: DataUpdateResult, opts?: {
486
- computeUnitLimit?: number;
487
- }): Promise<SubmitResult>;
539
+ * `(sourceId, signaturesRequired, submitter)` is created on first use.
540
+ *
541
+ * Per the program, the instruction takes one read-only `Node` account per signer bit
542
+ * (ascending bit order, resolved from the registry snapshot the round was signed
543
+ * against) and a {@link CoalitionKey} argument. Unless `opts.coalitionKey` is given the
544
+ * SDK fetches those `Node` accounts and sums their secp256k1 keys client-side
545
+ * (`computeCoalitionKey`); the program only checks the key, so a wrong one fails the
546
+ * transaction and nothing else.
547
+ *
548
+ * `opts.rawValue` is for values longer than 32 bytes: the signed `payload.value` must be
549
+ * `keccak256(rawValue)`; {@link buildSubmitAttestationArgs} validates that before send.
550
+ */
551
+ submitAttestation(attestation: Attestation, opts?: SubmitAttestationOptions): Promise<SubmitResult>;
552
+ /** Sum of the signers' keys, read from their on-chain `Node` accounts (one batched fetch). */
553
+ private computeSignerCoalitionKey;
488
554
  /**
489
555
  * Read the feed written by `submitter` (default: this wallet) for
490
556
  * `(sourceId, signaturesRequired)`, or `null` before its first submit.
@@ -502,10 +568,59 @@ declare class MolphaSolanaClient {
502
568
  /** `usdc_mint` from `ProtocolConfig`; the treasury is its ATA owned by the config PDA. */
503
569
  private fetchProtocolTokens;
504
570
  }
505
- /** Build the Anchor `SubmitAttestationArgs` for a gateway result. */
506
- declare function buildSubmitAttestationArgs(result: DataUpdateResult): SubmitAttestationArgs;
571
+ /**
572
+ * Build the Anchor `SubmitAttestationArgs` for a gateway result: `{ attestation: { payload,
573
+ * signature }, rawValue, coalitionKey }`. `coalitionKey` is the affine sum of the signers'
574
+ * keys (see `computeCoalitionKey`).
575
+ */
576
+ declare function buildSubmitAttestationArgs(attestation: Attestation, coalitionKey: CoalitionKey, rawValue?: Uint8Array | null): SubmitAttestationArgs;
507
577
 
508
- /** Gateway wire shape — defaults applied before hash / encryption. */
578
+ /**
579
+ * Aggregation (tolerance mode) config validation and canonicalization.
580
+ *
581
+ * `aggregation` is part of the API config and therefore part of `sourceId`. It is OMITTED
582
+ * for exact mode: a config carrying `mode: "exact"` would hash differently from the same
583
+ * config without the key, so it is rejected rather than silently normalized. The node
584
+ * (`new/tolerance.Validate`) is the reference.
585
+ */
586
+
587
+ /** Tolerance mode needs at least this many signers (`signaturesRequired >= 3`). */
588
+ declare const MIN_TOLERANCE_SIGNATURES = 3;
589
+ /** Thrown for an unusable `aggregation` config. */
590
+ declare class AggregationConfigError extends Error {
591
+ constructor(message: string);
592
+ }
593
+ /**
594
+ * Validate an `aggregation` config and return a fresh object with the canonical key order
595
+ * (`mode`, `rule`, `maxDeviationBps`, `maxAgeMs`, `numeric{type, decimals}`) — the order
596
+ * the source hash and the node's JSON blob use.
597
+ *
598
+ * The result is built field by field: unknown or reordered keys on the input can never
599
+ * reach the hash or the wire. `undefined` / `null` mean exact mode and return `undefined`.
600
+ *
601
+ * @throws {AggregationConfigError} on `mode: "exact"`, an unsupported mode / rule / numeric
602
+ * type, or an out-of-range number.
603
+ */
604
+ declare function canonicalizeAggregation(aggregation: AggregationConfig | null | undefined): AggregationConfig | undefined;
605
+ /**
606
+ * Tolerance mode needs `signaturesRequired >= 3`; the node rejects anything lower.
607
+ * A no-op for exact mode (`aggregation` omitted).
608
+ *
609
+ * @throws {AggregationConfigError}
610
+ */
611
+ declare function assertAggregationQuorum(aggregation: AggregationConfig | null | undefined, signaturesRequired: number): void;
612
+
613
+ /**
614
+ * Gateway wire shape — defaults applied before hash / encryption.
615
+ *
616
+ * Keys are emitted in the fixed order `url`, `method`, `headers`, `responseParser`,
617
+ * `valueTransform`, `aggregation`; `aggregation` is present only for tolerance mode and its
618
+ * nested keys are rebuilt in canonical order (`canonicalizeAggregation`), so no extra or
619
+ * reordered input key can reach the hash. A config without `aggregation` hashes exactly as
620
+ * before.
621
+ *
622
+ * @throws {AggregationConfigError} if `aggregation` is invalid (including `mode: "exact"`).
623
+ */
509
624
  declare function canonicalizeAPIConfig(apiConfig: APIConfig): APIConfig;
510
625
  /**
511
626
  * `sourceId = keccak256(JSON.stringify(canonical apiConfig))` — the 32-byte identity of a
@@ -516,15 +631,13 @@ declare function canonicalizeAPIConfig(apiConfig: APIConfig): APIConfig;
516
631
  declare function deriveSourceId(apiConfig: APIConfig): Uint8Array;
517
632
  /** Hex-encoded {@link deriveSourceId} (64 lowercase hex chars, no `0x`). */
518
633
  declare function deriveSourceIdString(apiConfig: APIConfig): string;
519
- /** @deprecated Renamed to {@link deriveSourceId}; identical bytes. */
520
- declare const deriveApiConfigHash: typeof deriveSourceId;
521
634
 
522
635
  /**
523
636
  * Protocol-wide constants that must stay in sync with the vendored IDL. Kept as plain
524
637
  * literals so gateway-only / browser bundles never pull in `idl/molpha.json`.
525
638
  */
526
639
  /** Molpha program id (`idl/molpha.json` → `address`). Asserted equal in `test/gateway-auth.test.ts`. */
527
- declare const MOLPHA_PROGRAM_ID = "MoLFnEbuMS5gWnXNfUMLAYSqRM3eQZKWRzjeMQfqbT3";
640
+ declare const MOLPHA_PROGRAM_ID = "chivcFQgxzwkpLvW41PV431HQ4dYpaW3povQH3AdpQt";
528
641
 
529
642
  declare const utf8: (s: string) => Uint8Array;
530
643
  declare const concatBytes: (...arrays: Uint8Array[]) => Uint8Array;
@@ -534,6 +647,8 @@ declare const bytesToHex: (bytes: Uint8Array) => string;
534
647
  declare function hexToBytes(hex: string): Uint8Array;
535
648
  /** Hex with a leading `0x`. */
536
649
  declare const bytesToHex0x: (bytes: Uint8Array) => string;
650
+ /** u8 → 1 byte. Range-checked: `Uint8Array.of` would silently wrap an out-of-range value. */
651
+ declare function u8(value: number): Uint8Array;
537
652
  /** Big-endian u32 → 4 bytes. */
538
653
  declare function u32be(value: number): Uint8Array;
539
654
  /** Little-endian u32 → 4 bytes (used for PDA seeds like the registry index). */
@@ -558,13 +673,37 @@ declare function bytesToBase64(bytes: Uint8Array): string;
558
673
  /** Accepts padded or unpadded standard base64. */
559
674
  declare function base64ToBytes(value: string): Uint8Array;
560
675
 
676
+ /** `2^255 - 1`. */
677
+ declare const INT256_MAX: bigint;
678
+ /** `-2^255`. */
679
+ declare const INT256_MIN: bigint;
680
+ /** Two's-complement `bytes32` (big-endian) of a signed integer in `[-2^255, 2^255)`. */
681
+ declare function encodeInt256(value: bigint): Uint8Array;
682
+ /** Signed integer of a two's-complement `bytes32` (bytes or hex, optional `0x`). */
683
+ declare function decodeInt256(value: Uint8Array | string): bigint;
684
+ /**
685
+ * Parse an ordinary decimal string (`[+-]digits[.digits]`, no exponent, no whitespace),
686
+ * scale by `10^decimals`, round half to even, and return the `int256` two's-complement
687
+ * `bytes32` the nodes sign for a tolerance-mode source.
688
+ *
689
+ * @throws {Error} `invalid decimal`, `decimal too long`, or `int256 overflow`.
690
+ */
691
+ declare function encodeInt256Decimal(decimal: string, decimals: number): Uint8Array;
692
+ /**
693
+ * Render a signed integer — a two's-complement `bytes32` (bytes or hex), or an already
694
+ * decoded `bigint` — at the source's scale: `decimals` fractional places with trailing zeros
695
+ * trimmed (`-1.2`, `42`, `0.00000005`). Inverse of {@link encodeInt256Decimal} up to
696
+ * rounding.
697
+ */
698
+ declare function formatInt256Decimal(value: Uint8Array | string | bigint, decimals: number): string;
699
+
561
700
  /** `keccak256("MOLPHA_MESSAGE_V1")` domain separator. */
562
701
  declare const MESSAGE_PREFIX: Uint8Array;
563
702
  interface AttestationMessageFields {
564
703
  /** 32-byte source id (hex or bytes). */
565
704
  sourceId: string | Uint8Array;
566
705
  registryVersion: number;
567
- /** Encoded as `uint32` in the message even though the program stores a `u8`. */
706
+ /** Encoded as a single byte (`uint8`); throws `RangeError` outside `0..255`. */
568
707
  signaturesRequired: number;
569
708
  /** 32-byte big-endian signers bitmap (hex or bytes). */
570
709
  signersBitmap: string | Uint8Array;
@@ -575,8 +714,8 @@ interface AttestationMessageFields {
575
714
  }
576
715
  /** Compute the attestation message hash (32 bytes). */
577
716
  declare function attestationMessageHash(fields: AttestationMessageFields): Uint8Array;
578
- /** Message hash of a completed gateway round (`valuePacked` is the signed value). */
579
- declare function attestationMessageHashFromResult(result: DataUpdateResult): Uint8Array;
717
+ /** Message hash of a completed gateway attestation (`payload.value` is the signed word). */
718
+ declare function attestationMessageHashFromAttestation(attestation: Attestation): Uint8Array;
580
719
 
581
720
  /**
582
721
  * Parse a secp256k1 public key and return canonical compressed lower-case hex.
@@ -648,51 +787,77 @@ type VerifyCode = (typeof VERIFY_CODES)[VerifyCodeName];
648
787
  declare function verifyCodeName(code: number): VerifyCodeName | undefined;
649
788
 
650
789
  /**
651
- * Minimal Molpha verifier ABI for `verify` and registry reads.
652
- * Matches the deployed `verify(DataUpdate, SchnorrSignature)` verifier. The first tuple
653
- * component carries the 32-byte source id (the contract source names it `jobId`;
654
- * component names do not affect ABI encoding).
790
+ * Molpha EVM verifier ABI: `verify(Attestation, uint64 maxAge) -> (bool, uint8)` plus every
791
+ * read-only registry view on `IVerifier`. Owner-only mutators (`addNode`, `removeNode`,
792
+ * `setRedundancyBuffer`) and `Ownable` plumbing are deliberately left out.
793
+ *
794
+ * Mirrors `IVerifier.sol` in `molpha-core-contracts`. Struct member order is ABI-significant
795
+ * and equals the signed message order, so it is not the flat gateway field order on `Attestation`.
655
796
  */
656
797
  declare const MOLPHA_VERIFIER_ABI: readonly [{
657
798
  readonly type: "function";
658
799
  readonly name: "verify";
659
800
  readonly stateMutability: "view";
660
801
  readonly inputs: readonly [{
661
- readonly name: "dataUpdate";
802
+ readonly name: "attestation";
662
803
  readonly type: "tuple";
804
+ readonly internalType: "struct IVerifier.Attestation";
663
805
  readonly components: readonly [{
664
- readonly name: "sourceId";
665
- readonly type: "bytes32";
666
- }, {
667
- readonly name: "registryVersion";
668
- readonly type: "uint32";
669
- }, {
670
- readonly name: "signaturesRequired";
671
- readonly type: "uint32";
672
- }, {
673
- readonly name: "value";
674
- readonly type: "bytes32";
806
+ readonly name: "payload";
807
+ readonly type: "tuple";
808
+ readonly internalType: "struct IVerifier.AttestationPayload";
809
+ readonly components: readonly [{
810
+ readonly name: "value";
811
+ readonly type: "bytes32";
812
+ readonly internalType: "bytes32";
813
+ }, {
814
+ readonly name: "sourceId";
815
+ readonly type: "bytes32";
816
+ readonly internalType: "bytes32";
817
+ }, {
818
+ readonly name: "registryVersion";
819
+ readonly type: "uint32";
820
+ readonly internalType: "uint32";
821
+ }, {
822
+ readonly name: "signaturesRequired";
823
+ readonly type: "uint8";
824
+ readonly internalType: "uint8";
825
+ }, {
826
+ readonly name: "canonicalTimestamp";
827
+ readonly type: "uint64";
828
+ readonly internalType: "uint64";
829
+ }];
675
830
  }, {
676
- readonly name: "canonicalTimestamp";
677
- readonly type: "uint64";
678
- }];
679
- }, {
680
- readonly name: "schnorrData";
681
- readonly type: "tuple";
682
- readonly components: readonly [{
683
831
  readonly name: "signature";
684
- readonly type: "bytes32";
685
- }, {
686
- readonly name: "commitment";
687
- readonly type: "address";
688
- }, {
689
- readonly name: "signersBitmap";
690
- readonly type: "uint256";
832
+ readonly type: "tuple";
833
+ readonly internalType: "struct IVerifier.SchnorrSignature";
834
+ readonly components: readonly [{
835
+ readonly name: "signature";
836
+ readonly type: "bytes32";
837
+ readonly internalType: "bytes32";
838
+ }, {
839
+ readonly name: "commitment";
840
+ readonly type: "address";
841
+ readonly internalType: "address";
842
+ }, {
843
+ readonly name: "signersBitmap";
844
+ readonly type: "uint256";
845
+ readonly internalType: "uint256";
846
+ }];
691
847
  }];
848
+ }, {
849
+ readonly name: "maxAge";
850
+ readonly type: "uint64";
851
+ readonly internalType: "uint64";
692
852
  }];
693
853
  readonly outputs: readonly [{
694
- readonly name: "";
854
+ readonly name: "success";
695
855
  readonly type: "bool";
856
+ readonly internalType: "bool";
857
+ }, {
858
+ readonly name: "code";
859
+ readonly type: "uint8";
860
+ readonly internalType: "uint8";
696
861
  }];
697
862
  }, {
698
863
  readonly type: "function";
@@ -702,7 +867,150 @@ declare const MOLPHA_VERIFIER_ABI: readonly [{
702
867
  readonly outputs: readonly [{
703
868
  readonly name: "registryVersion";
704
869
  readonly type: "uint256";
870
+ readonly internalType: "uint256";
871
+ }];
872
+ }, {
873
+ readonly type: "function";
874
+ readonly name: "getTotalNodes";
875
+ readonly stateMutability: "view";
876
+ readonly inputs: readonly [];
877
+ readonly outputs: readonly [{
878
+ readonly name: "totalNodes";
879
+ readonly type: "uint256";
880
+ readonly internalType: "uint256";
705
881
  }];
882
+ }, {
883
+ readonly type: "function";
884
+ readonly name: "redundancyBuffer";
885
+ readonly stateMutability: "view";
886
+ readonly inputs: readonly [];
887
+ readonly outputs: readonly [{
888
+ readonly name: "";
889
+ readonly type: "uint256";
890
+ readonly internalType: "uint256";
891
+ }];
892
+ }, {
893
+ readonly type: "function";
894
+ readonly name: "getRegistryRoot";
895
+ readonly stateMutability: "view";
896
+ readonly inputs: readonly [];
897
+ readonly outputs: readonly [{
898
+ readonly name: "root";
899
+ readonly type: "bytes32";
900
+ readonly internalType: "bytes32";
901
+ }];
902
+ }, {
903
+ readonly type: "function";
904
+ readonly name: "getRegistryRoot";
905
+ readonly stateMutability: "view";
906
+ readonly inputs: readonly [{
907
+ readonly name: "registryVersion";
908
+ readonly type: "uint256";
909
+ readonly internalType: "uint256";
910
+ }];
911
+ readonly outputs: readonly [{
912
+ readonly name: "root";
913
+ readonly type: "bytes32";
914
+ readonly internalType: "bytes32";
915
+ }];
916
+ }, {
917
+ readonly type: "function";
918
+ readonly name: "getRegistryPointer";
919
+ readonly stateMutability: "view";
920
+ readonly inputs: readonly [];
921
+ readonly outputs: readonly [{
922
+ readonly name: "registryPointer";
923
+ readonly type: "address";
924
+ readonly internalType: "address";
925
+ }];
926
+ }, {
927
+ readonly type: "function";
928
+ readonly name: "getRegistryPointer";
929
+ readonly stateMutability: "view";
930
+ readonly inputs: readonly [{
931
+ readonly name: "registryVersion";
932
+ readonly type: "uint256";
933
+ readonly internalType: "uint256";
934
+ }];
935
+ readonly outputs: readonly [{
936
+ readonly name: "registryPointer";
937
+ readonly type: "address";
938
+ readonly internalType: "address";
939
+ }];
940
+ }, {
941
+ readonly type: "function";
942
+ readonly name: "activatesAt";
943
+ readonly stateMutability: "view";
944
+ readonly inputs: readonly [{
945
+ readonly name: "registryVersion";
946
+ readonly type: "uint256";
947
+ readonly internalType: "uint256";
948
+ }];
949
+ readonly outputs: readonly [{
950
+ readonly name: "ts";
951
+ readonly type: "uint256";
952
+ readonly internalType: "uint256";
953
+ }];
954
+ }, {
955
+ readonly type: "function";
956
+ readonly name: "retiredAt";
957
+ readonly stateMutability: "view";
958
+ readonly inputs: readonly [{
959
+ readonly name: "registryVersion";
960
+ readonly type: "uint256";
961
+ readonly internalType: "uint256";
962
+ }];
963
+ readonly outputs: readonly [{
964
+ readonly name: "ts";
965
+ readonly type: "uint256";
966
+ readonly internalType: "uint256";
967
+ }];
968
+ }, {
969
+ readonly type: "function";
970
+ readonly name: "isLatestVersion";
971
+ readonly stateMutability: "view";
972
+ readonly inputs: readonly [{
973
+ readonly name: "registryVersion";
974
+ readonly type: "uint256";
975
+ readonly internalType: "uint256";
976
+ }];
977
+ readonly outputs: readonly [{
978
+ readonly name: "latest";
979
+ readonly type: "bool";
980
+ readonly internalType: "bool";
981
+ }];
982
+ }, {
983
+ readonly type: "function";
984
+ readonly name: "nodeStatus";
985
+ readonly stateMutability: "view";
986
+ readonly inputs: readonly [{
987
+ readonly name: "node";
988
+ readonly type: "address";
989
+ readonly internalType: "address";
990
+ }];
991
+ readonly outputs: readonly [{
992
+ readonly name: "";
993
+ readonly type: "uint8";
994
+ readonly internalType: "uint8";
995
+ }];
996
+ }, {
997
+ readonly type: "function";
998
+ readonly name: "isNode";
999
+ readonly stateMutability: "view";
1000
+ readonly inputs: readonly [{
1001
+ readonly name: "node";
1002
+ readonly type: "address";
1003
+ readonly internalType: "address";
1004
+ }];
1005
+ readonly outputs: readonly [{
1006
+ readonly name: "";
1007
+ readonly type: "bool";
1008
+ readonly internalType: "bool";
1009
+ }];
1010
+ }, {
1011
+ readonly type: "error";
1012
+ readonly name: "InvalidRegistryVersion";
1013
+ readonly inputs: readonly [];
706
1014
  }];
707
1015
 
708
1016
  /**
@@ -748,23 +1056,63 @@ declare function evmAddressFromPrivateKey(privateKey: string | Uint8Array): stri
748
1056
  */
749
1057
  declare function createEvmSignerFromPrivateKey(privateKey: string | Uint8Array): EvmSigner;
750
1058
 
751
- /** `(bytes32 sourceId, uint32 registryVersion, uint32 signaturesRequired, bytes32 valuePacked, uint64 timestamp)` */
752
- type EvmDataUpdateTuple = readonly [
753
- sourceId: `0x${string}`,
754
- registryVersion: number,
755
- signaturesRequired: number,
756
- valuePacked: `0x${string}`,
757
- timestamp: number
758
- ];
759
- /** `(bytes32 s, address commitment, uint256 signersBitmap)` */
760
- type EvmSchnorrSignatureTuple = readonly [
761
- s: `0x${string}`,
762
- commitment: `0x${string}`,
763
- signersBitmap: bigint
764
- ];
1059
+ /**
1060
+ * `IVerifier.AttestationPayload` — the signed half of an attestation.
1061
+ *
1062
+ * Member order is the order of the signed message preimage and of the ABI tuple, so it is
1063
+ * load bearing — it is not the flat gateway field order on {@link Attestation}.
1064
+ */
1065
+ interface EvmAttestationPayload {
1066
+ /** `bytes32` packed value. */
1067
+ value: `0x${string}`;
1068
+ /** `bytes32` source id. */
1069
+ sourceId: `0x${string}`;
1070
+ /** `uint32`. */
1071
+ registryVersion: number;
1072
+ /** `uint8`. */
1073
+ signaturesRequired: number;
1074
+ /** `uint64`, unix seconds. */
1075
+ canonicalTimestamp: bigint;
1076
+ }
1077
+ /** `IVerifier.SchnorrSignature`. */
1078
+ interface EvmSchnorrSignature {
1079
+ /** `bytes32` Schnorr scalar `s`. */
1080
+ signature: `0x${string}`;
1081
+ /** `address` of the nonce point `R`. */
1082
+ commitment: `0x${string}`;
1083
+ /** `uint256` signers bitmap; bit `i` is node `i` of the registry version. */
1084
+ signersBitmap: bigint;
1085
+ }
1086
+ /** `IVerifier.Attestation`. */
1087
+ interface EvmAttestation {
1088
+ payload: EvmAttestationPayload;
1089
+ signature: EvmSchnorrSignature;
1090
+ }
1091
+ /** Positional arguments for `verify(attestation, maxAge)`. */
765
1092
  interface EvmVerifierArgs {
766
- dataUpdate: EvmDataUpdateTuple;
767
- signature: EvmSchnorrSignatureTuple;
1093
+ attestation: EvmAttestation;
1094
+ /** Freshness window in seconds (`uint64`). `0n` disables the check. */
1095
+ maxAge: bigint;
1096
+ }
1097
+ interface BuildEvmVerifierArgsOptions {
1098
+ /**
1099
+ * Freshness window in seconds. The verifier rejects the attestation with `STALE` when it
1100
+ * is older than this, and as `MALFORMED` when it is dated in the future.
1101
+ *
1102
+ * Required on purpose. `0` disables the check entirely, and that is not a neutral
1103
+ * default: the verifier is stateless, so without a window it accepts a correctly signed
1104
+ * attestation forever. Pass `0` only when the consuming contract enforces freshness or
1105
+ * ordering itself.
1106
+ */
1107
+ maxAge: number | bigint;
1108
+ }
1109
+ /** Decoded `verify` return value. */
1110
+ interface EvmVerifyResult {
1111
+ success: boolean;
1112
+ /** Raw result code — see `VERIFY_CODES`. */
1113
+ code: number;
1114
+ /** Name of `code`, or `"UNKNOWN"` for a code newer than this SDK. */
1115
+ reason: VerifyCodeName | "UNKNOWN";
768
1116
  }
769
1117
  /**
770
1118
  * Normalize hex to a fixed-size `0x`-prefixed value.
@@ -773,10 +1121,39 @@ interface EvmVerifierArgs {
773
1121
  declare function toFixedHex(value: string, bytes: number, label: string): `0x${string}`;
774
1122
  /** Convert a 32-byte hex bitmap to a `uint256` bigint (big-endian). */
775
1123
  declare function signersBitmapToUint256(value: string): bigint;
776
- /** Build verifier `DataUpdate` and `SchnorrSignature` tuples from a gateway result. */
777
- declare function buildEvmVerifierArgs(result: DataUpdateResult): EvmVerifierArgs;
778
- /** Decimal string form of the signers bitmap — useful for JSON logging or legacy tooling. */
1124
+ /** Decimal string form of the signers bitmap — useful for JSON logging. */
779
1125
  declare function signersBitmapToDecimal(value: string): string;
1126
+ /**
1127
+ * Build the `verify(attestation, maxAge)` arguments from a gateway result.
1128
+ *
1129
+ * ```ts
1130
+ * const { attestation, maxAge } = buildEvmVerifierArgs(result, { maxAge: 300 });
1131
+ * await client.readContract({ abi: MOLPHA_VERIFIER_ABI, functionName: "verify", args: [attestation, maxAge], ... });
1132
+ * ```
1133
+ */
1134
+ declare function buildEvmVerifierArgs(attestation: Attestation, options: BuildEvmVerifierArgsOptions): EvmVerifierArgs;
1135
+ /**
1136
+ * ABI calldata for `verify(attestation, maxAge)`: the 4-byte selector followed by nine
1137
+ * 32-byte words. Both structs are static, so they encode inline with no offsets:
1138
+ *
1139
+ * `value, sourceId, registryVersion, signaturesRequired, canonicalTimestamp, signature,
1140
+ * commitment, signersBitmap, maxAge`
1141
+ *
1142
+ * For a raw `eth_call` (`{ to: verifier, data }`).
1143
+ */
1144
+ declare function encodeEvmVerifyCalldata(args: EvmVerifierArgs): `0x${string}`;
1145
+ /**
1146
+ * Decode the `(bool, uint8)` returned by `verify`.
1147
+ *
1148
+ * Accepts the raw 64-byte return data from `eth_call`, or the tuple an ABI-aware client
1149
+ * decodes (viem `readContract` returns `[true, 0]`; an ethers `Result` indexes the same way).
1150
+ * Throws when the two halves disagree (`success` with a non-zero code, or failure with
1151
+ * `OK`), which means the call did not reach a Molpha verifier of this interface.
1152
+ */
1153
+ declare function parseEvmVerifyResult(result: string | {
1154
+ readonly 0: boolean | number | bigint;
1155
+ readonly 1: number | bigint;
1156
+ }): EvmVerifyResult;
780
1157
 
781
1158
  /**
782
1159
  * Deployed Molpha verifier contract addresses on Starknet testnets.
@@ -794,7 +1171,7 @@ declare function getMolphaStarknetVerifierAddress(network: MolphaStarknetNetwork
794
1171
  * Starknet calldata shape for `AttestationPayload`.
795
1172
  *
796
1173
  * Member order is the order of the signed message preimage and of Cairo `Serde`, so it is
797
- * load bearing — it is not the order of `DataUpdateResult`.
1174
+ * load bearing — it is not the flat gateway field order on {@link Attestation}.
798
1175
  */
799
1176
  interface StarknetAttestationPayload {
800
1177
  /** 32-byte packed value as `u256`. */
@@ -861,7 +1238,7 @@ declare function signersBitmapToStarknetUint256(value: string): bigint;
861
1238
  * const { attestation, maxAge } = buildStarknetVerifierArgs(result, { maxAge: 300 });
862
1239
  * ```
863
1240
  */
864
- declare function buildStarknetVerifierArgs(result: DataUpdateResult, options: BuildStarknetVerifierArgsOptions): StarknetVerifierArgs;
1241
+ declare function buildStarknetVerifierArgs(attestation: Attestation, options: BuildStarknetVerifierArgsOptions): StarknetVerifierArgs;
865
1242
  /**
866
1243
  * Flat felt calldata for `verify(attestation, max_age)`, in Cairo `Serde` order — 13 felts:
867
1244
  *
@@ -896,10 +1273,11 @@ declare const registryStatePda: (programId: SolanaAddress) => Address;
896
1273
  /** Immutable, version-addressed registry snapshot: `["molpha_registry", version u32 LE]`. */
897
1274
  declare const registryPda: (version: number, programId: SolanaAddress) => Address;
898
1275
  /**
899
- * Owner-keyed `Node` account: `["molpha_node", owner]`. Registry snapshots store these
900
- * addresses directly in `nodes[i]`, so consumers rarely need to derive them.
1276
+ * Authority-keyed `Node` account: `["molpha_node", authority]` (`Node.authority`). Registry
1277
+ * snapshots store these addresses directly in `nodes[i]`, so consumers rarely need to
1278
+ * derive them.
901
1279
  */
902
- declare const nodePda: (owner: SolanaAddress, programId: SolanaAddress) => Address;
1280
+ declare const nodePda: (authority: SolanaAddress, programId: SolanaAddress) => Address;
903
1281
  /** Bonded gateway account: `["molpha_gateway", gatewayAuthority]` — the `gateway` bound into `RequestAuth`. */
904
1282
  declare const gatewayPda: (authority: SolanaAddress, programId: SolanaAddress) => Address;
905
1283
  /** Plan PDA is `[b"molpha_plan", [planType as u8]]`. */
@@ -958,10 +1336,10 @@ declare class MolphaSDK {
958
1336
  * on-chain registry version) and submit it via `submit_attestation`.
959
1337
  */
960
1338
  requestAndSubmit(opts: RequestSignedDataOptions): Promise<{
961
- result: DataUpdateResult;
1339
+ result: Attestation;
962
1340
  signature: string;
963
1341
  feed: Address;
964
1342
  }>;
965
1343
  }
966
1344
 
967
- export { APIConfig, AssetDomain, type AttestationMessageFields, type BuildStarknetVerifierArgsOptions, DEFAULT_GATEWAY_ENDPOINT, DataUpdateResult, EIP712_DOMAIN_TYPEHASH, type Eip712Domain, type EvmDataUpdateTuple, type EvmSchnorrSignatureTuple, EvmSigner, type EvmVerifierArgs, type FeedAccount, type GatewayEndpoint, type GatewayEndpointInput, GatewayError, type GatewayInfo, MESSAGE_PREFIX, MOLPHA_IDL, MOLPHA_PROGRAM_ADDRESS, MOLPHA_PROGRAM_ID, MOLPHA_VERIFIER_ABI, MOLPHA_VERIFIER_ADDRESS, MOLPHA_VERIFIER_STARKNET_ADDRESSES, MOLPHA_VERIFIER_STARKNET_SEPOLIA, type MolphaEvmNetwork, MolphaGateway, type MolphaGatewayOptions, MolphaSDK, type MolphaSDKOptions, MolphaSolanaClient, type MolphaStarknetNetwork, MolphaWallet, Node, NodeKeyVerifier, NodeKeyVerifierArgs, NodesInfo, type PlanId, type PlanInfo, PlanType, REQUEST_AUTH_DOMAIN, RegistrySelectionConfig, type RegistryStateView, type RegistryView, type RequestAuthFields, type RequestSignedDataOptions, type RoundContext, Signer, SourcePaymentOptions, type StarknetAttestation, type StarknetAttestationPayload, type StarknetFeltLike, type StarknetSchnorrSignature, type StarknetVerifierArgs, type StarknetVerifyResult, type SubmitAttestationArgs, type SubmitResult, type SubscribeResult, type SubscriptionInfo, TRANSFER_WITH_AUTHORIZATION_TYPEHASH, type TransferAuthorization, UpstreamPaymentRequiredError, UpstreamQuote, UpstreamTerms, VERIFY_CODES, type VerifyCode, type VerifyCodeName, addressToBytes, attestationMessageHash, attestationMessageHashFromResult, base64ToBytes, bigIntFromBytesBe, bitmapBitSet, bitmapToIndices, buildEvmVerifierArgs, buildStarknetVerifierArgs, buildSubmitAttestationArgs, bytesToBase64, bytesToHex, bytesToHex0x, canonicalizeAPIConfig, commitmentAddressToStarknetFelt, concatBytes, createEvmSignerFromPrivateKey, deriveApiConfigHash, deriveGatewayPda, deriveGatewayPdaAddress, deriveGroupBitmap, deriveSelectionBitmap, deriveSelectionSeed, deriveSourceId, deriveSourceIdString, domainSeparator, effectiveSelectionSize, eligibleSetSize, encodeRequestAuth, encodeStarknetVerifyCalldata, ensureLength, evmAddressFromPrivateKey, feedPda, gatewayPda, getMolphaStarknetVerifierAddress, hashRequestAuth, hexToBytes, nodePda, normalizeEndpoint, normalizeSecp256k1PublicKeyHex, parseGatewayInfo, parseStarknetVerifyResult, parseUpstreamQuote, planIdFromVariant, planPda, planVariant, probeSource, protocolConfigPda, registryPda, registryStatePda, resolveRemainingAccounts, secp256k1PublicKeyFromCoordinates, selectedIndices, signSourcePayments, signersBitmapToDecimal, signersBitmapToStarknetUint256, signersBitmapToUint256, subscriptionPda, toChecksumAddress, toFixedBytes, toFixedHex, transferWithAuthorizationDigest, transferWithAuthorizationHash, u256beFromBigInt, u32be, u32le, u64be, u64le, utf8, validateSuppliedTerms, verifyCodeName };
1345
+ export { APIConfig, AggregationConfig, AggregationConfigError, AssetDomain, Attestation, type AttestationMessageFields, type BuildEvmVerifierArgsOptions, type BuildStarknetVerifierArgsOptions, type CoalitionKey, DEFAULT_GATEWAY_ENDPOINT, EIP712_DOMAIN_TYPEHASH, type Eip712Domain, type EvmAttestation, type EvmAttestationPayload, type EvmSchnorrSignature, EvmSigner, type EvmVerifierArgs, type EvmVerifyResult, type FeedAccount, type GatewayEndpoint, type GatewayEndpointInput, GatewayError, type GatewayInfo, INT256_MAX, INT256_MIN, MESSAGE_PREFIX, MIN_TOLERANCE_SIGNATURES, MOLPHA_IDL, MOLPHA_PROGRAM_ADDRESS, MOLPHA_PROGRAM_ID, MOLPHA_VERIFIER_ABI, MOLPHA_VERIFIER_ADDRESS, MOLPHA_VERIFIER_STARKNET_ADDRESSES, MOLPHA_VERIFIER_STARKNET_SEPOLIA, type MolphaEvmNetwork, MolphaGateway, type MolphaGatewayOptions, MolphaSDK, type MolphaSDKOptions, MolphaSolanaClient, type MolphaStarknetNetwork, MolphaWallet, Node, NodeKeyVerifier, NodeKeyVerifierArgs, NodesInfo, type PlanId, type PlanInfo, PlanType, REQUEST_AUTH_DOMAIN, RegistrySelectionConfig, type RegistryStateView, type RegistryView, type RequestAuthFields, type RequestSignedDataOptions, type RoundContext, type Secp256k1KeyInput, Signer, SourcePaymentOptions, type StarknetAttestation, type StarknetAttestationPayload, type StarknetFeltLike, type StarknetSchnorrSignature, type StarknetVerifierArgs, type StarknetVerifyResult, type SubmitAttestationArgs, type SubmitAttestationOptions, type SubmitResult, type SubscribeResult, type SubscriptionInfo, TRANSFER_WITH_AUTHORIZATION_TYPEHASH, type TransferAuthorization, UpstreamPaymentRequiredError, UpstreamQuote, UpstreamTerms, VERIFY_CODES, type VerifyCode, type VerifyCodeName, addressToBytes, assertAggregationQuorum, attestationMessageHash, attestationMessageHashFromAttestation, base64ToBytes, bigIntFromBytesBe, bitmapBitSet, bitmapToIndices, buildEvmVerifierArgs, buildStarknetVerifierArgs, buildSubmitAttestationArgs, bytesToBase64, bytesToHex, bytesToHex0x, canonicalizeAPIConfig, canonicalizeAggregation, commitmentAddressToStarknetFelt, computeCoalitionKey, concatBytes, createEvmSignerFromPrivateKey, decodeInt256, deriveGatewayPda, deriveGatewayPdaAddress, deriveGroupBitmap, deriveSelectionBitmap, deriveSelectionSeed, deriveSourceId, deriveSourceIdString, domainSeparator, effectiveSelectionSize, eligibleSetSize, encodeEvmVerifyCalldata, encodeInt256, encodeInt256Decimal, encodeRequestAuth, encodeStarknetVerifyCalldata, ensureLength, evmAddressFromPrivateKey, feedPda, formatInt256Decimal, gatewayPda, getMolphaStarknetVerifierAddress, hashRequestAuth, hexToBytes, nodePda, normalizeEndpoint, normalizeSecp256k1PublicKeyHex, parseEvmVerifyResult, parseGatewayInfo, parseStarknetVerifyResult, parseUpstreamQuote, planIdFromVariant, planPda, planVariant, probeSource, protocolConfigPda, registryPda, registryStatePda, resolveRemainingAccounts, secp256k1PublicKeyFromCoordinates, selectedIndices, signSourcePayments, signersBitmapToDecimal, signersBitmapToStarknetUint256, signersBitmapToUint256, subscriptionPda, toChecksumAddress, toFixedBytes, toFixedHex, transferWithAuthorizationDigest, transferWithAuthorizationHash, u256beFromBigInt, u32be, u32le, u64be, u64le, u8, utf8, validateSuppliedTerms, verifyCodeName };