> ## 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.

# Cách sử dụng getVoteAccounts

> Tìm hiểu các trường hợp sử dụng getVoteAccounts, ví dụ mã, tham số yêu cầu, cấu trúc phản hồi và mẹo.

Phương thức RPC [`getVoteAccounts`](https://www.helius.dev/docs/api-reference/rpc/http/getvoteaccounts) trả về thông tin về tất cả tài khoản bỏ phiếu (trình xác thực) trong bank hiện tại. Phương thức này phân biệt giữa các trình xác thực `current` (đang hoạt động) và `delinquent`, đồng thời cung cấp thông tin chi tiết về số cổ phần, hoạt động bỏ phiếu và danh tính của chúng.

## Các trường hợp sử dụng phổ biến

* **Giám sát trình xác thực:** Theo dõi trạng thái, số cổ phần và hiệu suất của các trình xác thực trên mạng.
* **Bảng điều khiển staking:** Hiển thị thông tin về các trình xác thực khả dụng cho người dùng muốn ủy quyền SOL của họ.
* **Phân tích tình trạng mạng:** Đánh giá tình trạng tổng thể và mức độ phi tập trung của mạng bằng cách xem xét sự phân bổ cổ phần và hoạt động của trình xác thực.
* **Xác định trình xác thực không hoạt động đúng hạn:** Tìm các trình xác thực không tích cực tham gia vào quá trình đồng thuận.

## Tham số yêu cầu

Phương thức này chấp nhận một đối tượng cấu hình tùy chọn với các trường sau:

1. **`commitment`** (chuỗi, tùy chọn): Chỉ định [mức cam kết](https://www.helius.dev/blog/solana-commitment-levels) cho truy vấn (ví dụ: `"finalized"`, `"confirmed"`, `"processed"`). Nếu bỏ qua, mức cam kết mặc định của nút sẽ được sử dụng.
2. **`votePubkey`** (chuỗi, tùy chọn): Nếu được cung cấp, kết quả sẽ được lọc để chỉ bao gồm địa chỉ tài khoản bỏ phiếu của trình xác thực đã chỉ định (được mã hóa base-58).
3. **`keepUnstakedDelinquents`** (boolean, tùy chọn): Mặc định là `false`. Nếu được đặt thành `true`, danh sách `delinquent` sẽ bao gồm các trình xác thực không có cổ phần nào được kích hoạt. Nếu không, chúng sẽ bị lọc bỏ.
4. **`delinquentSlotDistance`** (u64, tùy chọn): Chỉ định số lượng slot mà một trình xác thực phải chậm hơn đầu sổ cái để bị coi là không hoạt động đúng hạn. Nếu không được chỉ định, nút sẽ sử dụng giá trị mặc định.

## Cấu trúc phản hồi

Trường `result` trong phản hồi JSON-RPC là một đối tượng chứa hai mảng:

* **`current`**: Một mảng các đối tượng, trong đó mỗi đối tượng đại diện cho một tài khoản bỏ phiếu đang hoạt động với các trường sau:
  * **`votePubkey`** (chuỗi): Địa chỉ tài khoản bỏ phiếu (được mã hóa base-58).
  * **`nodePubkey`** (chuỗi): Khóa công khai định danh của nút trình xác thực (được mã hóa base-58).
  * **`activatedStake`** (u64): Lượng cổ phần, tính bằng lamport, được ủy quyền cho tài khoản bỏ phiếu này và đang hoạt động trong epoch hiện tại.
  * **`epochVoteAccount`** (boolean): Có giá trị `true` nếu tài khoản bỏ phiếu đã hoạt động ít nhất một lần trong epoch hiện tại.
  * **`commission`** (số): Tỷ lệ phần trăm hoa hồng (0-100) do trình xác thực thu.
  * **`lastVote`** (u64): Số slot gần nhất mà trình xác thực này đã bỏ phiếu.
  * **`rootSlot`** (u64): Slot cuối cùng mà nút coi là root (một khối đã được xác nhận hoàn toàn và sẽ không bị hoàn tác).
  * **`epochCredits`** (mảng): Một mảng gồm các mảng, trong đó mỗi mảng bên trong chứa `[epoch, credits_earned_in_epoch, previous_total_credits]`.
* **`delinquent`**: Một mảng các đối tượng có cùng cấu trúc với `current`, đại diện cho các trình xác thực bị nút coi là không hoạt động đúng hạn.

**Đoạn phản hồi mẫu:**

```json theme={"system"}
{
  "jsonrpc": "2.0",
  "result": {
    "current": [
      {
        "commission": 10,
        "epochCredits": [[300, 12345, 567890]],
        "epochVoteAccount": true,
        "lastVote": 180000500,
        "nodePubkey": "NodePubkeyExample123...",
        "rootSlot": 180000450,
        "activatedStake": "50000000000000", // lamports
        "votePubkey": "VoteAccountPubkeyExample123..."
      }
      // ... more current validators
    ],
    "delinquent": [
      // ... delinquent validators, if any
    ]
  },
  "id": 1
}
```

## Ví dụ mã

<CodeGroup>
  ```bash cURL theme={"system"}
  # Get all current and delinquent vote accounts:
  curl -X POST -H "Content-Type: application/json" -d \
    '{
      "jsonrpc": "2.0",
      "id": 1,
      "method": "getVoteAccounts"
    }' \
    <YOUR_RPC_URL>

  # Get a specific vote account:
  curl -X POST -H "Content-Type: application/json" -d \
    '{
      "jsonrpc": "2.0",
      "id": 1,
      "method": "getVoteAccounts",
      "params": [
        {
          "votePubkey": "<SPECIFIC_VOTE_ACCOUNT_PUBKEY>"
        }
      ]
    }' \
    <YOUR_RPC_URL>

  # Get vote accounts with "confirmed" commitment and keep unstaked delinquents:
  curl -X POST -H "Content-Type: application/json" -d \
    '{
      "jsonrpc": "2.0",
      "id": 1,
      "method": "getVoteAccounts",
      "params": [
        {
          "commitment": "confirmed",
          "keepUnstakedDelinquents": true
        }
      ]
    }' \
    <YOUR_RPC_URL>
  ```

  ```javascript JavaScript (using @solana/web3.js) theme={"system"}
  const { Connection } = require('@solana/web3.js');

  async function fetchVoteAccounts() {
    // Replace with your RPC endpoint
    const connection = new Connection('https://mainnet.helius-rpc.com/?api-key=<api-key>');

    try {
      // Get all vote accounts
      const voteAccounts = await connection.getVoteAccounts();
      console.log(`Found ${voteAccounts.current.length} current validators.`);
      console.log(`Found ${voteAccounts.delinquent.length} delinquent validators.`);

      if (voteAccounts.current.length > 0) {
        console.log("\nFirst current validator details:");
        console.log(`  Vote Pubkey: ${voteAccounts.current[0].votePubkey}`);
        console.log(`  Node Pubkey: ${voteAccounts.current[0].nodePubkey}`);
        console.log(`  Activated Stake: ${voteAccounts.current[0].activatedStake} lamports`);
        console.log(`  Commission: ${voteAccounts.current[0].commission}%`);
        console.log(`  Last Vote: ${voteAccounts.current[0].lastVote}`);
        // console.log(JSON.stringify(voteAccounts.current[0], null, 2)); // For full details
      }

      // Get a specific vote account (replace with an actual vote account public key)
      // const specificVotePubkey = 'SPECIFIC_VOTE_ACCOUNT_PUBKEY';
      // const specificValidator = await connection.getVoteAccounts('confirmed', specificVotePubkey);
      // console.log(`\nDetails for ${specificVotePubkey}:`, JSON.stringify(specificValidator, null, 2));

    } catch (error) {
      console.error('Error fetching vote accounts:', error);
    }
  }

  fetchVoteAccounts();
  ```
</CodeGroup>

## Mẹo dành cho nhà phát triển

* **Phản hồi lớn:** Phương thức này có thể trả về lượng dữ liệu lớn, đặc biệt trên các mạng có nhiều trình xác thực như Mainnet Beta. Hãy lưu ý đến kích thước phản hồi và thời gian xử lý.
* **Định nghĩa trạng thái không hoạt động đúng hạn:** Định nghĩa về "không hoạt động đúng hạn" có thể phụ thuộc vào `delinquentSlotDistance` và góc nhìn của nút. Một trình xác thực có thể bị coi là không hoạt động đúng hạn trên một nút nhưng không phải trên nút khác nếu các nút có góc nhìn khác nhau về đầu sổ cái.
* **Kích hoạt cổ phần:** `activatedStake` phản ánh số cổ phần đang hoạt động trong epoch hiện tại. Việc kích hoạt và hủy kích hoạt cổ phần cần thời gian.
* **Tín dụng epoch:** `epochCredits` cung cấp lịch sử hiệu suất của trình xác thực trong việc kiếm tín dụng thông qua bỏ phiếu.

Hướng dẫn này trình bày phương thức RPC `getVoteAccounts`, giúp bạn truy vấn và hiểu thông tin về trình xác thực trên mạng Solana.
