Skip to content

Mykelsown/smart_transaction_stack-solana-

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

28 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Smart Transaction Stack

A real-time Solana transaction infrastructure system built for the Superteam Nigeria Advanced Infrastructure Challenge. It observes live network state, prices Jito bundle tips using an LLM-backed reasoning agent, submits bundles on mainnet, and tracks every submission across the full commitment lifecycle.

Architecture document: https://app.notion.com/p/Smart-Transaction-Stack-Architecture-Document-1e1d32ea43984f8da9af5f57a2799515


What this does

  • Streams live slot data from Solana via Yellowstone gRPC
  • Tracks the upcoming leader schedule and cross-references it against the live Jito validator set to find Jito-enabled leader windows
  • Uses an AI agent (Claude) to decide Jito tip amounts based on live tip percentiles, network urgency, and recent submission outcomes, with no hardcoded tip values
  • Constructs and submits real Jito bundles on Solana mainnet
  • Tracks each bundle's lifecycle (submitted → processed → confirmed → finalized) with timestamps, slot numbers, and latency deltas
  • Classifies failures (expired blockhash, fee too low, compute exceeded, bundle failure) rather than treating every non-success the same way
  • Writes structured JSON logs for every submission, success or failure, to /logs/

Known limitation: mainnet bundle landing

Real bundle submissions in this deployment were consistently accepted by Jito's block engine API (a bundle ID was returned each time) but did not land on-chain, confirmed via getBundleStatuses returning an empty result set and unchanged wallet balances across every attempt.

This was investigated across several independent angles rather than left unexamined: insufficient balance was ruled out (pre-flight balance checks passed every time), malformed transaction encoding was ruled out (a separate, distinct decode error encountered earlier was fixed and did not recur), and tip size as the sole cause was tested directly (a 300x tip increase produced an identical result). Leader-window timing was restructured three separate times, requiring proximity within two slots, then requiring the leader to be the current slot exactly, then targeting one to two slots ahead to account for submission round-trip latency, with no change in outcome across any variant. An RPC endpoint swap was also attempted as a further isolation step.

The consistency of this result across that many independently varied causes points toward infrastructure-level constraints rather than a single code defect: most likely network round-trip latency between the development environment and Jito's block engine exceeding the bundle's roughly 800ms effective validity window, and/or genuine auction loss against competing bundles tipping higher in the same window (observed directly in one run, where a parser fallback caused a 1,024 lamport tip to be submitted against a same-moment p95 of 27,653 lamports).

The full diagnostic process, including the specific evidence ruled in and out at each step, is documented in Section 5.3 of the architecture document. The submission logic, AI tip agent, lifecycle tracking, and failure classification system are all functional and were validated independently; the constraint identified here is specifically in the final mainnet network path to Jito's block engine under this deployment's conditions.

Why both devnet and mainnet

Jito's bundle infrastructure and tip economics are mainnet-only in any meaningful sense, since there's no real MEV incentive on devnet, which this project confirmed empirically rather than assumed (zero Jito-enabled leaders found in repeated devnet leader-schedule sampling). So:

  • Devnet is used for slot streaming and leader-schedule mechanics (free, safe, identical mechanics to mainnet for observation purposes).
  • Mainnet is used for actual Jito bundle submission, since that's the only place the bundle auction and tip economics are real. A small, dedicated wallet is used for this, funded with a minimal amount of real SOL.

Setup

Prerequisites

  • Node.js 18+
  • A Solana keypair (devnet) and a separate, small, dedicated Solana keypair funded with real SOL (mainnet); see Wallets below
  • An Anthropic API key (console.anthropic.com)

Install

git clone https://github.com/Mykelsown/Smart_Transaction_Checker-solana.git
cd Smart_Transaction_Checker-solana
npm install

Configure environment

Create a .env file in the project root:

RPC_URL=https://api.devnet.solana.com
YELLOWSTONE_ENDPOINT=https://solana-yellowstone-grpc.publicnode.com:443
YELLOWSTONE_TOKEN=
KEYPAIR_PATH=/path/to/your/devnet-keypair.json

MAINNET_RPC_URL=https://api.mainnet-beta.solana.com
MAINNET_KEYPAIR_PATH=/path/to/your/mainnet-keypair.json
JITO_BLOCK_ENGINE_URL=https://mainnet.block-engine.jito.wtf/api/v1/bundles

ANTHROPIC_API_KEY=your_key_here

.env is gitignored and must never be committed. It is not included in this repository.

Wallets

This project uses two separate keypairs:

Keypair Network Purpose
devnet-keypair.json Devnet Free testing, slot streaming, leader tracking
mainnet-keypair.json Mainnet Real Jito bundle submission, fund with a small amount only (0.05 to 0.1 SOL is sufficient for ~10+ submissions)

Generate a devnet keypair and fund it for free:

solana-keygen new --outfile ~/.config/solana/devnet.json
solana airdrop 2 <pubkey> --url devnet

The mainnet keypair should be funded with real SOL from an exchange or wallet, and should be treated as disposable. Never reuse a wallet holding significant funds for testing.

Running each phase

Slot streaming (devnet):

npx ts-node src/stream/slotStream.ts

Leader tracking (devnet, cross-referenced against live Jito validators):

npx ts-node src/stream/leaderTracker.ts

Real bundle submission (mainnet, spends real SOL):

npx ts-node src/bundle/submitRealBundle.ts

Lifecycle tracking loop (writes structured logs to /logs/):

npx ts-node src/tracker/runTracker.ts

AI agent demo (Tip Intelligence, against representative scenarios):

npx ts-node src/agent/runAgentDemo.ts

Project structure

src/
├── stream/
│   ├── slotStream.ts        # Yellowstone gRPC live slot subscription
│   └── leaderTracker.ts     # Leader schedule + Jito validator cross-reference
├── bundle/
│   └── submitRealBundle.ts  # Real mainnet bundle construction & submission
├── tracker/
│   ├── types.ts             # Shared BundleRecord / FailureReason types
│   ├── logger.ts            # JSON log read/write
│   ├── mockSource.ts        # Simulated bundle data (used during development)
│   ├── realSource.ts        # Real bundle submission wired into the tracker
│   └── runTracker.ts        # Orchestrates submission + logging loop
└── agent/
    ├── tipAgent.ts          # Claude-backed tip decision logic
    └── runAgentDemo.ts      # Standalone agent demo across test scenarios
logs/                        # Structured JSON lifecycle records (generated)

README questions

What does the delta between processed_at and confirmed_at tell you about network health at the time of submission?

This delta measures how long it took for a supermajority of stake-weighted validators to vote on the block containing the transaction. A short delta indicates validators are voting promptly, a healthy network. A delta that grows under load signals congestion or validator-side delays in vote propagation, even if slot production itself remains on schedule.

Why should you never use finalized commitment when fetching a blockhash for a time-sensitive transaction?

A blockhash is valid for roughly 150 slots from when it was produced. finalized commitment reflects state from roughly 30+ slots in the past, since Solana finalizes conservatively to guarantee irreversibility. Fetching a blockhash at finalized commitment starts the transaction's validity countdown already a fifth of the way through its window, before the transaction is even built, which is a real risk under any submission delay or retry. confirmed commitment gives a blockhash that is both recent and safely backed by supermajority vote.

What happens to your bundle if the Jito leader skips their slot?

The bundle is not retried automatically. It is simply never seen by whichever block actually gets produced. Jito routes bundles to the specific leader scheduled for that slot; if that leader misses its slot, the next validator who produces a block may not run Jito at all, and has no visibility into the bundle queue. This is indistinguishable, from the submitter's side, from a bundle that lost the tip auction, since both look like "accepted, never landed." This project's submission logic gates on leader-window proximity before submitting specifically to minimize this failure mode.

License

MIT

About

No description, website, or topics provided.

Resources

License

Stars

2 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors