A dummy's guide to Solana's architecture

A dummy's guide to Solana's architecture

a one-stop run through of Solana's core concepts

Introduction

This tutorial is meant to be for a spectrum of readers:

  1. Those experienced in the EVM space

  2. Those new to web3

  3. Non-developers

We will be going through some of the core concepts in Solana's architecture. These are basic building blocks for every action on this chain. The concepts we are going to discuss are not only beneficial to understand for aspiring developers but also for end users to make the most out of the experience of fast and cheap transactions on Solana.

Let us start with understanding how to read data on-chain. This will give us more context for the theoretical concepts we discuss later.

The Block Explorer: a window to the chain

Block explorers are online interfaces which provide the user a chance to search for past and on-going transactions, wallet addresses and other useful info on a given chain. This provides a dimensionality of transparency between the chain and its users.

Solana has several block explorers to choose from:

Image description

Throughout the tutorial, we'll see examples right from the block explorers that juxtapose the theory we discuss. Here are some of the words you'll see often throughout the tutorial:

  1. Blocks, Validators and Proof of History

  2. Accounts

  3. Instructions and Transactions

  4. Programs

  5. Token Program

  6. Token Metadata Program

  7. Program Derived Addresses (PDA)

  8. SPL-tokens, Fungible Assets and Non-Fungible Tokens (NFTs)

Let's start from the very top. What is a Blockchain?


Blocks, Validators and Proof of History:

blockchain

Without going into the depths of the jargon ocean, a blockchain is simply a digitally distributed database. The key difference between a typical database and a blockchain is how the stored data is structured.

A blockchain stores and manages data into small groups known as Blocks. A block usually stores important information like input and output hashes, number of transactions and the event it contains. When a block is filled with data or "created" by a blockchain node, it is linked to the previous blocks. This forms a chain of blocks, or a blockchain.

In the case of Solana, when a node claims to have created a block, the other nodes strive to verify this claim. The node that generated the block is known as the Leader and the nodes that verify the claim are known as Validators.

How does this validation, or consensus work on Solana? The answer is something called Proof of History (PoH)

vdf

"Proof of History is exactly what the name suggests: a proof of historical events", Anatoly Yakovenko.

PoH is a SHA-256 hashed, verifiable delay function (VDF): this function guarantees the following: when the output hash is validated for an input hash, it is by the nature of PoH that we can confirm that some time has passed since we provided the input. This very nature of the VDFs insures the super fast speeds of the Solana blockchain.

This is exactly what makes Solana unique. Its extremely easy, fast and cheap-to-use nature allows itself to be named the world's first web-scale blockchain.

Coming back to how Validators prove that the Leader node is the node that generated the block: the Validators run the above PoH VDF on a number of transactions existing on the block to be verified. The outputs of the VDF are then compared with the outputs provided by the Leader node. Once proven, the Leader is then confirmed to have created the block and rewards for validation are distributed to all the validators, including the Leader.

Image description

In the above view of a given block #154616344, we can see a variety of information.

  • Block Hash: The SHA-256 hash (reference number) for a given block on chain.

  • Leader: The block hash of the node that created the given block.

  • Previous Block Hash: The parent block's # of the given block.

  • Reward: The total rewards distributed to the Validators.

  • Transactions: The total number of transactions (successful + unsuccessful) executed in the given block.

Now, if you click on one of the hashes in the By column of the Transactions section, we land on a page which gives a detailed overview of the Account with hash GFDmfhoPtZZATNxw8zyZPVYKkBZutf1zoZTbRbxDjh5E.

Image description

Let us first go through some theory and after which we can truly understand the account page and all its components.


Accounts

Solana's Account model is very unique and is partially responsible for why it's so fun to build apps on it.

On any blockchain, decentralised apps need to track the current state: number of tokens, NFTs transferred, current highest bidder in an auction, orders for a token on a dex etc. These states need to be saved in data storing units on-chain, called accounts.

On EVM, smart contracts are executable pieces of code or programs. They are accounts themselves and store their own data. The code inside the smart contract defines how the data within the account is going to be modified.

On Solana, Accounts and on-chain programs interact differently. On-chain executable programs are stored in completely immutable accounts, whereas data that the executable programs interact with is stored in mutable accounts.

All accounts on Solana are assigned a Program as the owner and only these owners are allowed to make changes to the data (or debit SOL) from a given account. Important to note here: anyone can credit funds permissionless-ly to an account.

