Chuyển đến nội dung chính

Documentation Index

Fetch the complete documentation index at: https://docs.raydium.io/llms.txt

Use this file to discover all available pages before exploring further.

Trang này được dịch tự động bằng AI. Phiên bản tiếng Anh là bản chính thức.Xem bản tiếng Anh →
Giao dịch Solana là danh sách các instruction được thực thi nguyên tử. Hiểu rõ cấu trúc giao dịch — instruction, account, signer, compute budget — là điều cần thiết để xây dựng, gỡ lỗi hoặc tối ưu bất kỳ thứ gì với Raydium. Trang này bao gồm cấu trúc đó, các giới hạn ràng buộc nó, và cách hai loại phí (phí mạng Solana, phí giao thức Raydium) được tích lũy trong một swap thực tế.

Cấu trúc giao dịch

Giao dịch Solana có ba thành phần cốt lõi:
  • Message: danh sách có thứ tự các instruction, các account mà chúng tham chiếu, và blockhash gần đây.
  • Signatures: một cái cho mỗi signer, xác nhận rằng giao dịch được phép.
  • Recent blockhash: chứng minh giao dịch là gần đây; các giao dịch có blockhash cũ (>150 slot) bị từ chối.

Instructions

Một instruction chỉ định:
  • program_id — chương trình được gọi.
  • accounts — các account (và cờ writable/signer của chúng) mà chương trình có thể sửa đổi.
  • data — các byte không minh bạch mà chương trình diễn giải.
Một giao dịch có thể chứa nhiều instruction. Chúng thực thi theo thứ tự; nếu bất kỳ instruction nào thất bại, tất cả các instruction trước đó đều được hoàn tác (nguyên tử). Giao dịch swap Raydium điển hình bao gồm:
  1. ComputeBudget::SetComputeUnitLimit — nâng giới hạn CU mặc định.
  2. ComputeBudget::SetComputeUnitPrice — đặt priority fee.
  3. Optional CreateAssociatedTokenAccount — tạo output ATA nếu người dùng không có.
  4. Raydium::SwapBaseInput — thực thi swap.
  5. Optional CloseAccount — đóng wrapped-SOL ATA.
SDK đóng gói các instruction này tự động thông qua raydium.trade.swap().

Accounts trong giao dịch

Mỗi account được sửa đổi bởi bất kỳ instruction nào trong giao dịch phải được liệt kê trong các account key của giao dịch. Mỗi account được đánh cờ:
  • Signer / non-signer: chủ sở hữu của account phải ký giao dịch không?
  • Writable / read-only: giao dịch có thể sửa đổi account không?
Runtime thực thi các cờ này: một chương trình cố gắng ghi vào account non-writable sẽ thất bại, và runtime từ chối các giao dịch thiếu signer cần thiết. Đối với CPMM swap, danh sách account có khoảng ~13 entry (xem solana-fundamentals/account-model). CLMM swap với nhiều lần vượt qua tick array có thể có 20+.

Giới hạn kích thước giao dịch

Solana giới hạn giao dịch ở mức 1232 byte bao gồm signature, message và header. Đây là trở ngại phổ biến nhất cho các giao dịch phức tạp — CLMM của Raydium với định tuyến multi-hop thường xuyên ấn vào giới hạn này. Breakdown của swap Raydium típ ~1000-byte:
Thành phầnKích thước
Signature64 B
Signature count1 B
Message header3 B
Blockhash32 B
Account keys (13 × 32 B)416 B
Instructions (4 × ~100-150 B)400–600 B
Tổng cộng~900–1100 B

Address Lookup Tables (ALTs)

ALT cho phép giao dịch tham chiếu các account bằng chỉ mục 1-byte trong bảng được công bố thay vì pubkey đầy đủ 32-byte. Điều này nén giao dịch một cách đáng kể:
  • Giao dịch tham chiếu 20 account trực tiếp: ~640 B pubkey.
  • Cùng giao dịch sử dụng ALT: ~20 B chỉ mục + tham chiếu ALT.
Raydium duy trì ALT cho các đường dẫn swap CPMM/CLMM trên mainnet. SDK sử dụng chúng tự động. Các aggregator xây dựng multi-hop route dựa vào chúng rất nhiều.
import { VersionedTransaction } from "@solana/web3.js";

// SDK xây dựng v0 (versioned) tx với tham chiếu ALT
const { transaction } = await raydium.trade.swap({ /* ... */ });
// transaction là VersionedTransaction, không phải legacy Transaction.

Compute budget

Mỗi giao dịch có compute unit (CU) budget. Vượt quá nó sẽ kết thúc thực thi và giao dịch thất bại.
  • Mặc định: 200,000 CU mỗi giao dịch.
  • Tối đa: 1,400,000 CU mỗi giao dịch (nâng lên thông qua ComputeBudget::SetComputeUnitLimit).
  • Trần mỗi block: 48M CU mỗi block (cấp độ giao thức).
Tiêu thụ CU điển hình của Raydium (xem integration-guides/priority-fee-tuning để xem bảng đầy đủ):
InstructionCU
CPMM swap~140,000
CLMM swap (không vượt tick)~170,000
CLMM swap (4 lần vượt tick)~320,000
Farm v6 stake~130,000
CPMM pool creation~250,000
Luôn đặt giới hạn CU rõ ràng thông qua ComputeBudget; nếu không, bạn sẽ nhận mặc định 200k, quá thấp cho hầu hết các instruction Raydium.
import { ComputeBudgetProgram } from "@solana/web3.js";

tx.add(
  ComputeBudgetProgram.setComputeUnitLimit({ units: 300_000 }),
);
Nếu bạn đặt giới hạn CU quá thấp, giao dịch sẽ thất bại khi chạm vào giới hạn; đặt quá cao và bạn rủi ro bị hạ ưu tiên khi có tắc nghẽn (và tùy theo mô hình giá, bạn thanh toán cho compute mà bạn không bao giờ sử dụng).

Priority fees

Ngoài phí giao dịch cơ sở (5000 lamport mỗi signature), các validator ngày càng ưu tiên các giao dịch thanh toán priority fee: một tip per-CU tính bằng microlamport.
priority_fee = compute_unit_price (micro-lamports) × compute_unit_limit
Ví dụ: 10,000 µL/CU × 300,000 CU = 3,000,000 µL = 0.003 SOL. Priority fee là cục bộ — chúng chỉ ảnh hưởng đến thứ tự trong một block; chúng không cải thiện khả năng được đưa vào so với không được. Đặt priority fee hợp lý là cần thiết khi có tắc nghẽn.
tx.add(
  ComputeBudgetProgram.setComputeUnitPrice({ microLamports: 10_000 }),
);
Xem integration-guides/priority-fee-tuning để biết cách điều chỉnh điều này một cách động.

Giới hạn số lượng instruction và account

Ngoài giới hạn 1232-byte tổng cộng:
  • Max account mỗi giao dịch: 128.
  • Max account mỗi instruction (CPI): 64.
  • Max instruction mỗi giao dịch: không có giới hạn cứng, chỉ bị giới hạn bởi giới hạn kích thước.
  • Max CPI depth: 4 (một chương trình có thể gọi cái khác, cái đó có thể gọi cái khác, 4 cấp độ).
CLMM swap của Raydium vượt qua nhiều tick array có thể ấn mạnh vào giới hạn account — một swap duy nhất sửa đổi pool, input/output vault, input/output ATA, nhiều tick array, có thể các account phụ của chương trình transfer-hook, cộng với các tham chiếu compute budget / system / token program bắt buộc. Các thiết kế soạn Raydium thông qua CPI (ví dụ: auto-compounders) cần phải tính đến điều này.

Danh mục phí trong swap Raydium

Giao dịch swap của người dùng trả phí trong hai danh mục:

Phí mạng Solana

Thanh toán cho các validator bằng SOL.
  • Base signature fee: 5000 lamport mỗi signature. Hầu như luôn là 1 signature = 0.000005 SOL.
  • Priority fee: CU-price × CU-limit tính bằng microlamport. Thay đổi tùy theo tắc nghẽn; xem integration-guides/priority-fee-tuning.
Các phí này đi đến validator, không liên quan đến Raydium, và được tính ngay cả cho các giao dịch thất bại (ngoại trừ một số trường hợp priority fee).

Phí giao thức Raydium

