npm package: @kamino-finance/metavault-sdk
Description: TypeScript SDK for the Kamino MetaVault program
Latest version: 0.1.0

# @kamino-finance/metavault-sdk

TypeScript SDK for the Kamino MetaVault program on Solana. Provides instruction builders and account decoders for managing multi-token vaults with rebalancing, fee management, and Scope oracle integration.

## Installation

```bash
yarn add @kamino-finance/metavault-sdk
```

## Program IDs

| Environment | Address |
|-------------|---------|
| Production  | `KMVDpdAL8Ric1GfxJPqnQN5w7Mojex1rnSoEMq8QBZG` |
| Staging     | `SkmjBqY7J6jemkXeTNkiWhcYRLo4JHFsQ6zzjxvz8YC` |

## Usage

### Initialize the client

```typescript
import { MetaVaultClient, PROGRAM_ID } from '@kamino-finance/metavault-sdk';

const client = new MetaVaultClient(rpc, PROGRAM_ID);
```

### Create a vault

```typescript
import { generateKeyPairSigner } from '@solana/kit';
import { getCreateAccountInstruction } from '@solana-program/system';
import { TOKEN_PROGRAM_ADDRESS } from '@solana-program/token';
import { VAULT_STATE_SPACE } from '@kamino-finance/metavault-sdk';

const vaultKeypair = await generateKeyPairSigner();

const rentLamports = await rpc
  .getMinimumBalanceForRentExemption(VAULT_STATE_SPACE)
  .send();

const createAccountIx = getCreateAccountInstruction({
  payer: admin,
  space: VAULT_STATE_SPACE,
  lamports: rentLamports,
  programAddress: PROGRAM_ID,
  newAccount: vaultKeypair,
});

const initIx = await client.initVaultIx(
  admin,
  vaultKeypair.address,
  tokenMint,
  TOKEN_PROGRAM_ADDRESS,
  scopeConfiguration
);

// Send [createAccountIx, initIx] in a single transaction
```

### Buy vault shares (single token)

```typescript
const result = await client.buyIx(
  user,
  vaultAddress,
  tokenMint,
  1_000_000n, // maxAmount
  0n          // minSharesOut (slippage)
);

// Send [...result.setupIxs, result.buyIx]
```

### Sell vault shares (single token)

```typescript
const result = await client.sellIx(
  user,
  vaultAddress,
  tokenMint,
  sharesToSell, // shares amount
  0n            // minTokensOut (slippage)
);

// Send [...result.setupIxs, result.sellIx]
```

### Proportional buy (all tokens)

```typescript
const result = await client.buyProportionalIx(
  user,
  vaultAddress,
  [1_000_000n, 1_000_000n] // one max amount per enabled token
);

// Send [...result.setupIxs, result.buyProportionalIx]
```

### Proportional sell (all tokens)

```typescript
const result = await client.sellProportionalIx(
  user,
  vaultAddress,
  sharesToBurn
);

// Send [...result.setupIxs, result.sellProportionalIx]
```

### Query vault state

```typescript
const vaultState = await client.fetchVaultState(vaultAddress);
const enabledTokens = client.getEnabledTokens(vaultState);
const name = client.decodeVaultName(vaultState.name);
const pendingFees = client.getPendingFees(vaultState);
```

### Admin operations

```typescript
// Add a second token to the vault
await client.addVaultTokenIx(admin, vaultAddress, tokenBMint, TOKEN_PROGRAM_ADDRESS, scopeConfig);

// Update vault configuration
await client.updateVaultConfigIx(admin, vaultAddress, new VaultConfigField.PerformanceFeeBps(), data);

// Rebalancing
await client.startRebalanceIx(admin, vaultAddress, 3600n); // duration in seconds
await client.stopRebalanceIx(admin, vaultAddress);

// Fee withdrawal
const result = await client.withdrawPendingFeesIx(admin, vaultAddress);

// Shares token metadata (Metaplex)
await client.initializeSharesMetadataIx(admin, vaultAddress, 'My Vault', 'MV', 'https://example.com');
```

## API Reference

### MetaVaultClient

The primary class for building instructions against the MetaVault program.

```typescript
new MetaVaultClient(rpc: Rpc<SolanaRpcApi>, programId?: Address)
```

#### Account loaders

| Method | Description |
|--------|-------------|
| `fetchVaultState(address)` | Fetch and decode a vault's on-chain state |
| `fetchGlobalConfig()` | Fetch the protocol's global configuration |

#### Buy / Sell

| Method | Description |
|--------|-------------|
| `buyIx(user, vault, mint, maxAmount, minSharesOut)` | Buy shares with a single token (fetches state) |
| `buildBuyIx(user, vault, state, mint, maxAmount, minSharesOut)` | Buy shares (uses provided state) |
| `sellIx(user, vault, mint, sharesAmount, minTokensOut)` | Sell shares for a single token (fetches state) |
| `buildSellIx(user, vault, state, mint, sharesAmount, minTokensOut)` | Sell shares (uses provided state) |
| `buyProportionalIx(user, vault, maxAmounts[])` | Buy all vault tokens proportionally |
| `sellProportionalIx(user, vault, sharesToBurn)` | Sell to receive all vault tokens proportionally |

#### Admin

| Method | Description |
|--------|-------------|
| `initVaultIx(admin, vault, mint, tokenProgram, scopeConfig)` | Create a new vault with an initial token |
| `addVaultTokenIx(admin, vault, mint, tokenProgram, scopeConfig)` | Add a token to an existing vault (max 10) |
| `updateVaultConfigIx(admin, vault, field, data)` | Update vault parameters |
| `updateAdminIx(pendingAdmin, vault)` | Accept admin transfer |
| `withdrawPendingFeesIx(admin, vault)` | Withdraw accumulated fees as shares |
| `giveUpPendingFeesIx(admin, vault, maxAmount)` | Reduce pending fees |

#### Rebalancing

| Method | Description |
|--------|-------------|
| `startRebalanceIx(admin, vault, duration)` | Begin a rebalance period |
| `finishRebalanceIx(vault)` | Complete the current rebalance |
| `stopRebalanceIx(admin, vault)` | Cancel the current rebalance |
| `rebalanceSwapIx(user, vault, tokenIn, tokenOut, amountIn, minOut)` | Swap tokens during rebalance |

#### Query helpers

| Method | Description |
|--------|-------------|
| `getEnabledTokens(vaultState)` | List tokens currently active in the vault |
| `decodeVaultName(nameBytes)` | Decode the vault name from on-chain bytes |
| `getPendingFees(vaultState)` | Get pending fees as a `Decimal` |

### MetaVault

Higher-level wrapper around a single vault with cached state.

```typescript
const vault = await MetaVault.load(client, vaultAddress);
vault.getState();
vault.getEnabledTokens();
vault.getVaultName();
vault.getPendingFees();
await vault.reloadState();
```

All instruction methods from `MetaVaultClient` are also available on `MetaVault`, using the cached state to avoid redundant fetches.

## Development

### Build

```bash
yarn build
```

### Test

Tests run against a local Solana validator with pre-deployed programs.

```bash
# Start validator and run tests in one command
yarn start-validator-and-test

# Or separately
yarn start-validator   # in one terminal
yarn test              # in another
```

### Code generation

Regenerate TypeScript types from the program IDL:

```bash
yarn codegen
```

### Lint

```bash
yarn lint       # check
yarn lint:fix   # auto-format
```

## License

MIT