HESTIAdocs

The Hestia client

Every field of HestiaConfig, how Hestia.create wires the chain clients, and the Node vs. browser profiles.


Hestia is the single object an agent holds. You build it once with Hestia.create(config), and it owns the public client (reads), the wallet client (submits), the local store, and the indexer.

HestiaConfig

ts
interface HestiaConfig {
  chain: Chain;                 // viem chain (base | baseSepolia | foundry)
  rpcUrl: string;               // RPC endpoint for reads
  pool: Address;                // HestiaPool contract
  registry: Address;            // AssociationSetRegistry contract
  usdc: Address;                // USDC token address for this chain
  account: Account | Address;   // signer (Node) or connected address (browser)
  keys: Keys;                   // derived identity (sk, SK, vk, VK)
  association: AssociationProvider; // supplies the association root + proofs
  artifacts: ArtifactsByArity;  // wasm/zkey sources for proving
  transport?: Transport;        // optional: browser wallet transport
  metaChain?: ChainName;        // chain tag for your meta-address (default "baseSepolia")
}
FieldNotes
chainA viem Chain. The console maps NEXT_PUBLIC_HESTIA_CHAIN to base / baseSepolia / foundry.
rpcUrlUsed to build the read client and, unless transport is given, the wallet client too.
pool / registryDeployed contract addresses for the target chain.
usdcThe token address; USDC_ADDRESS.base / .baseSepolia are provided.
accountAn Account (e.g. privateKeyToAccount) in Node; the connected Address in the browser.
keysFrom deriveKeysFromSeed / deriveKeysFromSignature.
associationAny AssociationProvider.
artifactsPer-arity wasm/zkey. Paths in Node, URLs in the browser.
transportPass custom(window.ethereum) so the user's wallet signs and submits.
metaChainThe chain tag baked into hestia.metaAddress. Defaults to baseSepolia.

What create builds

ts
static async create(cfg: HestiaConfig): Promise<Hestia>;

Internally it constructs:

  • a public clientcreatePublicClient({ chain, transport: http(rpcUrl) }) — for all reads (leaf index, receipts, events);
  • a wallet clientcreateWalletClient({ account, chain, transport: transport ?? http(rpcUrl) }) — for approve, shield, and submitting transactions; and
  • a fresh store + indexer bound to the pool and registry.

The address the SDK acts as is resolved from account (the address itself, or account.address for an Account).

Node profile

A server-side agent signs with an in-process key and talks to an RPC directly:

ts
import { privateKeyToAccount } from "viem/accounts";

const hestia = await Hestia.create({
  chain: baseSepolia,
  rpcUrl: "https://sepolia.base.org",
  pool, registry, usdc,
  account: privateKeyToAccount(process.env.AGENT_KEY as `0x${string}`),
  keys, association, artifacts,
  // transport omitted → defaults to http(rpcUrl)
});

Browser profile

In a dApp the user's wallet signs. Pass a custom transport and the connected address:

ts
import { createWalletClient, custom, hexToBytes } from "viem";
import { deriveKeysFromSignature, KEY_DERIVATION_MESSAGE } from "@hestia/sdk";

const transport = custom(window.ethereum);
const wallet = createWalletClient({ chain, transport });
const [address] = await wallet.requestAddresses();

const sig = await wallet.signMessage({ account: address, message: KEY_DERIVATION_MESSAGE });
const keys = await deriveKeysFromSignature(hexToBytes(sig));

const hestia = await Hestia.create({
  chain, rpcUrl, pool, registry, usdc,
  account: address,   // an Address, not an Account
  transport,          // user's wallet signs + submits
  keys, association, artifacts,
});

This is exactly how the Labs console is wired.

The instance surface

ts
hestia.metaAddress;            // string — share to receive
hestia.exportViewingKey();     // Hex — for selective disclosure
await hestia.sync();           // pull latest events into the local index
await hestia.balance(token);   // bigint — sum of unspent notes
await hestia.shield({ token, amount });
await hestia.send({ token, amount, to, fee? });
await hestia.unshield({ token, amount, to, fee? });

Each is detailed in operations, and the full type signatures are in the API reference.