A developer coming from the EVM space might find this state-less Account Model to be a little confusing and complex. But this model allows something which is not possible in other chains: Transaction parallelisation. We are going to talk more about this in the following section.

On Solscan's page for account GFDmfhoPtZZATNxw8zyZPVYKkBZutf1zoZTbRbxDjh5E, we can see that the account holds some SOL and has some tokens. We'll discuss what tokens are later. But for now lets check out the section for Transactions. If you click on any one of the Signatures of these transactions, we'll land on a new page which shows some Transaction details. Before we dive deep into this, let's understand what transactions are.


Instructions and Transactions

Instructions are the basic operational units on Solana. Instructions are commands that can be bundled up together to form Transactions. These transactions can then be executed by a Program to read and/or write data from one or more Accounts. The instructions that form the transaction are executed atomically, or one-by-one in the order in which they were added to form the transaction. If one instruction fails, the entire transaction is invalidated.

An instruction takes the following data:

  1. program_id of the Program which owns the accounts who's states are going to change

  2. Array of all accounts the instruction intends to read/write data from.

  3. instruction_data array which specifies more metadata intended for the program program_id.

One of more of such instructions are then bundled to form the transaction which needs to specify the following data before it can be executed:

  1. Array of all accounts it intends to read/write data from.

  2. Array of all instructions the transaction wants to specify in the very same order the user wants to execute them

  3. Recent blockhash: this is required to prevent duplication and stale transactions. The max age of transaction is 150 blocks.

  4. signatures of all accounts the given transaction intends to debit from or to write data into. This signature array needs to be in the same order of the corresponding accounts in the accounts array.

While we are talking about transactions, it's important to also talk about the Transactions per Second (TPS) of the network. Solana is famed to have one of the highest TPS of any chain.

vote vs non-vote

There are two types of transactions Vote and Non-Vote transactions. Vote transactions are used to do the network validation as described in the Proof of History section and hence are not the "true" transactions being utilised for doing the actual work like transferring NFTs / tokens, bidding, selling etc. The graph above shows that in the last 7 days, the number of Vote transactions are almost 7 times as much as the Non-Vote transactions. This plays into the true TPS (Transactions per Second) debate of Solana: although Solana is blazingly fast with reported TPS touching averaging >3k, the true TPS (removing transactions for Voting) is <1.5K.

Now that we know what transactions and instructions are, we ought to understand who actually triggers/interacts with them. The answer is Programs.


Programs

We have mentioned Programs quite a lot of times in this tutorial. But what exactly are Programs?

The equivalent to smart contracts on Solana are Programs. Programs are nothing but executable code that is stored in completely immutable Accounts marked as executable.

The way Programs differ from Smart Contracts is that Programs on Solana are stateless, i.e., they do not store the data that they are processing and acting on. Programs are stateless and all data must be passed in via separate accounts from the outside. This allows the processing of data in a parallel fashion: multiple programs can reuse the same accounts for different purposes, in different transactions.

analogy

You can imagine this parallelisation to be something similar to how functions in programming work. In programming, we can define variables to store some data. These variables can then be passed as reference to functions that make changes to these variables. In this analogy, the variables are Accounts and the functions are Programs.

Coming back to the Solscan page for a transaction with signature 3bsfEaCdbjcBvXQT3Fx85R2TvKL3KJe5kb4G8XYqUFXCBxKzemu6FV3fi2C51TBtcKpjygCfzdXsjg9dTjVxpEo5, we can start to understand what its trying to tell us.

tx overview

In the transaction overview, we can checkout the block in which the transaction was executed, the fee to run the transaction, whether the transaction was successful or not and most importantly, the main actions that the transaction executes. In this case, there was a transfer of 253 SOL from wallet GFDmfhoPtZZATNxw8zyZPVYKkBZutf1zoZTbRbxDjh5E to 4tzAkc7cGTns1dsVaP18KvMkt9jEmzA1AaV3rMzgyi7f.

tx ix detail

We can also see the same on the instruction detail. In the given transaction, only 1 instruction was executed. As it was a simple SOL transfer, the program which interacts with the transaction is the System Program, with hash: 11111111111111111111111111111111.

If we go back to the Account page on Solscan, we can see a section for Token Accounts and also see some SPL-tokens listed. Let us see what these are.


SPL-tokens, NFTs and the Token Program

