npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@rialo/ts-cdk

v0.12.2

Published

Rialo CDK - A comprehensive toolkit for building with the Rialo blockchain

Readme

@rialo/ts-cdk

TypeScript library for building on the Rialo blockchain. Provides Ed25519 cryptographic primitives, BIP39/SLIP-0010 HD wallet derivation, transaction construction and signing, a JSON-RPC client for node communication, program deployment, and HPKE encryption for TEE programs. Works in Node.js ≥ 18 and modern browsers (ESM and CJS bundles included).

Installation

npm install @rialo/ts-cdk
# or
pnpm add @rialo/ts-cdk
# or
yarn add @rialo/ts-cdk

Requires Node.js ≥ 18. Ships both ESM (dist/index.mjs) and CJS (dist/index.js) bundles with bundled TypeScript declarations. Works in modern browsers when bundled with Vite/webpack.

Key public types

Cryptography

| Export | Purpose | |---|---| | Keypair | Ed25519 keypair; generate, derive from seed, sign, verify, dispose | | PublicKey | 32-byte Ed25519 public key; PDA derivation, base58 encoding | | Signature | 64-byte Ed25519 signature; base58 encoding | | Mnemonic | BIP39 mnemonic; generate, restore, derive keypairs via SLIP-0010 |

Keyring management

| Export | Purpose | |---|---| | RialoKeyring | Named collection of Keypair instances with an active signing key | | InMemoryKeyringProvider | Create RialoKeyring from a mnemonic or a list of keypairs | | DerivedKeypairInfo | Metadata for a single derived keypair (index, pubkey, path) |

Transactions

| Export | Purpose | |---|---| | TransactionBuilder | Fluent builder for constructing transactions | | Transaction | Signed/unsigned transaction; serialize, deserialize, multi-sig | | Message | Compiled transaction message with account keys and instructions | | Instruction | Single operation: program ID, accounts, data | | AccountMeta | Account reference with isSigner / isWritable flags | | AccountMetaTable | Deduplication table for account references within a message | | transferInstruction | System-program transfer helper | | createAccount | System-program create-account helper |

RPC

| Export | Purpose | |---|---| | createRialoClient | Factory for RialoClient; accepts a chain preset or custom config | | getDefaultRialoClientConfig | Returns a RialoClientConfig for "mainnet", "devnet", "testnet", or "localnet" | | RialoClient | Full RPC surface for a Rialo node | | RIALO_MAINNET_CHAIN / …TESTNET… / …DEVNET… / …LOCALNET… | Chain presets |

Other

| Export | Purpose | |---|---| | Signer / KeypairSigner | Abstract signing interface for hardware wallets and custom signers | | ProgramDeployment | Deploy PolkaVM program binaries to the network | | RexValue | Typed wrapper for plain or HPKE-encrypted byte payloads | | RialoError / RialoErrorType | Structured error with discriminated type field |

Usage

Keypair and signing

import { Keypair, PublicKey } from "@rialo/ts-cdk";

// Generate a random keypair
const keypair = Keypair.generate();
console.log("Address:", keypair.publicKey.toString());

// Restore from a known 32-byte secret key
const restored = Keypair.fromSecretKey(secretKeyBytes);

const message = new TextEncoder().encode("Hello Rialo");
const sig = keypair.sign(message);
const ok = keypair.verify(message, sig);

// Always dispose keypairs when finished to zero out the private key.
keypair.dispose();

BIP39 mnemonic and HD derivation

Rialo uses BIP44 coin type 756 with SLIP-0010 (m/44'/756'/{index}'/0').

import { Mnemonic } from "@rialo/ts-cdk";

// Generate a new 12-word mnemonic (pass 256 for 24-word)
const mnemonic = Mnemonic.generate();           // 128-bit entropy, 12 words
console.log(mnemonic.toString());
console.log("Words:", mnemonic.getWordCount()); // 12

// Validate a phrase without constructing a Mnemonic
const valid = Mnemonic.isValid("word1 word2 … word12");

// Restore from an existing phrase
const restored = Mnemonic.fromPhrase("word1 word2 … word12");

// Derive account keypairs
const account0 = await mnemonic.toKeypair(0);  // m/44'/756'/0'/0'
const account1 = await mnemonic.toKeypair(1);  // m/44'/756'/1'/0'

// With an optional BIP39 passphrase
const secure = await mnemonic.toKeypair(0, { passphrase: "my-secret" });

