<!--
Sitemap:
- [Newton Agent NeoBank](/index)
- [Getting Started](/getting-started)
- [Onboard an Agent](/guides/onboard-an-agent)
- [Give an Agent a Budget](/guides/agent-budget)
- [Pay for an API](/guides/pay-for-an-api)
- [Issue a Card](/guides/issue-a-card)
- [Meter Your API](/guides/meter-your-api)
- [SDK Essentials](/reference/sdk)
- [ModularVault](/reference/sdk/modular-vault)
- [PlatformClient](/reference/sdk/platform-client)
- [FacilitatorClient](/reference/sdk/facilitator-client)
- [createX402Fetch](/reference/sdk/create-x402-fetch)
- [buildPolicyParams](/reference/sdk/build-policy-params)
- [Networks & Addresses](/reference/networks)
-->

# ModularVault

Connect to a custody vault to read balances, manage agents, install per-agent policy modules, and move funds.

```typescript
import { ModularVault } from "@newton-xyz/isaac";
```

## Connecting

There are two ways to connect, depending on who holds the signing key.

### Direct mode

You hold the operator key locally — best for scripts and backends that sign their own transactions.

```typescript
const vault = ModularVault.connect({
  rpcUrl: "https://sepolia.base.org",
  vaultAddress: "0x...",
  operatorKey: "0x...", // operator private key
  chainId: 84532, // optional, defaults to Base Sepolia
});
```

`connect(config)` — `rpcUrl`, `vaultAddress`, and `operatorKey` are required; `chainId` is optional.

### Managed mode

The signing key lives in a managed signing service and agent creation and signing go through the hosted API. Admin operations (withdraw, shutdown, module install) still need a local wallet or the dashboard.

```typescript
const vault = ModularVault.connectManaged({
  rpcUrl: "https://sepolia.base.org",
  vaultAddress: "0x...",
  platformApiUrl: "https://api.example.com",
  platformApiKey: "nab_sk_...",
  chainId: 84532, // optional
});
```

## Reading balances

```typescript
const usdc = await vault.getBalance("0x036CbD..."); // bigint, raw token units
const { eth, tokens } = await vault.getBalances(["0x036CbD...", "0x8cff..."]);
```

`getBalance(token)` returns the raw on-chain balance as a `bigint`. `getBalances(tokens)` returns `{ eth, tokens }` — the vault's ETH balance plus a map of each token address to its balance.

## Agents (managed mode)

```typescript
const { agent, signer } = await vault.createAgent("research-bot");
const platform = vault.getPlatformClient(); // listAgents, refreshSession, ...
```

`createAgent(name)` provisions an agent with a managed signing session and returns a `NewtonAgent` plus its `AgentSigner`. Both methods require managed mode.

## Modules

Each (agent, rail) pair has its own policy module. Pass the rail as a `Rail` value — `Rail.Token` for on-chain token payments, `Rail.Card` for the card rail.

```typescript
import { Rail } from "@newton-xyz/isaac";

const module = await vault.getModule(agentAddress, Rail.Token); // module address
const installed = await vault.isInstalledModule(module); // boolean

await vault.installModule(agentAddress, Rail.Token, moduleAddress); // tx hash
await vault.uninstallModule(agentAddress, Rail.Token);
```

## Funds and admin

```typescript
await vault.fundERC20(tokenAddress, 1_000_000n); // deposit ERC-20
await vault.fundETH(1_000_000_000_000_000n);     // deposit ETH (wei)
await vault.withdraw(tokenAddress, 500_000n, recipient);
await vault.emergencyShutdown(); // pause the vault
await vault.unpause();
```

Every write method returns a transaction hash.

## See also

* [PlatformClient](/reference/sdk/platform-client) — manage agents, policy, and cards over HTTP.
* [buildPolicyParams](/reference/sdk/build-policy-params) — construct an agent's spending policy.