Like any other blockchain, Solana has tokens as well. These are assets that exist on-chain and can be traded from person to person or through secondary marketplaces. These tokens fuel several use-cases of blockchain technology like DeFi and are important for retail adoption of the crypto-economy.

All tokens on Solana are made with Solana's Token Program and follow Metaplex's Token Metadata Standard. Let us see how these programs play together to form different tokens on Solana.


Token Program

Solana's Token program is responsible for defining the common implementation for all tokens on Solana.

The spl-token-cli is a part of the Token program and allows the generation of tokens using command line:

spl-token create-token

You can follow the following reference guide to play around with the CLI but we won't go too deep into the specifics in this tutorial.

To fully understand how tokens work on Solana, its important to understand the account model of the Token program.

token program

In the image above we can see 3 accounts: Wallet Account, Token Account and the Mint Account. The Wallet Account is owned by the native System Program and represents a user's wallet. The Token Account and the Mint Account are owned by the Token Program.

  1. The Mint Account is responsible for storing global information regarding the Token, like current supply, Authority (the account address which has the authority to make changes to the given Account), token name, decimals, number of holders etc.

  2. The Token Account is responsible for storing the relationship between the Wallet Account and the Mint Account. This account stores data like the number of tokens held by the wallet etc.

Associated Token Account Program

While discussing Token Accounts, its important to mention about the Associated Token Accounts. Why are these needed?

There can be more than 1 token accounts for a given token in a wallet. When a user sends a token from wallet A to wallet B, the user does not know which token account to specify as the destination token account. To solve this problem, associated token accounts are used to deterministically derive a token account address from a user's System Account (wallet) and the mint address.

While the Mint Account stores some global information regarding tokens, it is not capable of storing enough data to be able to be standardised and used globally by dapps and wallets. Here's where Metaplex's Token Metadata Program comes in.


Token Metadata Program

The Token Metadata Program is used to attach additional data to all tokens on Solana. This allows wallets, dapps and even block explorers to present tokens in a standardized way, creating a uniform user experience across the ecosystem.

To enhance Mint Accounts with additional metadata, the Metadata program uses a concept called Program Derived Addresses (PDA).

Program Derived Addresses (PDAs)

When we discussed Accounts, we talked about the need for the account's owner to sign transactions whenever a program makes a change to the said account.

This is problematic and not always possible. Imagine a use-case where we are counting the number of tokens in a given account and this number needs to be saved on-chain. The account's owner will have to sign transactions each time this number changes.

An ingenious solution to this is PDAs. PDAs envelop accounts that can be programmatically controlled by certain programs. This allows programs to sign on behalf of these accounts without requiring a private key, as shown below.

PDAs

PDAs are deterministically derived from a program_id and a string (also known as seeds) like "auction_house" or "token_metadata". If you want to dive deep into how PDAs are generated, I highly recommend reading Solana Cookbook's PDA guide.

To attach additional data to a Mint Account, the Token Metadata Program derives a PDA from the Mint Account’s address. This PDA is then used to store a Metadata Account with the Mint Account using a PDA as shown below.

token metadata program

A Metadata account stores lots of useful information that Mint Accounts could not provide. This account also has a URI field which points to an off-chain JSON object. This object saves information like the image and attributes for an NFT.

The combination of the Token Program and the Token Metadata Program allows tokens to be categorised into three broad categories depending on two characteristics:

  1. supply: the total number of tokens in circulation.

  2. decimal places: the number of decimals points a token is allowed to have. For example: SOL is allowed to have 9 decimal points, which means, 10^-9 SOL is a valid denomination and can be transferred between wallets.

different types of tokens

Fungible Tokens

Fungible tokens are based on the Solana Program Library (SPL) and are supported by SOL the same way ERC-20 tokens are supported by ETH. These tokens can be held in any quantity and can be freely mixed with others of the same mint, just like SOL, BTC, ETH and other cryptocurrencies.

SPL-tokens and their associated metadata can be generated on the CLI using Metaboss

metaboss create fungible -d <decimals> -m <metadata_file>

What sets the SPL-tokens apart are their characteristic of having:

  1. supply > 1

  2. decimal places > 0

We can see an example of such a token on Solscan as well. Lets check out DUST Protocol, which is a Fungible token on Solana.

dust protocol

On the Profile Summary, we can see the token's name and address. We can also see that this account is owned by the Token Program, indicating that this is a Mint Account. Furthermore, we can see the authority of the token as well as the number of decimal places. On the Market Overview, we can see the supply which is > 1. The supply and decimal combination shows that the given token is a Fungible token.