// Derive with an explicit full path (advanced)
const custom = await mnemonic.toKeypairWithPath("m/44'/756'/0'/0'");

// Derive multiple at once (indices 0–4)
const keypairs = await mnemonic.deriveKeypairs(5);

// Convert to raw 64-byte BIP39 seed
const seed = await mnemonic.toSeed();

Keyring management

RialoKeyring manages a set of derived keypairs and tracks the active signing key, useful when an application needs to sign on behalf of multiple accounts.

import { Mnemonic, InMemoryKeyringProvider } from "@rialo/ts-cdk";

const mnemonic = Mnemonic.generate();
const provider = new InMemoryKeyringProvider();

// Derive 3 keypairs into a single keyring
const keyring = await provider.createFromMnemonic(mnemonic, 3);

// Switch the active keypair
keyring.setActiveKeypair(2);
console.log("Active:", keyring.pubkeyString());

// Sign with the active keypair
const sig = keyring.sign(messageBytes);

// Sign with a specific keypair without switching active
const sig1 = keyring.signWithKeypair(messageBytes, 1);

// Inspect all keypairs
for (const info of keyring.getKeypairsInfo()) {
  console.log(`index=${info.index}  pubkey=${info.pubkeyString}`);
}

// Securely zero all private keys when done
keyring.dispose();

Build and send a transaction

TransactionBuilder requires a configHashPrefix fetched from the network. Every transaction submitted to a live node must carry the current prefix or it will be rejected.

import {
  TransactionBuilder,
  transferInstruction,
  createRialoClient,
  getDefaultRialoClientConfig,
  RIALO_DEVNET_CHAIN,
} from "@rialo/ts-cdk";

// Using a chain preset directly
const client = createRialoClient({ chain: RIALO_DEVNET_CHAIN });

// Or by network name — useful when network comes from config/env
// const client = createRialoClient(getDefaultRialoClientConfig("devnet"));

const configHashPrefix = await client.getConfigHashPrefix();  // required

const transfer = transferInstruction(
  keypair.publicKey,
  recipientPubkey,
  1_000_000n,       // amount in kelvin; 1 RLO = 1_000_000_000 kelvin
);

const tx = TransactionBuilder.create()
  .setPayer(keypair.publicKey)
  .setValidFrom(BigInt(Date.now()))
  .setConfigHashPrefix(configHashPrefix)
  .addInstruction(transfer)
  .build();

const signedTx = tx.sign(keypair);
const sig = await client.sendTransaction(signedTx.serialize());
console.log("Signature:", sig.toString());

Multi-sig transactions

// Each partial sign adds one signer's signature; isSigned() returns true when all
// required signers have contributed.
const partial = tx.partialSign(signer1);
const complete = partial.partialSign(signer2);
complete.ensureSigned();              // throws if any signature is missing

// Async signer interface (hardware wallets, browser extensions, etc.)
const signedAsync = await tx.signWith(new KeypairSigner(keypair));

Deserialize a transaction

Transaction.deserialize reconstructs a transaction from its wire bytes — useful for inspecting or re-signing transactions received from another party.

import { Transaction } from "@rialo/ts-cdk";

// Reconstruct from wire bytes (e.g. received over a socket)
const tx = Transaction.deserialize(wireBytes);

// Inspect the compiled message
for (const ix of tx.message.instructions) {
  console.log("program:", ix.programId.toString());
}

// Re-sign (e.g. when acting as co-signer)
const reSigned = tx.partialSign(myKeypair);

Borsh serialization for instruction data

Use Borsh to encode typed parameters into the opaque data field of an Instruction.

import { field, serialize, deserialize } from "@dao-xyz/borsh";
import { Instruction, AccountMeta } from "@rialo/ts-cdk";

class TransferParams {
  @field({ type: "u64" }) amount!: bigint;
  constructor(amount: bigint) { this.amount = amount; }
}

const params = new TransferParams(1_000_000n);
const data = Buffer.from(serialize(params));

const ix = new Instruction({
  programId: myProgramId,
  accounts: [new AccountMeta({ pubkey: myAccount, isSigner: false, isWritable: true })],
  data,
});

Program Derived Addresses (PDAs)

PDAs are off-curve addresses deterministically derived from seeds and a program ID. No private key exists; only the program can sign on their behalf.

import { PublicKey } from "@rialo/ts-cdk";

// Automatic bump discovery — returns [address, bump]
const [vaultPda, bump] = PublicKey.findProgramAddress(
  ["vault", userPubkey.toBytes()],
  programId,
);

// With known bump (more efficient)
const pda = PublicKey.createProgramAddress(
  ["metadata", mintPubkey.toBytes(), new Uint8Array([bump])],
  metadataProgramId,
);

Note: Each seed must be ≤ 32 bytes; at most 16 seeds per derivation. String seeds are UTF-8-encoded automatically.

Deploy a program

import { ProgramDeployment } from "@rialo/ts-cdk";

const deployment = new ProgramDeployment({
  programData: fs.readFileSync("program.polkavm"),
  programKeypair: programKeypair,
  config: {
    chunkSize: 900,         // bytes per upload chunk
    maxRetries: 5,
  },
});

const programId = await deployment.deploy(client, payerKeypair);
console.log("Program deployed:", programId.toString());

Encrypt a secret for TEE programs

RexValue wraps a plain or HPKE-encrypted payload. Use it to pass sensitive data to programs that run inside a Trusted Execution Environment (TEE). The node's HPKE public key is fetched via getSecretSharingPubkey(); the CDK handles the HPKE encryption.

import { RexValue } from "@rialo/ts-cdk";

// 1. Fetch the TEE's HPKE public key from the node
const skPub = await client.getSecretSharingPubkey();

// 2. Encrypt your secret — RexValue.fromPlaintext performs HPKE encryption
const plaintext = new TextEncoder().encode("Bearer sk-…");
const rexValue = await RexValue.fromPlaintext(plaintext, skPub);

// 3. Serialise as Borsh bytes and embed in your instruction data
const borshBytes = rexValue.toBorsh();

To include unencrypted bytes (for non-sensitive payloads):

const plain = RexValue.plain(new TextEncoder().encode("public-data"));
const borshBytes = plain.toBorsh();

Custom signer (hardware wallets)

import { type Signer, PublicKey, Signature } from "@rialo/ts-cdk";

class LedgerSigner implements Signer {
  async getPublicKey(): Promise<PublicKey> {
    return PublicKey.fromBytes(await ledger.getPublicKey());
  }
  async signMessage(message: Uint8Array): Promise<Signature> {
    const sigBytes = await ledger.sign(message);
    return Signature.fromBytes(sigBytes);
  }
}

const signedTx = await tx.signWith(new LedgerSigner());

Subscription workflows (REX)

REX subscriptions let a program trigger downstream transactions automatically. Use getSubscription to inspect an active subscription and getTriggeredTransactions to audit which transactions it has fired.

import { createRialoClient, RIALO_DEVNET_CHAIN } from "@rialo/ts-cdk";

const client = createRialoClient({ chain: RIALO_DEVNET_CHAIN });

// Look up a subscription by subscriber address and nonce
const subscription = await client.getSubscription(subscriberPubkey, nonce);
console.log("Topic:", subscription.topic);
console.log("Kind:", subscription.kind);

// List the last 10 transactions triggered by this subscription account
const triggered = await client.getTriggeredTransactions(subscriptionAccount, 10);
for (const tx of triggered) {
  console.log(`sig=${tx.signature}  block=${tx.blockNumber}`);
}

Workflow lineage

const lineage = await client.getWorkflowLineage(request);
// lineage.nodes contains the DAG of related transactions.

Error handling

import { RialoError, RialoErrorType } from "@rialo/ts-cdk";

try {
  await client.sendTransaction(signedTx.serialize());
} catch (err) {
  if (err instanceof RialoError) {
    switch (err.type) {
      case RialoErrorType.RPC:
        console.error("Node error", err.details?.code, err.details?.message);
        break;
      case RialoErrorType.NETWORK:
        console.error("Network failure:", err.cause);
        break;
      case RialoErrorType.INVALID_INPUT:
        console.error("Bad argument:", err.message);
        break;
      default:
        throw err;
    }
  }
}

Error types

| RialoErrorType | Condition | |---|---| | RPC | Node rejected the request | | NETWORK | HTTP/network failure | | TRANSACTION | Transaction build or signing error | | WALLET | Keypair load or create failure | | ENCRYPTION | HPKE encryption/decryption failure | | BIP32 | HD key derivation error | | INVALID_INPUT | Invalid parameter or data | | PARSE_PUBKEY | Public key parse failure | | INVALID_BLOCKHASH_FORMAT | Blockhash format error | | CONFIG | Configuration load or parse failure | | JSON | JSON parse error | | SERIALIZATION | Borsh/bincode serialisation error | | PASSWORD | Password validation failure |

