> For the complete documentation index, see [llms.txt](https://docs.yield.fi/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.yield.fi/earn-with-yieldfi/integration-sdk/contracts/manager-v3.md).

# Manager (V3)

The Manager V3 contract is the core protocol contract for deposits and withdrawals in YieldFi v3.

### Connecting to Manager V3

#### Using Wagmi

```typescript
import { connectManagerV3, getContractAddresses, Chain } from "yieldfi-sdk";
import { ethers } from "ethers";
import { useAccount, useWalletClient } from "wagmi";
import ManagerV3ABI from "yieldfi-sdk/abis/v3/Manager.json";

function ManagerV3Example() {
  const { address } = useAccount();
  const { data: walletClient } = useWalletClient();

  const connectManager = async () => {
    if (!walletClient || !address) {
      throw new Error("Wallet not connected");
    }

    const provider = new ethers.BrowserProvider(walletClient);
    const signer = await provider.getSigner();

    const contracts = getContractAddresses(Chain.ETHEREUM);
    const managerV3 = connectManagerV3(
      contracts.manager,
      ManagerV3ABI,
      signer
    );

    return managerV3;
  };
}
```

#### Using Browser Provider

```typescript
import { connectManagerV3, getContractAddresses, Chain } from "yieldfi-sdk";
import { ethers } from "ethers";
import ManagerV3ABI from "yieldfi-sdk/abis/v3/Manager.json";

// Connect to browser wallet
if (!window.ethereum) {
  throw new Error("No wallet found");
}

const provider = new ethers.BrowserProvider(window.ethereum);
const signer = await provider.getSigner();

// Get contract address
const contracts = getContractAddresses(Chain.ETHEREUM);

// Connect to Manager V3
const managerV3 = connectManagerV3(
  contracts.manager,
  ManagerV3ABI,
  signer // or provider for read-only operations
);
```

### Common Operations

#### Deposit Assets

Deposit assets to a vault and receive vault shares.

```typescript
// 1. Approve asset spending
await assetToken.approve(managerV3.target, amount);

// 2. Deposit via Manager V3
const shares = await managerV3.deposit(
  vaultAddress, // Vault address
  assetAddress, // Asset to deposit
  amount, // Amount to deposit
  receiver, // Receiver address
  minShares, // Minimum shares to receive (slippage protection, can be 0)
  referralCode // Referral code (bytes32, can be ethers.ZeroHash)
);

// Returns: shares received (bigint)
```

**Parameters:**

* `vault` - Vault contract address
* `asset` - Asset token address to deposit
* `amount` - Amount of asset to deposit
* `receiver` - Address that will receive vault shares
* `minShares` - Minimum shares to receive (slippage protection)
* `referralCode` - Referral code (bytes32)

#### Request Redemption

Request redemption from a vault. Shares are locked (not burned) until processed.

```typescript
await managerV3.requestRedemption(
  vaultAddress, // Vault address
  shares, // Amount of shares to redeem
  owner, // Owner of shares
  receiver // Receiver address (can be different from owner)
);

// Shares are locked in redemption queue
// Use cancelRedemption() to unlock if needed
```

**Parameters:**

* `vault` - Vault contract address
* `shares` - Amount of shares to redeem
* `owner` - Owner of the shares
* `receiver` - Address that will receive redemption assets

#### Cancel Redemption

Cancel a pending redemption request and unlock shares.

```typescript
await managerV3.cancelRedemption(
  vaultAddress, // Vault address
  queueIndex // Queue index of redemption to cancel
);
```

#### Process Redemption (Operator Only)

Process a redemption from the queue. Typically called by vault operators.

```typescript
await managerV3.processRedemption(
  vaultAddress, // Vault address
  queueIndex, // Queue index to process
  gasFeeShares // Gas fee in shares (can be 0)
);
```

### View Functions

#### Get Redemption Queue Length

```typescript
const queueLength = await managerV3.getRedemptionQueueLength(vaultAddress);
console.log(`Queue length: ${queueLength}`);
```

#### Get Redemption Queue Entry

```typescript
const entry = await managerV3.getRedemptionQueueEntry(vaultAddress, queueIndex);
console.log(`Owner: ${entry.owner}`);
console.log(`Locked Shares: ${entry.lockedShares}`);
console.log(`NAV at Request: ${entry.navAtRequest}`);
```

#### Get Standard Debt

Get total locked shares (standard debt) for a vault.

```typescript
const standardDebt = await managerV3.getStandardDebt(vaultAddress);
console.log(`Standard Debt: ${ethers.formatUnits(standardDebt, 18)} shares`);
```

#### Get NAV

Get current Net Asset Value (NAV) for a vault.

```typescript
const nav = await managerV3.getNAV(vaultAddress);
console.log(`NAV: ${ethers.formatUnits(nav, 18)}`);
```

#### Check Whitelisting

```typescript
const isWhitelisted = await managerV3.isWhitelisted(vaultAddress, assetAddress);
console.log(`Asset whitelisted: ${isWhitelisted}`);
```

#### Get Vault Asset

Get the base asset address for a vault.

```typescript
const assetAddress = await managerV3.getVaultAsset(vaultAddress);
console.log(`Vault Asset: ${assetAddress}`);
```

### Type Safety

The SDK provides TypeScript types for type-safe contract interactions:

```typescript
import type { ManagerV3 } from "yieldfi-sdk";
import { Contract } from "ethers";

const managerV3 = new Contract(
  contracts.manager,
  ManagerV3ABI,
  signer
) as unknown as ManagerV3;

// Full type safety and IntelliSense
await managerV3.deposit(/* ... */);
await managerV3.requestRedemption(/* ... */);
```

### Complete Example

#### Using Wagmi

```typescript
import { connectManagerV3, getContractAddresses, Chain } from "yieldfi-sdk";
import { ethers } from "ethers";
import { useAccount, useWalletClient } from "wagmi";
import ManagerV3ABI from "yieldfi-sdk/abis/v3/Manager.json";

function ManagerV3Example() {
  const { address } = useAccount();
  const { data: walletClient } = useWalletClient();

  const managerV3Flow = async () => {
    if (!walletClient || !address) {
      throw new Error("Wallet not connected");
    }

    const provider = new ethers.BrowserProvider(walletClient);
    const signer = await provider.getSigner();

    const contracts = getContractAddresses(Chain.ETHEREUM);
    const managerV3 = connectManagerV3(contracts.manager, ManagerV3ABI, signer);

    const vaultAddress = "0x5bE91d34FeFbB7554497a74e25dC6df96bFef5DB";
    const assetAddress = "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"; // USDC

    // Check if asset is whitelisted
    const whitelisted = await managerV3.isWhitelisted(vaultAddress, assetAddress);
    console.log(`Asset whitelisted: ${whitelisted}`);

    // Get vault info
    const vaultAsset = await managerV3.getVaultAsset(vaultAddress);
    const nav = await managerV3.getNAV(vaultAddress);
    console.log(`Vault Asset: ${vaultAsset}`);
    console.log(`NAV: ${ethers.formatUnits(nav, 18)}`);

    // Deposit
    const assetToken = new ethers.Contract(
      assetAddress,
      [
        "function approve(address spender, uint256 amount) returns (bool)",
        "function balanceOf(address account) view returns (uint256)",
      ],
      signer
    );

    const amount = ethers.parseUnits("100", 6);
    await assetToken.approve(managerV3.target, amount);

    const shares = await managerV3.deposit(
      vaultAddress,
      assetAddress,
      amount,
      address,
      0n,
      ethers.ZeroHash
    );
    console.log(`Received ${ethers.formatUnits(shares, 18)} shares`);

    // Request redemption
    await managerV3.requestRedemption(
      vaultAddress,
      shares / 2n,
      address,
      address
    );

    // Check queue
    const queueLength = await managerV3.getRedemptionQueueLength(vaultAddress);
    console.log(`Queue length: ${queueLength}`);
  };

  return <button onClick={managerV3Flow}>Run Manager V3 Flow</button>;
}
```

#### Using Browser Provider

```typescript
import { connectManagerV3, getContractAddresses, Chain } from "yieldfi-sdk";
import { ethers } from "ethers";
import ManagerV3ABI from "yieldfi-sdk/abis/v3/Manager.json";

async function managerV3Example() {
  if (!window.ethereum) {
    throw new Error("No wallet found");
  }

  const provider = new ethers.BrowserProvider(window.ethereum);
  const signer = await provider.getSigner();
  const userAddress = await signer.getAddress();

  const contracts = getContractAddresses(Chain.ETHEREUM);
  const managerV3 = connectManagerV3(contracts.manager, ManagerV3ABI, signer);

  const vaultAddress = "0x5bE91d34FeFbB7554497a74e25dC6df96bFef5DB";
  const assetAddress = "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48"; // USDC

  // Check if asset is whitelisted
  const whitelisted = await managerV3.isWhitelisted(vaultAddress, assetAddress);
  console.log(`Asset whitelisted: ${whitelisted}`);

  // Get vault info
  const vaultAsset = await managerV3.getVaultAsset(vaultAddress);
  const nav = await managerV3.getNAV(vaultAddress);
  console.log(`Vault Asset: ${vaultAsset}`);
  console.log(`NAV: ${ethers.formatUnits(nav, 18)}`);

  // Deposit
  const assetToken = new ethers.Contract(
    assetAddress,
    [
      "function approve(address spender, uint256 amount) returns (bool)",
      "function balanceOf(address account) view returns (uint256)",
    ],
    signer
  );

  const amount = ethers.parseUnits("100", 6);
  await assetToken.approve(managerV3.target, amount);

  const shares = await managerV3.deposit(
    vaultAddress,
    assetAddress,
    amount,
    userAddress,
    0n,
    ethers.ZeroHash
  );
  console.log(`Received ${ethers.formatUnits(shares, 18)} shares`);

  // Request redemption
  await managerV3.requestRedemption(
    vaultAddress,
    shares / 2n,
    userAddress,
    userAddress
  );

  // Check queue
  const queueLength = await managerV3.getRedemptionQueueLength(vaultAddress);
  console.log(`Queue length: ${queueLength}`);
}

managerV3Example();
```