Fungible assets

Fungible assets are tokens that have:

  1. supply > 1

  2. decimal places = 0

Having a supply greater than 1 but decimal places equal to 0 creates tokens that have very unique use-cases: gaming assets or utilities like a shield or a piece of wood. These assets with decimals equal to 0 can't be divided or fractionalised but are non-singular in supply, thus allowing distribution to a number of users.


Non-Fungible tokens (NFTs)

These tokens are the ones which have gained a lot of traction in this past year. NFTs are tokens that are non-replaceable / interchangeable. What this means is that there can not be more than one specimen of a given token. Every token is unique and can't be fractionalised. Here are their properties:

  1. supply = 1

  2. decimal places = 0

NFTs are usually represented by a visual asset: it could either be an image, video or gif. The asset could also be an mp3 file thus allowing the possibilities of music NFTs.

An example of an NFT on Solana can be seen here: Token Address HRFCfME6TpoiRMQ9bC3Peb7X9Suk5jeZZV15GYg5QGqM.

NFT

This NFT belongs to the well known DeGods Collection. In the NFT Overview section, we can see a Royalty set by the creator. This is a fee which is paid to the original creator of the NFT, on every trade of the given NFT. Recently DeGods creators have reduced their royalties from 10% to 0%. We can also see a Creators tab, which lists the addresses of the original creators of the collection and their corresponding percentages out of the total royalties they receive. On the Attributes tab, we can see some specific attributes of the NFT. These attributes vary across NFTs in the collection and hence give uniqueness to each NFT depending on the specific combinations of the attributes. In the Profile Summary, we can also see that the supply is 1, hence ensuring that its an NFT.

Let's check out the Metadata tab of the NFT which showcases some interesting information. There are two sets of metadata that we can see in this tab: on-chain and off-chain metadata.

Here's the on-chain metadata: solscan.io/token/HRFCfME6TpoiRMQ9bC3Peb7X9S..

We can quickly see that the on-chain metadata points to an off-chain json URI which is the off-chain metadata for the NFT:

{
   "name":"DeGod #6641",
   "symbol":"DGOD",
   "description":"10,000 of the most degenerate gods in the universe.",
   "seller_fee_basis_points":999,
   "image":"https://metadata.degods.com/g/6640-dead.png",
   "external_url":"https://degods.com/",
   "attributes":[
      {
         "trait_type":"background",
         "value":"Purple"
      },
      {
         "trait_type":"skin",
         "value":"Lavender Stripe"
      },
      {
         "trait_type":"specialty",
         "value":"Mythic Wings"
      },
      {
         "trait_type":"clothes",
         "value":"God Scout Uniform"
      },
      {
         "trait_type":"neck",
         "value":"None"
      },
      {
         "trait_type":"head",
         "value":"Bed Head"
      },
      {
         "trait_type":"eyes",
         "value":"Neon Shades"
      },
      {
         "trait_type":"mouth",
         "value":"None"
      },
      {
         "trait_type":"version",
         "value":"DeadGod"
      },
      {
         "trait_type":"y00t",
         "value":"Claimed"
      }
   ],
   "collection":{
      "name":"DeGods",
      "family":"Godplex"
   },
   "properties":{
      "files":[
         {
            "uri":"https://metadata.degods.com/g/6640-dead.png",
            "type":"image/png"
         }
      ],
      "category":"image",
      "creators":[
         {
            "address":"AxFuniPo7RaDgPH6Gizf4GZmLQFc4M5ipckeeZfkrPNn",
            "share":100
         }
      ]
   }
}

One can read more about how to mint an NFT and set the metadata for the NFTs on Metaplex docs.


Further Reading

We've gone through a lot of information on Solana's architecture. This is just the basic information needed by a someone to get started with developing on Solana. Here are some important links I highly recommend going though once you've understood this article:

  1. Solana Cookbook: for diving deep into some of the concepts we talked about and also getting started with some easy to understand JS code snippets.

  2. Solana Bytes: A very easy to understand quick video tutorials on the concepts discussed in this article.

  3. Solana Development Course: A very good starting point to start coding on Solana once some of the core concepts are clear.

  4. Loris Leiva's DApp from Scratch: A very simple to understand tutorial for making a full stack DApp on Solana.

  5. At this point you Solana concepts are pretty strong. You can start coding your own programs on Solana with Rust lang**.

References