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

# 如何获取所有 Solana 钱包转账

> 跟踪任何 Solana 钱包的所有进出代币转账。查看发送方/接收方信息、金额和时间戳以获取完整的转账历史记录。

<Note>
  钱包API处于测试阶段。端点和响应格式可能会更改。
</Note>

## 概览

Token Transfers端点检索Solana钱包的所有代币转账活动，包括详细的发送者和接收者信息。与完整的[交易历史](/zh/wallet-api/history)不同，此端点专注于转账，非常适合支付跟踪和转账监控。

此端点每次请求最多返回100次转账（默认50次）。使用`cursor`参数和`pagination.nextCursor`来获取下一页，当有更多结果可用时，请阅读`pagination.hasMore`。

## 何时使用

当您需要以下操作时，请使用 Token Transfers API：

* **跟踪付款**：监控支付处理器的来款。
* **构建转账提要**：显示简单的“发送/接收”活动提要。
* **监控特定代币**：跟踪特定代币的转账（例如，USDC支付）。
* **识别交易对手**：查看谁发送或接收了代币。
* **生成收据**：创建包含发送者/接收者详细信息的付款收据。
* **检测可疑活动**：监控异常转账模式。

## 快速开始

### 基本转账查询

获取最近的进出转账：

<Tabs>
  <Tab title="JavaScript">
    ```javascript theme={"system"}
    const getWalletTransfers = async (address) => {
      const url = `https://api.helius.xyz/v1/wallet/${address}/transfers?api-key=YOUR_API_KEY`;

      const response = await fetch(url);
      if (!response.ok) {
        throw new Error(`HTTP error! status: ${response.status}`);
      }

      const data = await response.json();

      console.log(`Found ${data.data.length} transfers`);

      // Display recent transfers
      data.data.forEach(transfer => {
        const date = new Date(transfer.timestamp * 1000).toLocaleString();
        const direction = transfer.direction === 'in' ? 'Received' : 'Sent';
        const counterparty = transfer.counterparty.slice(0, 8) + '...';

        console.log(`\n${direction} - ${date}`);
        console.log(`Amount: ${transfer.amount} ${transfer.symbol || transfer.mint.slice(0, 8) + '...'}`);
        console.log(`${transfer.direction === 'in' ? 'From' : 'To'}: ${counterparty}`);
        console.log(`Signature: ${transfer.signature.slice(0, 20)}...`);
      });

      return data;
    };

    getWalletTransfers("86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY");
    ```
  </Tab>

  <Tab title="Python">
    ```python theme={"system"}
    import requests
    from datetime import datetime

    def get_wallet_transfers(address: str):
        url = f"https://api.helius.xyz/v1/wallet/{address}/transfers"
        headers = {"X-Api-Key": "YOUR_API_KEY"}

        response = requests.get(url, headers=headers)
        response.raise_for_status()

        data = response.json()

        print(f"Found {len(data['data'])} transfers")

        # Display recent transfers
        for transfer in data['data']:
            date = datetime.fromtimestamp(transfer['timestamp']).strftime('%Y-%m-%d %H:%M:%S')
            direction = 'Received' if transfer['direction'] == 'in' else 'Sent'
            counterparty = transfer['counterparty'][:8] + '...'
            symbol = transfer.get('symbol') or transfer['mint'][:8] + '...'

            print(f"\n{direction} - {date}")
            print(f"Amount: {transfer['amount']} {symbol}")
            print(f"{'From' if transfer['direction'] == 'in' else 'To'}: {counterparty}")
            print(f"Signature: {transfer['signature'][:20]}...")

        return data

    get_wallet_transfers("86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY")
    ```
  </Tab>

  <Tab title="cURL">
    ```bash theme={"system"}
    curl "https://api.helius.xyz/v1/wallet/86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY/transfers?api-key=YOUR_API_KEY"
    ```
  </Tab>
</Tabs>

### 按方向筛选

在客户端筛选结果以仅获取传入或传出的转账：

<Tabs>
  <Tab title="仅入账">
    ```javascript theme={"system"}
    const getIncomingTransfers = async (address) => {
      const data = await getWalletTransfers(address);

      const incoming = data.data.filter(t => t.direction === 'in');

      console.log(`Received ${incoming.length} incoming transfers`);

      incoming.forEach(transfer => {
        console.log(`Received ${transfer.amount} ${transfer.symbol} from ${transfer.counterparty.slice(0, 8)}...`);
      });

      return incoming;
    };
    ```
  </Tab>

  <Tab title="仅出账">
    ```javascript theme={"system"}
    const getOutgoingTransfers = async (address) => {
      const data = await getWalletTransfers(address);

      const outgoing = data.data.filter(t => t.direction === 'out');

      console.log(`Made ${outgoing.length} outgoing transfers`);

      outgoing.forEach(transfer => {
        console.log(`Sent ${transfer.amount} ${transfer.symbol} to ${transfer.counterparty.slice(0, 8)}...`);
      });

      return outgoing;
    };
    ```
  </Tab>
</Tabs>

## 查询参数

| 参数       | 类型      | 默认值 | 描述               |
| -------- | ------- | --- | ---------------- |
| `limit`  | integer | 50  | 返回的最大转账数 (1-100) |
| `cursor` | string  | -   | 上一次响应的分页游标       |

## 响应格式

```json theme={"system"}
{
  "data": [
    {
      "signature": "5wHu1qwD7Jsj3xqWjdSEJmYr3Q5f5RjXqjqQJ7jqEj7jqEj7jqEj7jqEj7jqEj7jqE",
      "timestamp": 1704067200,
      "direction": "in",
      "counterparty": "HXsKP7wrBWaQ8T2Vtjry3Nj3oUgwYcqq9vrHDM12G664",
      "mint": "So11111111111111111111111111111111111111111",
      "symbol": "SOL",
      "amount": 1.5,
      "amountRaw": "1500000000",
      "decimals": 9
    },
    {
      "signature": "4aHu2qwD8Jtj4xqWjdSEJmYr3Q5f5RjXqjqQJ7jqEj7jqEj7jqEj7jqEj7jqEj7jqE",
      "timestamp": 1704067100,
      "direction": "out",
      "counterparty": "2ojv9BAiHUrvsm9gxDe7fJSzbNZSJcxZvf8dqmWGHG8S",
      "mint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
      "symbol": "USDC",
      "amount": 100.0,
      "amountRaw": "100000000",
      "decimals": 6
    }
  ],
  "pagination": {
    "hasMore": true,
    "nextCursor": "5wHu1qwD7Jsj3xqWjdSEJmYr3Q5f5RjXqjqQJ7jqEj7jqEj7jqEj7jqEj7jqEj7jqE"
  }
}
```

### 字段说明

* **`direction`**：相对于您查询的钱包。`in`是代币**接收**（传入支付）；`out`是代币**发送**（传出支付）。
* **`counterparty`**：对于`in`转账，为发送者；对于`out`转账，为接收者。
* **`amount`**：人类可读的转账金额，已除以`decimals`。用于显示（例如，`1.5` SOL，`100.0` USDC）。
* **`amountRaw`**：相同金额的原始整数字符串，在小数调整之前（例如，`"1500000000"`代表1.5 SOL）。序列化为字符串以避免浮点精度丢失。用于链上指令或精确计算：`amount = parseInt(amountRaw) / 10**decimals`。
* **`mint`**：代币铸造地址（`So11111111111111111111111111111111111111111`用于本地SOL）。
* **`symbol`**：代币符号。并非所有代币都有，如果`symbol`为`null`，请回退至铸造地址。

## 使用案例

### 跟踪商户付款历史

监控USDC入款：

```javascript theme={"system"}
const trackMerchantPayments = async (merchantWallet) => {
  const data = await getWalletTransfers(merchantWallet);

  // Filter for incoming USDC transfers
  const usdcPayments = data.data.filter(t =>
    t.direction === 'in' &&
    t.mint === 'EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v' // USDC
  );

  console.log(`Received ${usdcPayments.length} USDC payments`);

  const totalReceived = usdcPayments.reduce((sum, t) => sum + t.amount, 0);
  console.log(`Total USDC Received: $${totalReceived.toFixed(2)}`);

  // Display each payment
  usdcPayments.forEach(payment => {
    const date = new Date(payment.timestamp * 1000).toLocaleString();
    console.log(`${date}: $${payment.amount} from ${payment.counterparty}`);
  });

  return {
    count: usdcPayments.length,
    total: totalReceived,
    payments: usdcPayments
  };
};
```

### 生成付款收据

为特定转账创建详细收据：

```javascript theme={"system"}
const generatePaymentReceipt = async (address, signature) => {
  const data = await getWalletTransfers(address);

  const transfer = data.data.find(t => t.signature === signature);

  if (!transfer) {
    console.log('Transfer not found');
    return null;
  }

  const receipt = {
    receiptId: transfer.signature.slice(0, 16),
    date: new Date(transfer.timestamp * 1000).toISOString(),
    type: transfer.direction === 'in' ? 'Payment Received' : 'Payment Sent',
    amount: `${transfer.amount} ${transfer.symbol || 'tokens'}`,
    from: transfer.direction === 'in' ? transfer.counterparty : address,
    to: transfer.direction === 'out' ? transfer.counterparty : address,
    transactionUrl: `https://orbmarkets.io/tx/${transfer.signature}`
  };

  console.log('--- PAYMENT RECEIPT ---');
  Object.entries(receipt).forEach(([key, value]) => {
    console.log(`${key}: ${value}`);
  });

  return receipt;
};
```

### 监控可疑的转账模式

检测异常转账活动：

```javascript theme={"system"}
const detectSuspiciousActivity = async (address) => {
  const data = await getWalletTransfers(address);

  const recentTransfers = data.data.filter(t => {
    const hourAgo = Date.now() / 1000 - 3600;
    return t.timestamp > hourAgo;
  });

  // Check for high frequency
  if (recentTransfers.length > 100) {
    console.log(`Warning: ${recentTransfers.length} transfers in the last hour`);
  }

  // Check for large amounts
  const largeTransfers = recentTransfers.filter(t => {
    // Assuming USDC/stablecoins
    return t.amount > 10000 && t.decimals === 6;
  });

  if (largeTransfers.length > 0) {
    console.log(`Warning: ${largeTransfers.length} large transfers (>$10k) in the last hour`);
  }

  // Check for transfers to same address
  const counterparties = recentTransfers.map(t => t.counterparty);
  const duplicates = counterparties.filter((item, index) => counterparties.indexOf(item) !== index);

  if (duplicates.length > 5) {
    console.log(`Warning: Multiple transfers to the same address`);
  }

  return {
    recentCount: recentTransfers.length,
    largeTransfers: largeTransfers.length,
    suspiciousPatterns: duplicates.length > 5
  };
};
```

### 构建转账活动提要

创建用户友好的活动提要：

```javascript theme={"system"}
const buildTransferFeed = async (address) => {
  const data = await getWalletTransfers(address);

  const feed = data.data.map(transfer => {
    const date = new Date(transfer.timestamp * 1000);
    const timeAgo = getTimeAgo(date);

    return {
      id: transfer.signature,
      direction: transfer.direction,
      title: transfer.direction === 'in' ? 'Received' : 'Sent',
      subtitle: `${transfer.amount} ${transfer.symbol || 'tokens'}`,
      description: transfer.direction === 'in'
        ? `from ${transfer.counterparty.slice(0, 8)}...`
        : `to ${transfer.counterparty.slice(0, 8)}...`,
      timeAgo,
      explorerUrl: `https://orbmarkets.io/tx/${transfer.signature}`
    };
  });

  return feed;
};

function getTimeAgo(date) {
  const seconds = Math.floor((new Date() - date) / 1000);

  if (seconds < 60) return 'Just now';
  if (seconds < 3600) return `${Math.floor(seconds / 60)}m ago`;
  if (seconds < 86400) return `${Math.floor(seconds / 3600)}h ago`;
  return `${Math.floor(seconds / 86400)}d ago`;
}
```

### 对账付款

将转账与预期付款匹配：

```javascript theme={"system"}
const reconcilePayments = async (address, expectedPayments) => {
  const data = await getWalletTransfers(address);

  const recentTransfers = data.data.filter(t =>
    t.direction === 'in' &&
    t.mint === 'EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v' // USDC
  );

  const reconciliation = expectedPayments.map(expected => {
    const match = recentTransfers.find(t =>
      Math.abs(t.amount - expected.amount) < 0.01 &&
      t.counterparty === expected.from
    );

    return {
      orderId: expected.orderId,
      expectedAmount: expected.amount,
      status: match ? 'Received' : 'Pending',
      receivedAmount: match?.amount,
      signature: match?.signature,
      timestamp: match?.timestamp
    };
  });

  console.log('Payment Reconciliation:');
  reconciliation.forEach(r => {
    console.log(`Order ${r.orderId}: ${r.status}`);
  });

  return reconciliation;
};

// Example usage
const expected = [
  { orderId: 'ORDER-001', amount: 100.00, from: 'ABC...' },
  { orderId: 'ORDER-002', amount: 250.50, from: 'XYZ...' }
];

reconcilePayments("86xCnPeV69n6t3DnyGvkKobf9FdN2H9oiVDdaMpo2MMY", expected);
```

## 分页

对于拥有大量转账的钱包，使用 `cursor` 参数和 `pagination.hasMore` 翻页浏览结果：

```javascript theme={"system"}
const getAllTransfers = async (address) => {
  let allTransfers = [];
  let cursor = null;

  do {
    const url = cursor
      ? `https://api.helius.xyz/v1/wallet/${address}/transfers?api-key=YOUR_API_KEY&cursor=${cursor}`
      : `https://api.helius.xyz/v1/wallet/${address}/transfers?api-key=YOUR_API_KEY`;

    const response = await fetch(url);
    const data = await response.json();

    allTransfers = allTransfers.concat(data.data);
    cursor = data.pagination.hasMore ? data.pagination.nextCursor : null;

    console.log(`Fetched ${allTransfers.length} transfers so far...`);

  } while (cursor);

  console.log(`\nTotal transfers: ${allTransfers.length}`);
  return allTransfers;
};
```

## 最佳实践

* **客户端过滤特定代币。** API返回所有代币转账。通过 `mint` 地址过滤以跟踪特定代币，如USDC或SOL。
* **结合身份API。** 使用 [Identity](/zh/wallet-api/identity) 端点显示已知交易对手（交易所、协议等）的人可读名称。
* **缓存最近的转账。** 转账数据不变。缓存结果，只获取自上次查询以来的新转账。
* **分页以获取完整历史记录。** 实现分页以高效处理拥有数千笔转账的钱包。
* **处理缺失的符号。** 并非所有代币都有 `symbol` 字段。当 `symbol` 是 `null` 时，退回铸币地址。

## 转账与交易历史

| 功能       | 转账        | 交易历史      |
| -------- | --------- | --------- |
| **重点**   | 仅代币转账     | 所有交易类型    |
| **数据**   | 发件人/收件人信息 | 所有代币的余额变化 |
| **使用案例** | 付款跟踪      | 完整活动日志    |
| **性能**   | 更快，更简单    | 更全面       |

当您只关心付款时，使用 [Transfers](/zh/wallet-api/transfers)。当您需要完整的余额变更数据时，使用 [Transaction History](/zh/wallet-api/history)。

## 常见错误

| 错误代码 | 描述          | 解决方案                    |
| ---- | ----------- | ----------------------- |
| 400  | 无效的钱包地址格式   | 确认地址是有效的base58 Solana地址 |
| 401  | 缺少或无效的API密钥 | 检查你的API密钥是否包含在请求中       |
| 429  | 超出速率限制      | 减少请求频率或升级你的计划           |

## 下一步

<CardGroup cols={3}>
  <Card title="钱包历史" icon="clock-rotate-left" href="/zh/wallet-api/history">
    完整的交易历史，包含每笔交易的余额变化。
  </Card>

  <Card title="钱包API概述" icon="wallet" href="/zh/wallet-api/overview">
    所有钱包API端点和共享约定。
  </Card>

  <Card title="API参考" icon="code" href="/zh/api-reference/wallet-api/transfers">
    代币转移的请求和响应模式。
  </Card>
</CardGroup>
