OpenViSTAI · Agents · Blockchain · Crypto
Menu
OPENVIST RECIPES

Build a read-only Solana balance tool

Python

Create a small balance reader with an explicit network, public account and commitment level.

Python code excerpt: Build a read-only Solana balance tool. Version 1.0.0. Read the full recipe for code, sources and recorded test scope.

An agent tool should expose a narrow operation and validate its arguments before making a request. This function reads a public account through Solana’s getBalance method and returns the integer amount in lamports with the RPC context. It can be connected to a tool-calling application after its inputs and errors have been tested.

Before you start

  • Python 3.10 or later; this example uses only its standard library.
  • A base58 public account address that decodes to 32 bytes.
  • Access to the selected Solana RPC endpoint. Public endpoints have rate limits.

Build and check

  1. Start on Devnet and choose the commitment required by your application.
  2. Change the account field and inspect the generated request and validation function.
  3. Run the file and keep the network, commitment, lamports and context together.
  4. Before attaching the function to an agent, define the allowed arguments and handle RPC errors, timeouts and rate limits in the host application.

Limits to understand

  • This recipe does not sign or submit transactions and does not need a private key.
  • Devnet and Mainnet beta are separate networks. A balance on one is not a balance on the other.
  • Keep lamports as an integer. The preview validates the address shape and length, not the account’s purpose or existence.
ADJUST THE EXAMPLE

Change a setting. Inspect the result.

This browser preview builds code locally. It does not contact an API or run the code.

Default example ready.

Python example
"""Read an account balance without signing or sending a transaction."""
import json
from urllib.request import Request, urlopen

NETWORK = "devnet"
COMMITMENT = "finalized"
ADDRESS = "11111111111111111111111111111111"
ENDPOINTS = {"devnet": "https://api.devnet.solana.com", "mainnet-beta": "https://api.mainnet-beta.solana.com"}


def validate_address(address):
    alphabet = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"
    if not 32 <= len(address) <= 44 or any(c not in alphabet for c in address):
        raise ValueError("Expected a base58 public account address.")
    number = 0
    for char in address:
        number = number * 58 + alphabet.index(char)
    decoded_length = (number.bit_length() + 7) // 8 + len(address) - len(address.lstrip("1"))
    if decoded_length != 32:
        raise ValueError("Expected a 32-byte public account address.")


def get_balance(address=ADDRESS, network=NETWORK, commitment=COMMITMENT):
    validate_address(address)
    if network not in ENDPOINTS or commitment not in {"processed", "confirmed", "finalized"}:
        raise ValueError("Unsupported network or commitment.")
    body = {"jsonrpc": "2.0", "id": 1, "method": "getBalance", "params": [address, {"commitment": commitment}]}
    request = Request(ENDPOINTS[network], data=json.dumps(body).encode(), headers={"Content-Type": "application/json"})
    with urlopen(request, timeout=15) as reply:
        data = json.load(reply)
    if not isinstance(data, dict):
        raise RuntimeError("The RPC response must be a JSON object.")
    if "error" in data:
        raise RuntimeError(f"RPC error: {data['error']}")
    result = data.get("result")
    value = result.get("value") if isinstance(result, dict) else None
    if type(value) is not int or value < 0:
        raise RuntimeError("RPC response did not contain a non-negative lamport balance.")
    return {"network": network, "commitment": commitment, "address": address, "lamports": value, "context": data["result"].get("context", {})}


if __name__ == "__main__":
    print(json.dumps(get_balance(), indent=2))
What to verify after running
  • Only getBalance is requested; no transaction or signing method is present.
  • Invalid addresses and unsupported networks are rejected before a network request.
  • Large lamport values remain integers, and a JSON-RPC error stops processing.

Request or format preview

Illustrative preview. No provider response, price or balance is fetched.

Change a setting to inspect the preview.

Official sources and related profiles

Code license: MIT. Keep the license notice with your copy.

Example version 1.0.0 · Documentation reviewed 2026-10-06.

Code syntax, address validation, network selection and mocked RPC responses checked locally. No agent integration or live RPC execution is claimed.