@rialo/ts-cdk 0.2.0-alpha.0 → 0.2.0-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -1,3 +1,5 @@
1
+ export { field, fixedArray, option, vec } from '@dao-xyz/borsh';
2
+
1
3
  interface HttpTransportConfig {
2
4
  /** Request timeout in milliseconds */
3
5
  timeout?: number;
@@ -731,6 +733,341 @@ declare class RialoError extends Error {
731
733
  static serialization(message: string): RialoError;
732
734
  }
733
735
 
736
+ /**
737
+ * Error codes for HPKE encryption operations.
738
+ */
739
+ declare enum HpkeErrorCode {
740
+ /** Key length does not match expected size */
741
+ INVALID_KEY_LENGTH = "INVALID_KEY_LENGTH",
742
+ /** Ciphertext is shorter than minimum required length */
743
+ CIPHERTEXT_TOO_SHORT = "CIPHERTEXT_TOO_SHORT",
744
+ /** HPKE encryption operation failed */
745
+ ENCRYPTION_FAILED = "ENCRYPTION_FAILED",
746
+ /** Failed to deserialize Borsh data */
747
+ BORSH_DESERIALIZE_FAILED = "BORSH_DESERIALIZE_FAILED",
748
+ /** RexValue has invalid variant byte */
749
+ INVALID_ORACLE_VALUE = "INVALID_ORACLE_VALUE"
750
+ }
751
+ /**
752
+ * Error class for HPKE encryption operations.
753
+ *
754
+ * Provides detailed error information for encryption failures,
755
+ * including error codes and contextual details.
756
+ */
757
+ declare class HpkeError extends Error {
758
+ readonly code: HpkeErrorCode;
759
+ readonly cause?: Error;
760
+ constructor(code: HpkeErrorCode, message: string, cause?: Error);
761
+ /**
762
+ * Create an error for invalid key length.
763
+ *
764
+ * @param expected - Expected key length in bytes
765
+ * @param actual - Actual key length in bytes
766
+ * @param keyType - Description of the key type (e.g., "REX public key")
767
+ */
768
+ static invalidKeyLength(expected: number, actual: number, keyType: string): HpkeError;
769
+ /**
770
+ * Create an error for ciphertext that is too short.
771
+ *
772
+ * @param minLength - Minimum required length
773
+ * @param actual - Actual length
774
+ */
775
+ static ciphertextTooShort(minLength: number, actual: number): HpkeError;
776
+ /**
777
+ * Create an error for encryption failure.
778
+ *
779
+ * @param cause - The underlying error
780
+ */
781
+ static encryptionFailed(cause: Error): HpkeError;
782
+ /**
783
+ * Create an error for Borsh deserialization failure.
784
+ *
785
+ * @param cause - The underlying error
786
+ */
787
+ static borshDeserializeFailed(cause: Error): HpkeError;
788
+ /**
789
+ * Create an error for invalid RexValue variant.
790
+ *
791
+ * @param variant - The invalid variant byte
792
+ */
793
+ static invalidRexValue(variant: number): HpkeError;
794
+ }
795
+
796
+ /**
797
+ * Constants for REX HPKE encryption.
798
+ *
799
+ * These constants MUST match the Rust implementation exactly:
800
+ * - `crates/tee/secret-sharing/src/constants.rs`
801
+ *
802
+ * @module
803
+ */
804
+ /**
805
+ * Additional Authenticated Data (AAD) prefix for user secrets.
806
+ *
807
+ * This 13-byte string is prepended to the sender's public key to form
808
+ * the complete AAD for HPKE encryption. It provides domain separation
809
+ * to prevent cross-protocol attacks.
810
+ *
811
+ * Format: `USER_SECRET_AAD || senderPubkey` = 45 bytes total AAD
812
+ *
813
+ * @remarks
814
+ * Must match Rust: `pub const USER_SECRET_AAD: &[u8] = b"rex-secret-v1";`
815
+ */
816
+ declare const USER_SECRET_AAD: Uint8Array<ArrayBuffer>;
817
+ /**
818
+ * HPKE info string for secret sharing context.
819
+ *
820
+ * This 32-byte string is used as the `info` parameter in HPKE encryption,
821
+ * providing domain separation for secret sharing operations.
822
+ *
823
+ * @remarks
824
+ * Must match Rust: `pub const SECRET_SHARING_HPKE_INFO: &[u8; 32] = b"rialo/tee/secret-sharing-hpke/v1";`
825
+ */
826
+ declare const SECRET_SHARING_HPKE_INFO: Uint8Array<ArrayBuffer>;
827
+ /**
828
+ * Length of an X25519 public key in bytes.
829
+ *
830
+ * Used for the REX encryption public key (secret sharing key).
831
+ */
832
+ declare const X25519_PUBLIC_KEY_LENGTH = 32;
833
+ /**
834
+ * Length of an Ed25519 public key in bytes.
835
+ *
836
+ * Used for sender identity binding in AAD construction.
837
+ */
838
+ declare const ED25519_PUBLIC_KEY_LENGTH = 32;
839
+ /**
840
+ * Length of the HPKE encapsulated key (enc) in bytes.
841
+ *
842
+ * For X25519, this is always 32 bytes.
843
+ */
844
+ declare const HPKE_ENC_LENGTH = 32;
845
+ /**
846
+ * Length of the ChaCha20-Poly1305 authentication tag in bytes.
847
+ */
848
+ declare const CHACHA20_POLY1305_TAG_LENGTH = 16;
849
+ /**
850
+ * Total overhead added by HPKE encryption.
851
+ *
852
+ * This is the additional bytes beyond the plaintext:
853
+ * - enc (32 bytes): Encapsulated ephemeral public key
854
+ * - tag (16 bytes): ChaCha20-Poly1305 authentication tag
855
+ *
856
+ * Ciphertext length = plaintext length + 48 bytes
857
+ */
858
+ declare const HPKE_OVERHEAD_LENGTH: number;
859
+
860
+ /**
861
+ * Variant discriminator for RexValue Borsh serialization.
862
+ */
863
+ declare enum RexValueVariant {
864
+ /** Plain (unencrypted) data variant */
865
+ Plain = 0,
866
+ /** Encrypted data variant */
867
+ Encrypted = 1
868
+ }
869
+ /**
870
+ * Represents an rex value that can be plain or encrypted.
871
+ *
872
+ * This class provides Borsh-compatible serialization that matches
873
+ * the Rust `RexValue` enum:
874
+ *
875
+ * ```rust
876
+ * pub enum RexValue {
877
+ * Plain(Vec<u8>),
878
+ * Encrypted(Vec<u8>),
879
+ * }
880
+ * ```
881
+ *
882
+ * ## Borsh Format
883
+ *
884
+ * - Plain: `[0x00] [length: u32 LE] [data bytes]`
885
+ * - Encrypted: `[0x01] [length: u32 LE] [ciphertext bytes]`
886
+ *
887
+ * @example
888
+ * ```typescript
889
+ * // Plain value (unencrypted)
890
+ * const plain = RexValue.plain(new TextEncoder().encode("hello"));
891
+ *
892
+ * // Encrypted value (via HPKE)
893
+ * const encrypted = RexValue.encrypted(ciphertextBytes);
894
+ *
895
+ * // Serialize to Borsh
896
+ * const borsh = plain.toBorsh();
897
+ *
898
+ * // Deserialize from Borsh
899
+ * const restored = RexValue.fromBorsh(borsh);
900
+ * ```
901
+ */
902
+ declare class RexValue {
903
+ private readonly variant;
904
+ private readonly data;
905
+ private constructor();
906
+ /**
907
+ * Create a plain (unencrypted) RexValue from raw bytes.
908
+ *
909
+ * @param data - The raw byte data
910
+ * @returns A new RexValue with Plain variant
911
+ */
912
+ static plain(data: Uint8Array): RexValue;
913
+ /**
914
+ * Create a plain (unencrypted) RexValue from a UTF-8 string.
915
+ *
916
+ * @param s - The string to encode
917
+ * @returns A new RexValue with Plain variant
918
+ */
919
+ static plainString(s: string): RexValue;
920
+ /**
921
+ * Create an encrypted RexValue from HPKE ciphertext.
922
+ *
923
+ * @param ciphertext - The HPKE-encrypted ciphertext (enc || ct || tag)
924
+ * @returns A new RexValue with Encrypted variant
925
+ */
926
+ static encrypted(ciphertext: Uint8Array): RexValue;
927
+ /**
928
+ * Check if this is a plain (unencrypted) value.
929
+ */
930
+ isPlain(): boolean;
931
+ /**
932
+ * Check if this is an encrypted value.
933
+ */
934
+ isEncrypted(): boolean;
935
+ /**
936
+ * Get the variant type.
937
+ */
938
+ getVariant(): RexValueVariant;
939
+ /**
940
+ * Get the raw bytes (plaintext or ciphertext).
941
+ *
942
+ * For Plain values, returns the plaintext.
943
+ * For Encrypted values, returns the ciphertext.
944
+ */
945
+ asBytes(): Uint8Array;
946
+ /**
947
+ * Try to decode the plain value as a UTF-8 string.
948
+ *
949
+ * @returns The decoded string, or null if encrypted or not valid UTF-8
950
+ */
951
+ asString(): string | null;
952
+ /**
953
+ * Serialize to Borsh format.
954
+ *
955
+ * Format: `[variant: u8] [length: u32 LE] [data bytes]`
956
+ *
957
+ * @returns The Borsh-serialized bytes
958
+ */
959
+ toBorsh(): Uint8Array;
960
+ /**
961
+ * Deserialize from Borsh format.
962
+ *
963
+ * @param data - The Borsh-serialized bytes
964
+ * @returns A new RexValue
965
+ * @throws {HpkeError} If deserialization fails
966
+ */
967
+ static fromBorsh(data: Uint8Array): RexValue;
968
+ }
969
+
970
+ /**
971
+ * Encrypt data using HPKE for REX secret sharing.
972
+ *
973
+ * This function performs HPKE encryption using the Base mode with:
974
+ * - X25519 for key encapsulation
975
+ * - HKDF-SHA256 for key derivation
976
+ * - ChaCha20-Poly1305 for authenticated encryption
977
+ *
978
+ * The output format is: `enc (32 bytes) || ciphertext || tag (16 bytes)`
979
+ *
980
+ * @param rexPubkey - The REX X25519 public key (32 bytes)
981
+ * @param data - The plaintext data to encrypt
982
+ * @param senderPubkey - The sender's Ed25519 public key (32 bytes) for AAD construction
983
+ * @returns The encrypted ciphertext including enc and tag
984
+ * @throws {HpkeError} If key lengths are invalid or encryption fails
985
+ *
986
+ * @example
987
+ * ```typescript
988
+ * const rexPubkey = await client.getSecretSharingPubkey();
989
+ * const ciphertext = await hpkeEncrypt(
990
+ * rexPubkey,
991
+ * new TextEncoder().encode("secret data"),
992
+ * keypair.publicKey.toBytes()
993
+ * );
994
+ * ```
995
+ */
996
+ declare function hpkeEncrypt(rexPubkey: Uint8Array, data: Uint8Array, senderPubkey: Uint8Array): Promise<Uint8Array>;
997
+ /**
998
+ * Encrypt data for REX and wrap it in an RexValue.
999
+ *
1000
+ * This is a convenience function that combines:
1001
+ * 1. HPKE encryption using `hpkeEncrypt`
1002
+ * 2. Wrapping the ciphertext in an `RexValue.encrypted`
1003
+ *
1004
+ * The resulting RexValue can be serialized to Borsh and sent to the network.
1005
+ *
1006
+ * @param rexPubkey - The REX X25519 public key (32 bytes)
1007
+ * @param data - The plaintext data to encrypt
1008
+ * @param senderPubkey - The sender's Ed25519 public key (32 bytes)
1009
+ * @returns An RexValue containing the encrypted ciphertext
1010
+ * @throws {HpkeError} If key lengths are invalid or encryption fails
1011
+ *
1012
+ * @example
1013
+ * ```typescript
1014
+ * import { RpcClient, Keypair } from "@rialo/ts-cdk";
1015
+ * import { encryptForRex, RexValue } from "@rialo/ts-cdk/rex";
1016
+ *
1017
+ * // Get REX public key from the network
1018
+ * const client = new RpcClient("https://rpc.rialo.xyz");
1019
+ * const rexPubkey = await client.getSecretSharingPubkey();
1020
+ *
1021
+ * // Create keypair for signing
1022
+ * const keypair = Keypair.generate();
1023
+ *
1024
+ * // Encrypt secret data
1025
+ * const oracleValue = await encryptForRex(
1026
+ * rexPubkey,
1027
+ * new TextEncoder().encode("my secret API key"),
1028
+ * keypair.publicKey.toBytes()
1029
+ * );
1030
+ *
1031
+ * // The RexValue can now be serialized and used in transactions
1032
+ * const borshBytes = oracleValue.toBorsh();
1033
+ * ```
1034
+ */
1035
+ declare function encryptForRex(rexPubkey: Uint8Array, data: Uint8Array, senderPubkey: Uint8Array): Promise<RexValue>;
1036
+ /**
1037
+ * Calculate the expected ciphertext length for a given plaintext length.
1038
+ *
1039
+ * The ciphertext consists of:
1040
+ * - enc (32 bytes): Encapsulated ephemeral public key
1041
+ * - ciphertext (plaintext.length bytes): Encrypted data
1042
+ * - tag (16 bytes): ChaCha20-Poly1305 authentication tag
1043
+ *
1044
+ * @param plaintextLength - Length of the plaintext in bytes
1045
+ * @returns Expected ciphertext length
1046
+ *
1047
+ * @example
1048
+ * ```typescript
1049
+ * const ciphertextLen = getCiphertextLength(100);
1050
+ * console.log(ciphertextLen); // 148 (32 + 100 + 16)
1051
+ * ```
1052
+ */
1053
+ declare function getCiphertextLength(plaintextLength: number): number;
1054
+ /**
1055
+ * Validate that a ciphertext has a valid length.
1056
+ *
1057
+ * A valid HPKE ciphertext must be at least 48 bytes (32 enc + 16 tag).
1058
+ *
1059
+ * @param ciphertext - The ciphertext to validate
1060
+ * @returns true if the ciphertext length is valid
1061
+ *
1062
+ * @example
1063
+ * ```typescript
1064
+ * if (!isValidCiphertextLength(ciphertext)) {
1065
+ * throw new Error("Ciphertext too short");
1066
+ * }
1067
+ * ```
1068
+ */
1069
+ declare function isValidCiphertextLength(ciphertext: Uint8Array): boolean;
1070
+
734
1071
  /**
735
1072
  * Base client with JSON-RPC protocol handling.
736
1073
  *
@@ -973,15 +1310,6 @@ interface SignatureInfo {
973
1310
  * Get health response.
974
1311
  */
975
1312
  type GetHealthResponse = "ok" | string;
976
- /**
977
- * Get transactions configuration.
978
- */
979
- interface GetTransactionsConfig {
980
- /** Maximum number of transactions to return */
981
- limit?: number;
982
- /** Encoding format */
983
- encoding?: "json" | "base58" | "base64";
984
- }
985
1313
  /**
986
1314
  * Get transactions response.
987
1315
  */
@@ -1029,8 +1357,6 @@ interface ConfirmedTransaction {
1029
1357
  * Configuration for getAccountsByOwner.
1030
1358
  */
1031
1359
  interface GetAccountsByOwnerConfig {
1032
- /** Encoding format for account data */
1033
- encoding?: "base64" | "base58" | "json" | "jsonParsed";
1034
1360
  /** Maximum number of accounts to return */
1035
1361
  limit?: number;
1036
1362
  /** Cursor for pagination (base58 pubkey) */
@@ -1073,6 +1399,15 @@ interface GetAccountsByOwnerResponse {
1073
1399
  /** Pagination information */
1074
1400
  pagination?: PaginationInfo;
1075
1401
  }
1402
+ /**
1403
+ * Get secret sharing public key response.
1404
+ *
1405
+ * Contains the TEE's X25519 public key for HPKE encryption.
1406
+ */
1407
+ interface GetSecretSharingPubkeyResponse {
1408
+ /** The TEE's X25519 public key as a hex-encoded string */
1409
+ public_key: string;
1410
+ }
1076
1411
 
1077
1412
  /**
1078
1413
  * Main Rialo RPC client for blockchain interactions.
@@ -1554,6 +1889,50 @@ declare class QueryRpcClient extends BaseRpcClient {
1554
1889
  * ```
1555
1890
  */
1556
1891
  getTriggeredTransactions(subscriptionAccount: PublicKey, limit?: number): Promise<TriggeredTransaction[]>;
1892
+ /**
1893
+ * Retrieve the REX X25519 public key for secret sharing encryption.
1894
+ *
1895
+ * This key is used for HPKE encryption when sending encrypted data
1896
+ * that should only be decryptable within the REX execution environment.
1897
+ *
1898
+ * @returns The REX X25519 public key as a 32-byte Uint8Array
1899
+ *
1900
+ * @example
1901
+ * ```typescript
1902
+ * import { encryptForRex } from "@rialo/ts-cdk";
1903
+ *
1904
+ * // Get the REX public key
1905
+ * const rexPubkey = await client.getSecretSharingPubkey();
1906
+ *
1907
+ * // Use it for HPKE encryption
1908
+ * const encrypted = await encryptForRex(
1909
+ * rexPubkey,
1910
+ * new TextEncoder().encode("secret data"),
1911
+ * keypair.publicKey.toBytes()
1912
+ * );
1913
+ * ```
1914
+ */
1915
+ getSecretSharingPubkey(): Promise<Uint8Array>;
1916
+ /**
1917
+ * Get the config hash prefix for replay protection.
1918
+ *
1919
+ * Returns the first 64 bits of the config hash, which is used
1920
+ * for transaction replay protection across chains.
1921
+ *
1922
+ * @returns The config hash prefix as a bigint
1923
+ *
1924
+ * @example
1925
+ * ```typescript
1926
+ * const configHashPrefix = await client.getConfigHashPrefix();
1927
+ * const tx = TransactionBuilder.create()
1928
+ * .setPayer(payer)
1929
+ * .setValidFrom(validFrom)
1930
+ * .setConfigHashPrefix(configHashPrefix)
1931
+ * .addInstruction(instruction)
1932
+ * .build();
1933
+ * ```
1934
+ */
1935
+ getConfigHashPrefix(): Promise<bigint>;
1557
1936
  }
1558
1937
 
1559
1938
  /**
@@ -1805,6 +2184,387 @@ declare function createRialoClient(config: RialoClientConfig): RialoClient;
1805
2184
  */
1806
2185
  declare function getDefaultRialoClientConfig(network: RialoNetwork): RialoClientConfig;
1807
2186
 
2187
+ /**
2188
+ * Bincode deserialization reader
2189
+ *
2190
+ * Matches Rust's bincode crate with default configuration:
2191
+ * - Little-endian byte order
2192
+ * - Fixed-size integer encoding (no varint)
2193
+ * - u64 length prefixes for dynamic collections
2194
+ * - u32 enum variant indices
2195
+ */
2196
+ declare class BincodeReader {
2197
+ private view;
2198
+ private offset;
2199
+ private bytes;
2200
+ constructor(data: Uint8Array);
2201
+ getOffset(): number;
2202
+ remaining(): number;
2203
+ isExhausted(): boolean;
2204
+ skip(bytes: number): this;
2205
+ /**
2206
+ * Peek at bytes without advancing the offset
2207
+ */
2208
+ peek(length: number): Uint8Array;
2209
+ /**
2210
+ * Reset reader to beginning
2211
+ */
2212
+ reset(): this;
2213
+ /**
2214
+ * Seek to specific offset
2215
+ */
2216
+ seek(offset: number): this;
2217
+ readU8(): number;
2218
+ readU16(): number;
2219
+ readU32(): number;
2220
+ readU64(): bigint;
2221
+ readU128(): bigint;
2222
+ readI8(): number;
2223
+ readI16(): number;
2224
+ readI32(): number;
2225
+ readI64(): bigint;
2226
+ readI128(): bigint;
2227
+ readF32(): number;
2228
+ readF64(): number;
2229
+ readBool(): boolean;
2230
+ readBytes(length: number): Uint8Array;
2231
+ readFixedArray(length: number): Uint8Array;
2232
+ readVecBytes(): Uint8Array;
2233
+ readString(): string;
2234
+ readVariant(): number;
2235
+ readOption<T>(readValue: () => T): T | null;
2236
+ readVec<T>(readElement: () => T): T[];
2237
+ /**
2238
+ * Read a tuple of fixed size with heterogeneous types
2239
+ */
2240
+ readTuple<T extends unknown[]>(readers: {
2241
+ [K in keyof T]: () => T[K];
2242
+ }): T;
2243
+ readMap<K, V>(readKey: () => K, readValue: () => V): Map<K, V>;
2244
+ /**
2245
+ * Read length as u64 but validate it's within safe integer range
2246
+ */
2247
+ private readLength;
2248
+ private ensureAvailable;
2249
+ }
2250
+
2251
+ /**
2252
+ * Type definitions for bincode schemas
2253
+ *
2254
+ * IMPORTANT: For structs and enums, field/variant order MUST match Rust definition order.
2255
+ * Use arrays of tuples instead of objects to guarantee order preservation.
2256
+ */
2257
+ type BincodeSchema = {
2258
+ type: "u8";
2259
+ } | {
2260
+ type: "u16";
2261
+ } | {
2262
+ type: "u32";
2263
+ } | {
2264
+ type: "u64";
2265
+ } | {
2266
+ type: "u128";
2267
+ } | {
2268
+ type: "i8";
2269
+ } | {
2270
+ type: "i16";
2271
+ } | {
2272
+ type: "i32";
2273
+ } | {
2274
+ type: "i64";
2275
+ } | {
2276
+ type: "i128";
2277
+ } | {
2278
+ type: "f32";
2279
+ } | {
2280
+ type: "f64";
2281
+ } | {
2282
+ type: "bool";
2283
+ } | {
2284
+ type: "string";
2285
+ } | {
2286
+ type: "bytes";
2287
+ } | {
2288
+ type: "unit";
2289
+ } | {
2290
+ type: "fixedArray";
2291
+ length: number;
2292
+ } | {
2293
+ type: "vec";
2294
+ element: BincodeSchema;
2295
+ } | {
2296
+ type: "option";
2297
+ inner: BincodeSchema;
2298
+ } | {
2299
+ type: "tuple";
2300
+ elements: BincodeSchema[];
2301
+ } | {
2302
+ type: "struct";
2303
+ fields: StructField[];
2304
+ } | {
2305
+ type: "enum";
2306
+ variants: EnumVariant[];
2307
+ } | {
2308
+ type: "map";
2309
+ key: BincodeSchema;
2310
+ value: BincodeSchema;
2311
+ } | {
2312
+ type: "pubkey";
2313
+ };
2314
+ /**
2315
+ * Struct field definition - order matters!
2316
+ */
2317
+ interface StructField {
2318
+ name: string;
2319
+ schema: BincodeSchema;
2320
+ }
2321
+ /**
2322
+ * Enum variant definition - order matters!
2323
+ */
2324
+ interface EnumVariant {
2325
+ name: string;
2326
+ schema: BincodeSchema | null;
2327
+ }
2328
+ declare const Schema: {
2329
+ readonly u8: () => BincodeSchema;
2330
+ readonly u16: () => BincodeSchema;
2331
+ readonly u32: () => BincodeSchema;
2332
+ readonly u64: () => BincodeSchema;
2333
+ readonly u128: () => BincodeSchema;
2334
+ readonly i8: () => BincodeSchema;
2335
+ readonly i16: () => BincodeSchema;
2336
+ readonly i32: () => BincodeSchema;
2337
+ readonly i64: () => BincodeSchema;
2338
+ readonly i128: () => BincodeSchema;
2339
+ readonly f32: () => BincodeSchema;
2340
+ readonly f64: () => BincodeSchema;
2341
+ readonly bool: () => BincodeSchema;
2342
+ readonly string: () => BincodeSchema;
2343
+ readonly bytes: () => BincodeSchema;
2344
+ readonly unit: () => BincodeSchema;
2345
+ readonly fixedArray: (length: number) => BincodeSchema;
2346
+ readonly vec: (element: BincodeSchema) => BincodeSchema;
2347
+ readonly option: (inner: BincodeSchema) => BincodeSchema;
2348
+ readonly tuple: (...elements: BincodeSchema[]) => BincodeSchema;
2349
+ /**
2350
+ * Define a struct with ordered fields
2351
+ * @example
2352
+ * Schema.struct([
2353
+ * ["id", Schema.u64()],
2354
+ * ["name", Schema.string()],
2355
+ * ["active", Schema.bool()],
2356
+ * ])
2357
+ */
2358
+ readonly struct: (fields: [string, BincodeSchema][]) => BincodeSchema;
2359
+ /**
2360
+ * Define an enum with ordered variants
2361
+ * @example
2362
+ * Schema.enum([
2363
+ * ["None", null],
2364
+ * ["Some", Schema.u64()],
2365
+ * ["Error", Schema.string()],
2366
+ * ])
2367
+ */
2368
+ readonly enum: (variants: [string, BincodeSchema | null][]) => BincodeSchema;
2369
+ readonly map: (key: BincodeSchema, value: BincodeSchema) => BincodeSchema;
2370
+ readonly pubkey: () => BincodeSchema;
2371
+ };
2372
+ /**
2373
+ * Serialize a value according to a schema
2374
+ */
2375
+ declare function serialize(schema: BincodeSchema, value: unknown): Uint8Array;
2376
+ /**
2377
+ * Deserialize bytes according to a schema
2378
+ */
2379
+ declare function deserialize<T>(schema: BincodeSchema, data: Uint8Array): T;
2380
+ /**
2381
+ * Deserialize bytes with strict validation
2382
+ */
2383
+ declare function deserializeStrict<T>(schema: BincodeSchema, data: Uint8Array): T;
2384
+ /**
2385
+ * Infer TypeScript type from schema (for documentation purposes)
2386
+ *
2387
+ * Usage:
2388
+ * const mySchema = Schema.struct([...]);
2389
+ * type MyType = InferSchema<typeof mySchema>;
2390
+ */
2391
+ type InferSchema<S extends BincodeSchema> = S extends {
2392
+ type: "u8";
2393
+ } ? number : S extends {
2394
+ type: "u16";
2395
+ } ? number : S extends {
2396
+ type: "u32";
2397
+ } ? number : S extends {
2398
+ type: "u64";
2399
+ } ? bigint : S extends {
2400
+ type: "u128";
2401
+ } ? bigint : S extends {
2402
+ type: "i8";
2403
+ } ? number : S extends {
2404
+ type: "i16";
2405
+ } ? number : S extends {
2406
+ type: "i32";
2407
+ } ? number : S extends {
2408
+ type: "i64";
2409
+ } ? bigint : S extends {
2410
+ type: "i128";
2411
+ } ? bigint : S extends {
2412
+ type: "f32";
2413
+ } ? number : S extends {
2414
+ type: "f64";
2415
+ } ? number : S extends {
2416
+ type: "bool";
2417
+ } ? boolean : S extends {
2418
+ type: "string";
2419
+ } ? string : S extends {
2420
+ type: "bytes";
2421
+ } ? Uint8Array : S extends {
2422
+ type: "unit";
2423
+ } ? undefined : S extends {
2424
+ type: "fixedArray";
2425
+ } ? Uint8Array : S extends {
2426
+ type: "pubkey";
2427
+ } ? Uint8Array : S extends {
2428
+ type: "vec";
2429
+ element: infer E;
2430
+ } ? E extends BincodeSchema ? InferSchema<E>[] : never : S extends {
2431
+ type: "option";
2432
+ inner: infer I;
2433
+ } ? I extends BincodeSchema ? InferSchema<I> | null : never : unknown;
2434
+
2435
+ /**
2436
+ * Bincode serialization writer
2437
+ *
2438
+ * Matches Rust's bincode crate with default configuration:
2439
+ * - Little-endian byte order
2440
+ * - Fixed-size integer encoding (no varint)
2441
+ * - u64 length prefixes for dynamic collections
2442
+ * - u32 enum variant indices
2443
+ */
2444
+ declare class BincodeWriter {
2445
+ private buffer;
2446
+ private offset;
2447
+ private view;
2448
+ constructor(initialCapacity?: number);
2449
+ writeU8(value: number): this;
2450
+ writeU16(value: number): this;
2451
+ writeU32(value: number): this;
2452
+ writeU64(value: bigint | number): this;
2453
+ writeU128(value: bigint): this;
2454
+ writeI8(value: number): this;
2455
+ writeI16(value: number): this;
2456
+ writeI32(value: number): this;
2457
+ writeI64(value: bigint): this;
2458
+ writeI128(value: bigint): this;
2459
+ writeF32(value: number): this;
2460
+ writeF64(value: number): this;
2461
+ writeBool(value: boolean): this;
2462
+ writeBytes(bytes: Uint8Array): this;
2463
+ writeFixedArray(bytes: Uint8Array, expectedLength?: number): this;
2464
+ writeVecBytes(bytes: Uint8Array): this;
2465
+ writeString(str: string): this;
2466
+ writeVariant(index: number): this;
2467
+ writeOption<T>(value: T | null | undefined, writeValue: (writer: BincodeWriter, val: T) => void): this;
2468
+ writeVec<T>(items: T[], writeItem: (writer: BincodeWriter, item: T) => void): this;
2469
+ /**
2470
+ * Write a tuple (fixed-size heterogeneous collection)
2471
+ */
2472
+ writeTuple<T extends unknown[]>(items: T, writers: {
2473
+ [K in keyof T]: (writer: BincodeWriter, val: T[K]) => void;
2474
+ }): this;
2475
+ writeMap<K, V>(map: Map<K, V>, writeKey: (writer: BincodeWriter, key: K) => void, writeValue: (writer: BincodeWriter, value: V) => void): this;
2476
+ toBytes(): Uint8Array;
2477
+ /**
2478
+ * Get a view of the written bytes WITHOUT copying.
2479
+ *
2480
+ * ⚠️ WARNING: This returns a view into the internal buffer.
2481
+ * The view becomes INVALID if:
2482
+ * - The writer continues writing (may trigger resize)
2483
+ * - The writer is cleared via clear()
2484
+ *
2485
+ * Use toBytes() for a safe copy, or use this only for immediate
2486
+ * read-only access when performance is critical.
2487
+ */
2488
+ toView(): Uint8Array;
2489
+ length(): number;
2490
+ clear(): this;
2491
+ /**
2492
+ * Reserve additional capacity
2493
+ */
2494
+ reserve(additionalBytes: number): this;
2495
+ private ensureCapacity;
2496
+ }
2497
+
2498
+ /**
2499
+ * Serializes data using Borsh (Binary Object Representation Serializer for Hashing) encoding.
2500
+ *
2501
+ * Borsh is efficient for complex types like enums, Options, vectors, and nested structs.
2502
+ * Use the exported decorators (@field, @option, @vec) to define your data structures.
2503
+ *
2504
+ * @param data - Data object to serialize
2505
+ * @returns Serialized bytes
2506
+ *
2507
+ * @example
2508
+ * ```typescript
2509
+ * import { serializeBorsh, field, option } from '@rialo/ts-cdk';
2510
+ *
2511
+ * class SwapInstruction {
2512
+ * @field({ type: 'u8' })
2513
+ * instruction: number;
2514
+ *
2515
+ * @field({ type: 'u64' })
2516
+ * amountIn: bigint;
2517
+ *
2518
+ * @field({ type: option('u64') })
2519
+ * minAmountOut?: bigint;
2520
+ * }
2521
+ *
2522
+ * const data = serializeBorsh(new SwapInstruction({
2523
+ * instruction: 1,
2524
+ * amountIn: 1000n,
2525
+ * minAmountOut: 900n,
2526
+ * }));
2527
+ * ```
2528
+ */
2529
+ declare function serializeBorsh<T>(data: T): Uint8Array;
2530
+ /**
2531
+ * Deserializes Borsh-encoded data into a typed object.
2532
+ *
2533
+ * @param data - Borsh-encoded bytes
2534
+ * @param type - Class constructor for the target type
2535
+ * @returns Deserialized object instance
2536
+ */
2537
+ declare function deserializeBorsh<T>(data: Uint8Array, type: new () => T): T;
2538
+
2539
+ /**
2540
+ * Serializes a u16 value into compact encoding.
2541
+ *
2542
+ * @param buffer - Output buffer to append bytes to
2543
+ * @param value - Value to encode (0-65535)
2544
+ * @throws {TransactionError} If value is out of range
2545
+ */
2546
+ declare function serializeCompactU16(buffer: number[], value: number): void;
2547
+ /**
2548
+ * Deserializes a compact-u16 value from bytes.
2549
+ *
2550
+ * @param data - Input byte array
2551
+ * @param currentCursor - Starting position in the array
2552
+ * @returns Tuple of [decoded value, new cursor position]
2553
+ * @throws {TransactionError} If data is insufficient or malformed
2554
+ */
2555
+ declare function deserializeCompactU16(data: Uint8Array, currentCursor: number): [number, number];
2556
+ /**
2557
+ * Writes a compact-u16 value directly to a buffer (zero-copy).
2558
+ *
2559
+ * Optimized version for in-place writing without intermediate allocations.
2560
+ *
2561
+ * @param buffer - Target buffer
2562
+ * @param offset - Starting position to write at
2563
+ * @param value - Value to encode (0-127 only, uses 1-2 bytes)
2564
+ * @returns New offset after writing
2565
+ */
2566
+ declare function writeCompactU16(buffer: Uint8Array, offset: number, value: number): number;
2567
+
1808
2568
  /**
1809
2569
  * Interface for signing messages and transactions.
1810
2570
  *
@@ -2181,11 +2941,13 @@ declare class Message {
2181
2941
  readonly accountKeys: readonly PublicKey[];
2182
2942
  /** Transaction valid from (milliseconds since Unix epoch) */
2183
2943
  validFrom?: bigint;
2944
+ /** Config hash prefix for replay protection across chains */
2945
+ readonly configHashPrefix: bigint;
2184
2946
  /** Compiled instructions with account indices */
2185
2947
  readonly instructions: readonly CompiledInstruction[];
2186
2948
  /** Cached serialized bytes */
2187
2949
  private serializedCache?;
2188
- constructor(header: MessageHeader, accountKeys: readonly PublicKey[], validFrom: bigint, instructions: readonly CompiledInstruction[]);
2950
+ constructor(header: MessageHeader, accountKeys: readonly PublicKey[], validFrom: bigint, configHashPrefix: bigint, instructions: readonly CompiledInstruction[]);
2189
2951
  /**
2190
2952
  * Serialize message to bytes for signing.
2191
2953
  * Result is cached for performance.
@@ -2415,6 +3177,7 @@ declare class Transaction {
2415
3177
  declare class TransactionBuilder {
2416
3178
  private payer?;
2417
3179
  private validFrom?;
3180
+ private configHashPrefix?;
2418
3181
  private readonly instructions;
2419
3182
  private constructor();
2420
3183
  /**
@@ -2439,6 +3202,15 @@ declare class TransactionBuilder {
2439
3202
  * @param validFrom - Transaction valid from in milliseconds since Unix epoch
2440
3203
  */
2441
3204
  setValidFrom(validFrom: bigint): this;
3205
+ /**
3206
+ * Set the config hash prefix for replay protection.
3207
+ *
3208
+ * This is the first 64 bits of the config hash, used to ensure
3209
+ * transactions cannot be replayed on different chains.
3210
+ *
3211
+ * @param configHashPrefix - config hash prefix as a u64
3212
+ */
3213
+ setConfigHashPrefix(configHashPrefix: bigint): this;
2442
3214
  /**
2443
3215
  * Add an instruction to the transaction.
2444
3216
  *
@@ -2512,4 +3284,4 @@ declare function getMainnetUrl(): string;
2512
3284
  */
2513
3285
  declare function getLocalnetUrl(): string;
2514
3286
 
2515
- export { type AccountFilter, type AccountInfo, type AccountMeta, AccountMetaTable, BASE_DERIVATION_PATH, BaseRpcClient, type Bump, type ChainDefinition, type CompiledInstruction, type ConfirmTransactionOptions, type ConfirmedTransaction, CryptoError, CryptoErrorCode, DEFAULT_NUM_ACCOUNTS, type EpochInfoResponse, type EventData, type GetAccountsByOwnerConfig, type GetAccountsByOwnerResponse, type GetHealthResponse, type GetSignaturesForAddressConfig, type GetTransactionsConfig, type GetTransactionsResponse, type GetWorkflowLineageRequest, type GetWorkflowLineageResponse, HttpTransport, type HttpTransportConfig, type IdentifierString, type Instruction, KELVIN_PER_RLO, Keypair, KeypairSigner, Message, type MessageHeader, Mnemonic, type MnemonicStrength, type OwnerAccount, type PDA, PUBLIC_KEY_LENGTH, type PaginationInfo, PublicKey, QueryRpcClient, RIALO_DEVNET_CHAIN, RIALO_LOCALNET_CHAIN, RIALO_MAINNET_CHAIN, RIALO_SHITNET_CHAIN, RIALO_TESTNET_CHAIN, RialoClient, type RialoClientConfig, RialoError, RialoErrorType, type RialoNetwork, RpcError, RpcErrorCode, type RpcErrorDetails$1 as RpcErrorDetails, SECRET_KEY_LENGTH, SIGNATURE_LENGTH, SYSTEM_PROGRAM_ID, type Seed, type SendAndConfirmOptions, type SendTransactionOptions, Signature, type SignatureInfo, type SignatureStatus, type Signer, type Subscription, type SubscriptionKind, SystemInstruction, type TimestampRange, Transaction, TransactionBuilder, TransactionError, TransactionErrorCode, type TransactionNodeData, type TransactionResponse, TransactionRpcClient, type TriggerInfo, type TriggeredTransaction, type TruncationReason, URL_DEVNET, URL_LOCALNET, URL_MAINNET, URL_SHITNET, URL_TESTNET, type WorkflowLineage, type WorkflowNode, allocateInstruction, assignInstruction, calculateBackoff, concatBytes, createAccount, createBorshInstruction, createRialoClient, encodeBorshData, fromBase64, getDefaultRialoClientConfig, getDevnetUrl, getLocalnetUrl, getMainnetUrl, getTestnetUrl, isOnCurve, seedToBytes, sleep, toBase64, transferInstruction };
3287
+ export { type AccountFilter, type AccountInfo, type AccountMeta, AccountMetaTable, BASE_DERIVATION_PATH, BaseRpcClient, BincodeReader, type BincodeSchema, BincodeWriter, type Bump, CHACHA20_POLY1305_TAG_LENGTH, type ChainDefinition, type CompiledInstruction, type ConfirmTransactionOptions, type ConfirmedTransaction, CryptoError, CryptoErrorCode, DEFAULT_NUM_ACCOUNTS, ED25519_PUBLIC_KEY_LENGTH, type EnumVariant, type EpochInfoResponse, type EventData, type GetAccountsByOwnerConfig, type GetAccountsByOwnerResponse, type GetHealthResponse, type GetSecretSharingPubkeyResponse, type GetSignaturesForAddressConfig, type GetTransactionsResponse, type GetWorkflowLineageRequest, type GetWorkflowLineageResponse, HPKE_ENC_LENGTH, HPKE_OVERHEAD_LENGTH, HpkeError, HpkeErrorCode, HttpTransport, type HttpTransportConfig, type IdentifierString, type InferSchema, type Instruction, KELVIN_PER_RLO, Keypair, KeypairSigner, Message, type MessageHeader, Mnemonic, type MnemonicStrength, type OwnerAccount, type PDA, PUBLIC_KEY_LENGTH, type PaginationInfo, PublicKey, QueryRpcClient, RIALO_DEVNET_CHAIN, RIALO_LOCALNET_CHAIN, RIALO_MAINNET_CHAIN, RIALO_SHITNET_CHAIN, RIALO_TESTNET_CHAIN, RexValue, RexValueVariant, RialoClient, type RialoClientConfig, RialoError, RialoErrorType, type RialoNetwork, RpcError, RpcErrorCode, type RpcErrorDetails$1 as RpcErrorDetails, SECRET_KEY_LENGTH, SECRET_SHARING_HPKE_INFO, SIGNATURE_LENGTH, SYSTEM_PROGRAM_ID, Schema, type Seed, type SendAndConfirmOptions, type SendTransactionOptions, Signature, type SignatureInfo, type SignatureStatus, type Signer, type StructField, type Subscription, type SubscriptionKind, SystemInstruction, type TimestampRange, Transaction, TransactionBuilder, TransactionError, TransactionErrorCode, type TransactionNodeData, type TransactionResponse, TransactionRpcClient, type TriggerInfo, type TriggeredTransaction, type TruncationReason, URL_DEVNET, URL_LOCALNET, URL_MAINNET, URL_SHITNET, URL_TESTNET, USER_SECRET_AAD, type WorkflowLineage, type WorkflowNode, X25519_PUBLIC_KEY_LENGTH, allocateInstruction, assignInstruction, calculateBackoff, concatBytes, createAccount, createBorshInstruction, createRialoClient, deserialize, deserializeBorsh, deserializeCompactU16, deserializeStrict, encodeBorshData, encryptForRex, fromBase64, getCiphertextLength, getDefaultRialoClientConfig, getDevnetUrl, getLocalnetUrl, getMainnetUrl, getTestnetUrl, hpkeEncrypt, isOnCurve, isValidCiphertextLength, seedToBytes, serialize, serializeBorsh, serializeCompactU16, sleep, toBase64, transferInstruction, writeCompactU16 };