yo-protocol-react-sdk

star 1

ALWAYS use this skill when the user is working with React components or hooks that interact with Yo Protocol vaults, or imports from `@yo-protocol/react`. This skill covers the full React SDK: YieldProvider setup, query hooks (useVaultState, useVaultSnapshot, useUserPosition, useTokenBalance, useShareBalance, useAllowance, useMerklRewards, useLeaderboard, usePrices, etc.), action hooks (useDeposit, useRedeem, useApprove, useClaimMerklRewards), and migration from the old API (useVault→useVaultState, useUserBalance→useUserPosition, inputToken→token, account→owner, partnerId string→number, publicClient→publicClients). Trigger whenever the user mentions yo protocol React hooks, vault dashboard components, deposit/redeem UI flows, YieldProvider, useYoClient, @yo-protocol/react, yo-kit, or asks to build React components for yoETH, yoUSD, yoBTC, yoEUR, yoGOLD, or yoUSDT vaults. Also trigger when the user has broken imports or API changes after upgrading @yo-protocol/react. Do NOT use for CLI shell commands (use yo-p

yoprotocol By yoprotocol schedule Updated 3/4/2026

name: yo-protocol-react-sdk description: >- ALWAYS use this skill when the user is working with React components or hooks that interact with Yo Protocol vaults, or imports from @yo-protocol/react. This skill covers the full React SDK: YieldProvider setup, query hooks (useVaultState, useVaultSnapshot, useUserPosition, useTokenBalance, useShareBalance, useAllowance, useMerklRewards, useLeaderboard, usePrices, etc.), action hooks (useDeposit, useRedeem, useApprove, useClaimMerklRewards), and migration from the old API (useVault→useVaultState, useUserBalance→useUserPosition, inputToken→token, account→owner, partnerId string→number, publicClient→publicClients). Trigger whenever the user mentions yo protocol React hooks, vault dashboard components, deposit/redeem UI flows, YieldProvider, useYoClient, @yo-protocol/react, yo-kit, or asks to build React components for yoETH, yoUSD, yoBTC, yoEUR, yoGOLD, or yoUSDT vaults. Also trigger when the user has broken imports or API changes after upgrading @yo-protocol/react. Do NOT use for CLI shell commands (use yo-protocol-cli) or server-side Node.js scripts without React (use yo-protocol-sdk). author: yoprotocol homepage: https://github.com/yoprotocol/yo-protocol-skills source: https://github.com/yoprotocol/yo-protocol-skills/tree/main/skills/yo-protocol-react

Official Yo Protocol skill. Canonical repository: https://github.com/yoprotocol/yo-protocol-skills

@yo-protocol/react SDK

Architecture

Three layers:

  1. ProviderYieldProvider wraps app, provides config. useYoClient() creates YoClient from @yo-protocol/core
  2. Query hooks (32) — Read data via useQuery + client.getX(). Return { data, isLoading, isError, error, refetch }
  3. Action hooks (4) — Mutate via client.prepareX() + wagmi sendTransactionAsync(). Return { mutate, step, hash, reset }

Core only prepares transactions (PreparedTransaction { to, data, value }). React sends them via wagmi. No walletClient needed.

Quick Start

// Provider setup
<WagmiProvider config={wagmiConfig}>
  <QueryClientProvider client={queryClient}>
    <YieldProvider partnerId={9999} defaultSlippageBps={50}>
      <App />
    </YieldProvider>
  </QueryClientProvider>
</WagmiProvider>

// Read vault state
const { vaultState } = useVaultState("yoUSD")

// Read user position
const { position } = useUserPosition("yoUSD") // auto-uses connected wallet

// Deposit with auto-approval and chain switching
const { deposit, step } = useDeposit({ vault: "yoUSD", slippageBps: 50 })
await deposit({ token: usdcAddress, amount: 1_000_000n, chainId: 8453 })

// Redeem with auto-approval
const { redeem, instant, assetsOrRequestId } = useRedeem({ vault: "yoUSD" })
await redeem(500_000n)

Migration

When encountering code using the old API, consult references/migration.md for the complete migration guide.

Quick migration checklist — search and replace:

Find Replace with
useVault( useVaultState(
useUserBalance( useUserPosition(
useWeeklyRewards( useLeaderboard("weekly",
useAllTimeRewards( useLeaderboard("allTime",
{ vault: vaultState } { vaultState }
{ position } = useUserBalance { position } = useUserPosition
inputToken: (in deposit) token:
account: (in deposit/redeem params) owner:
fromChainId: / toChainId: chainId:
partnerId: " partnerId: (number, not string)
publicClient: (in createYoClient) publicClients: { [chainId]:
useWalletClient import Remove — no longer needed
walletClient param Remove — core only prepares txs

Import updates

// Old imports to find and remove
import { useVault } from '*/useVault'
import { useUserBalance } from '*/useUserBalance'
import { useWeeklyRewards } from '*/useWeeklyRewards'
import { useAllTimeRewards } from '*/useAllTimeRewards'

// New imports
import { useVaultState } from '@yo-protocol/react'
import { useUserPosition } from '@yo-protocol/react'
import { useLeaderboard } from '@yo-protocol/react'

Hooks Reference

For complete API signatures and query keys, see references/hooks-api.md.

Hook → Client Method Map

Vault on-chain: useVaultStategetVaultState(), usePreviewDepositpreviewDeposit(), usePreviewRedeempreviewRedeem()

Vault API: useVaultsgetVaults(), useVaultStatsgetVaultStats(), useVaultSnapshotgetVaultSnapshot(), useVaultSnapshotsgetVaultSnapshots(), useVaultHistorygetVaultYieldHistory() + getVaultTvlHistory(), useVaultTransactionHistorygetVaultHistory() | getVaultHistoryAllNetworks(), useGlobalVaultHistorygetGlobalVaultHistory(), useVaultPerformancegetVaultPerformance(), useVaultPercentilegetVaultPercentile(), usePerformanceBenchmarkgetPerformanceBenchmark(), useVaultAllocationsgetVaultAllocationsTimeSeries(), useVaultPendingRedeemsgetVaultPendingRedeems(), useSharePriceHistorygetSharePriceHistory(), useTotalTvlgetTotalTvlTimeseries(), usePricesgetPrices()

User on-chain: useUserPositiongetUserPosition(), useUserPositionsgetUserPositionsAllChains(), useTokenBalancegetTokenBalance(), useShareBalancegetShareBalance(), useAllowancegetAllowance()

User API: useUserHistorygetUserHistory(), useUserPerformancegetUserPerformance(), useUserSnapshotsgetUserSnapshots(), useUserBalancesgetUserBalances(), usePendingRedemptionsgetPendingRedemptions(), useUserRewardsgetUserRewardsByAsset()

Leaderboard: useLeaderboard("weekly"|"allTime", tokenAddr)getWeeklyRewards() | getAllTimeRewards()

Merkl: useMerklCampaignsgetMerklCampaigns(), useMerklRewardsgetClaimableRewards()

Actions: useDepositprepareDepositWithApproval(), useRedeemprepareRedeemWithApproval(), useApproveprepareApprove(), useClaimMerklRewardsprepareClaimMerklRewards()

Creating New Query Hooks

Follow this pattern for any new query hook:

import { useQuery } from '@tanstack/react-query'
import type { VaultId } from '@yo-protocol/core'
import type { Address } from 'viem'
import { useYoClient } from '../context'
import { resolveVaultAddress } from '../utils/vault'

export function useNewHook(vault: Address | VaultId, options?: { enabled?: boolean }) {
  const { enabled = true } = options ?? {}
  const client = useYoClient()
  const vaultAddress = resolveVaultAddress(vault)

  const { data, isLoading, isError, error, refetch } = useQuery({
    queryKey: ['yo-new-hook', vaultAddress, client?.chainId],
    queryFn: () => {
      if (!client) throw new Error('Client not available')
      return client.newMethod(vaultAddress)
    },
    enabled: enabled && !!client,
    staleTime: 30_000,
  })

  return { result: data, isLoading, isError, error: error ?? null, refetch }
}

Rules:

  • Query key prefix: 'yo-' for protocol hooks, 'merkl-' for Merkl hooks
  • Always include client?.chainId as last key segment
  • Guard with enabled && !!client (add !!userAddress for user-specific hooks)
  • Return error ?? null (not raw error)
  • User-scoped hooks should default to connected wallet via useAccount()

Creating New Action Hooks

Follow this pattern — prepare+send with step tracking:

import { useCallback, useState } from 'react'
import { useSendTransaction, useWaitForTransactionReceipt, useAccount } from 'wagmi'
import { useQueryClient } from '@tanstack/react-query'
import { useYieldConfig, useYoClient } from '../context'

export function useNewAction(options: { onSubmitted?, onConfirmed?, onError? }) {
  const client = useYoClient()
  const { address: account } = useAccount()
  const { sendTransactionAsync } = useSendTransaction()
  const queryClient = useQueryClient()
  const [hash, setHash] = useState<Hash>()
  const [step, setStep] = useState<string>('idle')
  const [error, setError] = useState<Error | null>(null)
  const { isSuccess } = useWaitForTransactionReceipt({ hash, query: { enabled: !!hash } })

  // Invalidate on confirmation
  useEffect(() => {
    if (isSuccess && hash) {
      queryClient.invalidateQueries({ queryKey: ['yo-relevant-key'] })
      options.onConfirmed?.(hash)
    }
  }, [isSuccess, hash])

  const execute = useCallback(async (params) => {
    const txs = await client.prepareX(params)     // PreparedTransaction[]
    for (const tx of txs) {
      const h = await sendTransactionAsync({ to: tx.to, data: tx.data, value: tx.value })
      if (tx !== txs[txs.length - 1]) await client.waitForTransaction(h)
    }
  }, [client, account, sendTransactionAsync])

  return { execute, step, isLoading: step !== 'idle' && step !== 'success' && step !== 'error', hash, error, reset }
}

Key Types

// Client config
interface YoClientConfig {
  chainId: SupportedChainId
  partnerId?: number
  publicClients?: Partial<Record<SupportedChainId, PublicClient>>
}

// Prepared transaction (core output, wagmi input)
interface PreparedTransaction { to: Address; data: Hex; value: bigint }

// Deposit params
interface PrepareDepositWithApprovalParams {
  vault: Address; token: Address; owner: Address
  recipient?: Address; amount: bigint
  slippageBps?: number; partnerId?: number; minShares?: bigint; chainId?: number
}

// Redeem params
interface PrepareRedeemWithApprovalParams {
  vault: Address; shares: bigint; owner: Address
  recipient?: Address; slippageBps?: number; partnerId?: number; minAssetsOut?: bigint
}

// Vault state
interface VaultState {
  address: Address; name: string; symbol: string; decimals: number
  totalAssets: bigint; totalSupply: bigint; asset: Address; assetDecimals: number; exchangeRate: bigint
}

// User position
interface UserVaultPosition { shares: bigint; assets: bigint }
Install via CLI
npx skills add https://github.com/yoprotocol/yo-protocol-skills --skill yo-protocol-react-sdk
Repository Details
star Stars 1
call_split Forks 0
navigation Branch main
article Path SKILL.md
More from Creator