RPC reference

| Method | Returns | Notes | |---|---|---| | getConfigHashPrefix() | ConfigHashPrefix | Required for every TransactionBuilder | | getBalance(pubkey) | Kelvin | Balance as bigint | | sendTransaction(bytes, opts?) | Signature | Submit signed bytes | | sendAndConfirmTransaction(bytes, opts?) | ConfirmedTransaction | Submit and poll | | confirmTransaction(sig, opts?) | ConfirmedTransaction | Poll by signature | | getAccountInfo(pubkey) | AccountInfo | Raw account data | | getMultipleAccounts(pubkeys) | OptionalAccountInfo[] | Batch query | | getAccountsByOwner(owner, filter?) | [OwnerAccount[], PaginationInfo?] | Program accounts | | getBlockHeight() | bigint | Finalized height | | getTransaction(sig) | TransactionResponse | By signature | | getEpochInfo() | EpochInfo | Current epoch | | getSignaturesForAddress(pubkey) | SignatureInfo[] | Transaction history for an account | | requestAirdrop(pubkey, kelvin) | Signature | Devnet/testnet only | | requestAirdropAndConfirm(pubkey, kelvin) | ConfirmedTransaction | Airdrop + wait | | getFeeForMessage(base64Msg) | FeeResponse | Estimate fee before sending | | getMinimumBalanceForRentExemption(size) | bigint | Rent-exempt threshold | | getSecretSharingPubkey() | SecretSharingPubkey | TEE HPKE public key | | getWorkflowLineage(req) | GetWorkflowLineageResponse | Workflow DAG traversal | | getSubscription(subscriber, nonce) | Subscription | REX subscription lookup | | getTriggeredTransactions(account, limit?) | TriggeredTransaction[] | Subscription-triggered txs |

Constants

import {
  KELVIN_PER_RLO,         // 1_000_000_000
  SYSTEM_PROGRAM_ID,       // "11111111111111111111111111111111"
  PUBLIC_KEY_LENGTH,       // 32
  SECRET_KEY_LENGTH,       // 32
  SIGNATURE_LENGTH,        // 64
  URL_MAINNET,             // "https://mainnet.rialo.io:4101"
  URL_TESTNET,             // "https://testnet.rialo.io:4101"
  URL_DEVNET,              // "https://devnet.rialo.io:4101"
  URL_LOCALNET,            // "http://localhost:4104"
} from "@rialo/ts-cdk";

// Currency conversion (KELVIN_PER_RLO is a number; use BigInt() when passing to RPC methods)
const kelvin = BigInt(Math.round(1.5 * KELVIN_PER_RLO));   // 1.5 RLO → 1_500_000_000n kelvin

Caveats

  • configHashPrefixTransactionBuilder.setConfigHashPrefix() is required. Omitting it or using a stale value causes the node to reject the transaction with a replay-protection error.

  • Currency units — all RPC amounts are in kelvin; 1 RLO = KELVIN_PER_RLO (1 000 000 000) kelvin. The transferInstruction helper takes kelvin as bigint.

  • Derivation path — Rialo uses BIP44 coin type 756. Mnemonic.toKeypair(index) uses m/44'/756'/{index}'/0'. Keys derived on other coin types are not compatible.

  • Keypair disposal — call keypair.dispose() (and keyring.dispose()) when the keypair is no longer needed. After disposal, signing methods throw CryptoError.

  • PDA seeds — strings are UTF-8-encoded; Uint8Array seeds are used as-is. A seed exceeding 32 bytes throws CryptoError.MAX_SEED_LENGTH_EXCEEDED.

  • Node.js version — requires Node.js ≥ 18 for the native crypto module and TextEncoder/TextDecoder globals.

  • AccountMetaTable — used internally by TransactionBuilder to deduplicate account references in a compiled Message. Constructing it manually is only needed for advanced multi-program transactions.

Development

pnpm install
pnpm build       # compiles ESM + CJS bundles to dist/
pnpm test        # runs vitest suite
pnpm lint        # biome check

See also

  • rialo-cdk — underlying Rust crate; source of truth for wire format and error codes
  • rialo-py-cdk — Python bindings with equivalent API surface
  • developer-frameworks/cdk/spec.wit — WIT specification from which the RPC surface is derived
  • developer-frameworks/cdk/rialo-ts-cdk/examples/ — runnable end-to-end examples