> ## Documentation Index
> Fetch the complete documentation index at: https://docs.zyf.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# depositFunds (compatibility)

`depositFunds` remains for compatibility with existing integrations. New
integrations should use [`sendDeposit`](/docs/sdk/api/send-deposit), then
explicitly await [`waitForDepositCredit`](/docs/sdk/api/wait-for-deposit-credit)
when their UI needs investable funds.

This convenience method transfers tokens from the user's EOA to their Smart
Wallet, then waits through a short normal credit-completion window before
returning.

On the **first deposit**, this is also how a user is onboarded onto Zyfai: a **pre-deployed** Safe with an already-signed session key is assigned to them, live on **Base, Arbitrum, and Ethereum Mainnet** at once. No separate `deploySafe` or `createSessionKey` call is needed (or supported).

**Supported assets:** USDC, WETH, EURC, USDT, PYUSD, and NVDAc. Chains, decimals, least-unit amounts, and minimums are on [Supported Assets](/docs/sdk/supported-assets).

<Warning title="First deposit assigns a pre-deployed account">
  The first time a user deposits into Zyfai, the backend associates their EOA with a **pre-deployed Smart Account** that already has a **signed session key**.

  That Smart Account becomes available **immediately on Base (8453), Arbitrum (42161), and Ethereum Mainnet (1)**, not only on the `chainId` you pass to `depositFunds`. The user is the owner of that Safe.

  This does **not** change how their EOA works: the EOA remains a normal wallet. Depositing only links a Zyfai Smart Wallet (with session) to that EOA as owner.
</Warning>

<Warning title="Important for WETH deposits">
  You must deposit **WETH** (Wrapped ETH), not native ETH. If the user has ETH, they must wrap it to WETH first before depositing.
</Warning>

<Info title="Minimum portfolio balance">
  Minimums apply to the **total Safe balance after the deposit** (current Safe balance + deposit amount). Top-ups smaller than the minimum are allowed if the Safe already holds enough of the asset to meet it.

  Stablecoins are a fixed token amount (10,000 on Ethereum, 10 on Base and Arbitrum). WETH and NVDAc are a dollar minimum ($10,000 of WETH on Ethereum, $10 of WETH or NVDAc on L2) converted from the live price at deposit time. Full table: [Supported Assets](/docs/sdk/supported-assets).
</Info>

## First Deposit Disclosure

Partners must show this notice **directly above** the first deposit confirmation button:

> By depositing, you authorize Zyfai automation to monitor risk and rebalance your funds within your selected strategy to seek better yield.

Include a link to the [Zyfai Terms and Conditions](/docs/product/other/terms-and-conditions).

**Recommended button label:** `Deposit & Activate`

This disclosure is only required when the user makes their **first deposit** and activates automation. Later deposits do not need it. The same UI requirement applies if you transfer tokens yourself and then call [`logDeposit`](/docs/sdk/api/log-deposit).

## Compatibility signature

```typescript theme={null}
depositFunds(
  userAddress: string,
  chainId: SupportedChainId,
  amount: string,
  asset: string,
  strategy?: Strategy
): Promise<DepositResponse>
```

## Parameters

| Parameter | Type | Required | Description |
| - | - | - | - |
| `userAddress` | `string` | ✅ | User's EOA address (owner of the Safe) |
| `chainId` | `SupportedChainId` | ✅ | Chain to deposit on |
| `amount` | `string` | ✅ | Amount in least units. See [Supported Assets](/docs/sdk/supported-assets) |
| `asset` | `string` | ✅ | `"USDC"`, `"WETH"`, `"EURC"`, `"USDT"`, `"PYUSD"`, or `"NVDAc"`. See [Supported Assets](/docs/sdk/supported-assets). Depositing on a chain where the asset does not exist throws before any transfer |
| `strategy` | `Strategy` | ❌ | First-deposit strategy: `"conservative"` (default), `"aggressive"` or `"yieldmaxxing"`. Ignored on later deposits (see below) |

## What happens under the hood

1. Resolves the Safe address for the EOA (backend-assigned for pre-deployed wallets, not derived from the EOA).
2. Ensures the Safe is available on-chain.
3. **First-deposit protocol patching** (see below), then transfers the token from the EOA to the Safe and logs the deposit.
4. Waits through the normal credit-completion window. If still in progress, returns `handover_pending` so the caller can continue tracking it.

### First-deposit protocol patching

Runs only when the USDC profile has **no `chains` configured yet** (later deposits and `pauseAgent` do not re-trigger it):

* Patches every managed asset on the chains it exists on: USDC and WETH on `[1, 8453, 42161]`, EURC on `[1, 8453]`, USDT and PYUSD on `[1]`, NVDAc on `[8453]`. See [Supported Assets](/docs/sdk/supported-assets).
* Fetches protocols, filters by strategy / chain / asset + pool availability, and persists via `updateUserProfile` → `assetTypeSettings.[usdc|eth|eurc|usdt|pyusd|nvdac]`.
* Failures are non-fatal (`console.warn`); the deposit still proceeds.

Protocols / chains are set on this first `depositFunds` call, not by any separate deploy or session-key step.

<Warning title="strategy only applies to the first deposit">
  On every later deposit the argument is **ignored, and no error is raised**. Re-running the patch would overwrite a protocol selection the user may have
  customised. Passing `"yieldmaxxing"` to an account that has already deposited
  leaves it on its current strategy.

  To change the strategy of an existing account, call
  [updateUserProfile](/docs/sdk/api/update-user-details) for each asset
  concerned:

  ```typescript theme={null}
  await sdk.updateUserProfile({ asset: "USDC", strategy: "yieldmaxxing" });
  ```
</Warning>

## Returns

Deposit response with transaction hash, confirmation, and lifecycle metadata. `registration` is `credited` when funds are investable, or `handover_pending` when the normal completion window elapsed while the backend continues handover.

For either a pending high-level deposit or an intentionally split [`logDeposit`](/docs/sdk/api/log-deposit) flow, use [`waitForDepositCredit`](/docs/sdk/api/wait-for-deposit-credit) with an explicit longer `timeoutMs`, or poll [`getDepositStatus`](/docs/sdk/api/get-deposit-status).

## Return Type

```typescript theme={null}
interface DepositLifecycleResponse {
  id: string;
  status: "handover_pending" | "credited" | "recovered_to_eoa";
  balanceCredited: boolean;
  statusUrl: string;
}

interface DepositResponse {
  success: boolean;
  txHash: string;
  smartWallet: string;
  amount: string;
  registration: DepositLifecycleResponse;
}
```

## Example

### Deposit USDC

```typescript theme={null}
// Deposit 100 USDC (6 decimals) to Safe on Base
// Optional strategy applies on first deposit only (default: "conservative")
const result = await sdk.depositFunds(
  "0xUser...",
  8453,
  "100000000", // 100 USDC = 100 * 10^6
  "USDC",
  "conservative"
);
console.log("Deposit confirmed:", result.txHash);
console.log("Smart Wallet:", result.smartWallet);

console.log("Deposit status:", result.registration.status);
```

### Deposit WETH

```typescript theme={null}
// Deposit 0.5 WETH (18 decimals) to Safe on Base
// IMPORTANT: User must have WETH, not ETH. Wrap ETH to WETH first if needed.
const result = await sdk.depositFunds(
  "0xUser...",
  8453,
  "500000000000000000", // 0.5 WETH = 0.5 * 10^18
  "WETH"
);
console.log("WETH deposit confirmed:", result.txHash);
```

### Deposit EURC

```typescript theme={null}
// Deposit 100 EURC (6 decimals) on Base (also supported on Mainnet)
const result = await sdk.depositFunds(
  "0xUser...",
  8453,
  "100000000",
  "EURC"
);
console.log("EURC deposit confirmed:", result.txHash);
```

### Deposit NVDAc

NVDAc is Base-only and is held exclusively by protocols with delayed
withdrawals, so it requires the
[`yieldmaxxing`](/docs/sdk/technical-reference#strategies) strategy. On a
`conservative` or `aggressive` profile the agent resolves zero protocols for
NVDAc and never deploys the funds.

```typescript theme={null}
// Existing account: one call sets the strategy and selects the protocols.
// Chains default to Base, the only one NVDAc exists on.
await sdk.setAssetStrategy({ asset: "NVDAc", strategy: "yieldmaxxing" });

// Deposit 1 NVDAc (8 decimals) on Base
const result = await sdk.depositFunds(
  "0xUser...",
  8453,
  "100000000",
  "NVDAc"
);
console.log("NVDAc deposit confirmed:", result.txHash);
```

<Warning title="Use setAssetStrategy, not updateUserProfile">
  [updateUserProfile](/docs/sdk/api/update-user-details) stores the strategy but
  does not compute a protocol list, so on its own it leaves NVDAc with an empty
  whitelist and the deposit sits idle in the Safe with no error anywhere.
  [setAssetStrategy](/docs/sdk/api/set-asset-strategy) does both.

  On a brand-new account this is handled for you: pass `"yieldmaxxing"` as the
  `strategy` argument of the very first `depositFunds` call instead.
</Warning>

<Info title="Deposits pause when the market is closed">
  Tokenized equities stop accepting deposits outside market hours, typically over
  the weekend. Funds stay idle in the Safe and are deployed at the next open;
  other assets are unaffected. [getPortfolio](/docs/sdk/api/get-portfolio) returns
  ready-to-display copy in `pauseMessageByToken["NVDAc"]` while that lasts.
</Info>

<Info title="Transferring outside depositFunds">
  `depositFunds` logs the deposit for you. If you send the ERC-20 transfer yourself, call [`logDeposit`](/docs/sdk/api/log-deposit) after it confirms. Otherwise, the backend will not rotate a reserved pool wallet or start yield tracking.
</Info>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.