Skip to content

fix(backend): submit playground classic txs via Horizon, not Soroban RPC#39

Merged
miguelnietoa merged 1 commit into
mainfrom
fix/playground-transient-submit
Jun 29, 2026
Merged

fix(backend): submit playground classic txs via Horizon, not Soroban RPC#39
miguelnietoa merged 1 commit into
mainfrom
fix/playground-transient-submit

Conversation

@miguelnietoa

Copy link
Copy Markdown
Member

Problem

After the earlier retry fixes, the playground still failed on random mess steps in production. Driving the API directly surfaced a rotating cast of failures, all from the load-balanced public Soroban RPC whose nodes lag each other and the just-closed ledger:

  • Account not found on the first read (ingestion lag)
  • tx_bad_seq — stale sequence served to a consecutive same-account submit
  • tx_no_account — SETUP confirmed, but the next submit hit a node that hadn't ingested the source yet
  • 90s+ pollTransaction confirmation timeouts

Measured live: the Soroban RPC was running ~3 ledgers (~15s) behind Horizon, and a test submit returned ERROR. A direct API run scored 1/4 full sessions.

These are one root cause: reading and confirming classic state against an inconsistent RPC. The codebase already treats Horizon as the lag-free source of truth for classic accounts (account-live.ts), and Horizon submits classic txs synchronously (it holds the request until inclusion), so there's no read-then-poll window for the lag to slip through.

Changes

  • buildSignSubmit now reads the source account and submits through Horizon (lib/playground/horizon-submit.ts, HORIZON_URLS) instead of the Soroban RPC. Does not touch the main demolish flow.
  • The retry is now belt-and-braces, broadened to the transient codes tx_bad_seq + tx_no_account; BAD_SEQ_* renamed to SUBMIT_RETRY_*.
  • Raw fetch, not the SDK Horizon Server, to avoid a second SDK copy (v16 dual-build hazard).
  • Tests for the tx_no_account retry and the renamed budget.

Verification

  • bun type-check ✅ · bun lint ✅ · bun test tests/unit ✅ (247 pass)
  • End-to-end on testnet: 4/4 sessions (3 Full at 13 steps + 1 Standard) completed every mess step, ~4-6s each, zero bad_seq / no_account / timeout — up from 1/4 against the Soroban RPC under the same conditions.

The playground built and confirmed its classic mess transactions through the
load-balanced public Soroban RPC. Its nodes lag each other and the just-closed
ledger, which surfaced as a rotating cast of failures on random steps:
account-not-found on the first read, tx_bad_seq (stale sequence), tx_no_account
(source not yet ingested on the node that received the submit), and 90s+
pollTransaction confirmation timeouts. All are the same root cause - reading and
confirming classic state against an inconsistent RPC.

The rest of the codebase already treats Horizon as the lag-free source of truth
for classic accounts (account-live.ts). Horizon also submits classic txs
synchronously - it holds the request until the tx is included - so there's no
separate read-then-poll window for the lag to slip through.

- route buildSignSubmit's account reads and submission through Horizon
  (lib/playground/horizon-submit.ts, HORIZON_URLS) instead of the Soroban RPC
- broaden the (now belt-and-braces) retry to the transient RPC-lag codes
  tx_bad_seq + tx_no_account; rename BAD_SEQ_* to SUBMIT_RETRY_*
- raw fetch, not the SDK Horizon Server, to avoid a second SDK copy (v16
  dual-build hazard)
- tests for tx_no_account retry and the renamed budget

Verified on testnet: 4/4 sessions (3 Full at 13 steps + 1 Standard) completed
every mess step, ~4-6s each, with zero bad_seq / no_account / timeout - up from
1/4 against the Soroban RPC under the same conditions.
@vercel

vercel Bot commented Jun 29, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
lumenwipe Ready Ready Preview, Comment Jun 29, 2026 7:07pm

@miguelnietoa miguelnietoa merged commit cfc04ee into main Jun 29, 2026
4 checks passed
@miguelnietoa miguelnietoa deleted the fix/playground-transient-submit branch June 29, 2026 19:07
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant