Guide

Solana versioned transactions and address lookup tables

A simple SOL transfer lists two accounts and fits easily in a transaction packet. A Jupiter swap, an NFT mint with metadata, or a liquidation across five programs might need thirty or more accounts — and each account pubkey is 32 bytes on the wire. Solana's answer is versioned (v0) transactions paired with address lookup tables (ALTs): on-chain tables that let you reference frequently used addresses with a single-byte index instead of repeating full pubkeys.

Why transaction size matters

Solana transactions are capped at 1,232 bytes for the serialized message that validators sign and broadcast. In a legacy transaction, every account address in the message header and every instruction's account list is a full 32-byte Ed25519 public key. Signatures add 64 bytes each. Instructions add program IDs, account indexes, and data payloads.

Do the math: twenty accounts alone consume 640 bytes before you count signatures, blockhash, or instruction data. Complex DeFi routes hit the limit quickly. Wallets and aggregators responded by splitting work across multiple transactions (slower, worse UX, atomicity lost) — until v0 and lookup tables shipped in 2022.

Versioned transactions do not change Solana's execution model — programs still receive the same account metas at runtime. They only change how addresses are encoded in the serialized message. The account model (owners, lamports, writable flags) is unchanged.

Legacy vs versioned (v0) wire format

Every Solana transaction message starts with a version prefix:

At execution time the runtime resolves v0 messages: it loads each referenced lookup table account, expands 1-byte indexes into full pubkeys, and builds the flat account list programs see. From a program's perspective, nothing differs — only the serializer and deserializer change.

What you see in explorers

Solscan and other explorers label transactions as "legacy" or "v0." A v0 swap may show fewer raw pubkeys in the compact view because many addresses were pulled from lookup tables. Our Solscan walkthrough explains how to read account roles once the table is expanded.

How address lookup tables work

An address lookup table is a normal on-chain account owned by the Address Lookup Table program (AddressLookupTab1e1111111111111111111111111). Its data is a list of pubkeys — up to 256 addresses per table (index 0–255). Creating and extending a table costs rent (lamports locked in the account) plus transaction fees.

Lifecycle

A single v0 transaction can reference up to 64 lookup tables and pull addresses from all of them. In practice, one or two well-maintained tables (Jupiter's, a DEX's, or your own app's) cover most routes.

Writable lookups

Lookup entries can be marked writable in the message. The runtime enforces the same rules as legacy txs: a program cannot write to an account unless the instruction declared it writable and the signer authorized the change. Read-only table entries behave like read-only account metas.

When you need v0 and ALTs

You usually do not need v0 for: single SOL transfers, simple SPL sends, or two-instruction flows with under a dozen accounts. Wallets pick legacy format automatically when the message fits.

Building and debugging v0 transactions

Libraries

@solana/web3.js (v1.66+) exposes VersionedTransaction, TransactionMessage.compileToV0Message(), and helpers to fetch lookup tables from RPC before signing. Anchor and most wallet adapters pass versioned transactions through unchanged once built.

Simulation is non-negotiable

Wrong table indexes, deactivated tables, or stale addresses produce failures that look cryptic in wallet popups. Always simulate before asking users to sign. Simulation expands lookup tables server-side and returns program logs for the fully resolved account set.

Common errors

Priority fees still apply

v0 does not exempt you from compute limits or congestion. Heavy routes should set priority fees so validators include the transaction during busy slots.

Security notes for users

Lookup tables are indirection — a wallet popup may show "Address Table Lookup" instead of listing every pool address. That is normal for aggregator swaps, not automatically suspicious. Still apply the usual rules:

Practical checklist

For developers

For power users

Related guides