Được trừ từ số tiền swap.
  • Swap fee: phần trăm của input (CPMM 0.25% típ, CLMM 0.01%–1% mỗi tier). Chia giữa LP và các điểm đến giao thức. Xem ray/protocol-fees.
Các phí này là nội bộ trong kế toán của Raydium — người dùng thấy chúng là số lượng output nhỏ hơn so với những gì pool không phí sẽ tạo ra.

Ví dụ: $1000 USDC → SOL qua CPMM 0.25% tier

Danh mục phíSố tiềnĐi đến
Base signature fee0.000005 SOL (~$0.0007)Validator
Priority fee (10k µL × 300k CU)0.003 SOL (~$0.45)Validator
CPMM swap fee (0.25%)$2.50LP + giao thức
Tổng chi phí người dùng~$2.95
Slippage (price impact + thị trường di chuyển) không phải là phí nhưng ảnh hưởng đến cùng một kết quả cuối cùng.

Versioned transactions

Solana có hai định dạng giao dịch:
  • Legacy: định dạng gốc, không hỗ trợ ALT.
  • v0 (Versioned): hỗ trợ ALT, mở rộng cho các phiên bản trong tương lai.
Tất cả công cụ Solana hiện đại sử dụng v0. SDK Raydium phát ra giao dịch v0 theo mặc định.
// Xây dựng v0 tx trực tiếp
import { VersionedTransaction, TransactionMessage } from "@solana/web3.js";

const msg = new TransactionMessage({
  payerKey:        owner.publicKey,
  recentBlockhash: blockhash,
  instructions:    [ /* ... */ ],
}).compileToV0Message([lookupTableAccount]);

const tx = new VersionedTransaction(msg);
tx.sign([owner]);

Tươi mới blockhash

Một giao dịch phải bao gồm blockhash từ trong 150 slot gần đây (~60 giây). Vượt quá cửa sổ đó, các validator từ chối nó. Đối với retry loop, tìm nạp blockhash mới trên mỗi lần thử lại:
async function sendWithRetry(tx, maxRetries = 3) {
  for (let i = 0; i < maxRetries; i++) {
    const { blockhash, lastValidBlockHeight } = await connection.getLatestBlockhash();
    tx.message.recentBlockhash = blockhash;
    tx.sign([owner]);
    try {
      return await connection.sendRawTransaction(tx.serialize());
    } catch (e) {
      if (i === maxRetries - 1) throw e;
    }
  }
}
Xem integration-guides/priority-fee-tuning để biết mẫu retry-with-escalating-fees đầy đủ.

Thực thi song song

Solana thực thi các giao dịch không xung đột song song trên các validator đa lõi. Hai giao dịch xung đột nếu cả hai sửa đổi cùng một account. Hàm ý cho Raydium:
  • Hai swap trên cùng pool không thể thực thi song song — cả hai sửa đổi trạng thái pool.
  • Swap trên Pool A và swap trên Pool B thực thi song song nếu danh sách account không chồng lấp.
  • Giao dịch read-only không bao giờ chặn writer trên cùng một account (read-only là song phương với chính nó nhưng không với ghi).
Đây là lý do tại sao Solana có thể duy trì throughput DEX cao mặc dù serialization pool duy nhất.

Mức xác nhận giao dịch

Khi gửi giao dịch, bạn chọn mức xác nhận:
Mức độChờTính chắc chắn
processed~400 msKhông được hoàn tất; có thể rollback
confirmed~1 sSupermajority bỏ phiếu
finalized~13 sSupermajority rooted
Đối với swap UX, confirmed là tiêu chuẩn. Đối với các hoạt động xử lý giá trị lớn (pool creation, reward top-up), finalized an toàn hơn.
await connection.sendAndConfirmTransaction(tx, [owner], {
  commitment: "confirmed",
});

Mô phỏng

Solana hỗ trợ mô phỏng giao dịch trước khi gửi:
const sim = await connection.simulateTransaction(tx);
console.log(sim.value.logs);
console.log(sim.value.unitsConsumed);
SDK Raydium sử dụng mô phỏng nội bộ khi tính toán getBestSwapInfo để xác minh rằng tuyến đường đã chọn thực sự thành công. Mô phỏng không miễn phí — nó tiêu tốn dung lượng RPC — nhưng nó bắt được lỗi trước khi thanh toán.

Con trỏ

Nguồn: