Skip to content

Repository files navigation

HyperEVM RAM / hyperRAM arbitrage bot

Mainnet-targeted keeper plus a fixed-route Solidity executor and Python GUI. Nothing is deployed until the GUI user presses Start with a funded key. The CLI starts in quote-only mode; the GUI Start button is an explicit HyperEVM mainnet live action.

Warning

Experimental and unaudited software that moves real mainnet funds. It provides no profit guarantee and may lose the entire amount exposed to it through contract bugs, protocol changes, MEV, stale prices, RPC faults, or operator error. Review the source and use a dedicated low-value wallet. Never enter a seed phrase or a primary-wallet key.

Clean-clone prerequisites

  • Windows 10/11 for the included GUI launcher
  • Node.js 20 or newer and npm
  • Python 3 with Tkinter
  • Foundry with forge on PATH

Complete the one-time setup in PowerShell before using the launcher:

git clone https://github.com/winglock/hyper-evm-arb-bot.git
Set-Location hyper-evm-arb-bot
npm ci
npm test
python gui.py --smoke-test

Python GUI — quickest start

After completing the prerequisites above, double-click start_gui.cmd, paste a dedicated wallet private key, and press 시작. The GUI builds without the key, then sends the key once to the ready worker through anonymous stdin. It is never put in argv, environment variables, .env, deployment records, or logs.

The first run automatically deploys the fixed executor with that wallet as owner/operator, so the wallet needs HYPE for deployment and trading gas. Later runs validate and reuse the saved public executor address/code hash. The default key-only strategy is flash-funded:

  1. Keep scanning when there is no net-profit opportunity; send no transaction.
  2. When expected RAM profit covers the configured minimum plus protected gas, simulate and execute atomically.
  3. After confirmation, return to step 1 and continue until 중지 is pressed.

Profits accumulate as RAM in the executor and its live balance is shown in the GUI. Use a dedicated wallet: running MetaMask or another bot from the same operator wallet can cause nonce conflicts. Stop requests cease new scanning and reconcile a pending transaction before exit; the non-secret pending/deployment journals live under .local/.

Manual launch:

python gui.py

Mechanism

The fixed route is:

  1. Start with RAM (prefunded executor) or borrow RAM from the fixed RAM/USDC V3 pool's flash facility.
  2. Swap RAM to hyperRAM through the fixed volatile V2 pair.
  3. Redeem hyperRAM to its xRAM asset.
  4. Exit xRAM to RAM, paying the on-chain slashing penalty.
  5. Repay principal plus the rounded-up V3 flash fee when using flash mode; keep only positive RAM profit.

The executor also rejects a flash callback whose actual RAM fee exceeds 5%. The prefunded path does not pay that flash fee and is therefore the practical default when the flash spread is too narrow.

The economic floor is previewRedeem(1e18) passed through xRAM's current exit penalty. At the observed 50% penalty this was about 0.7068 RAM per hyperRAM. The approximate ceiling (about 1.4135 in the supplied snapshot) is the direct mint/deposit cost before the early-exit haircut. The observed market near 0.6082 was below that floor. Those numbers are explanatory snapshots only: the keeper never hard-codes them. Every cycle reads BASIS, SLASHING_PENALTY, paused, reserves, V2/V3 fees, previewRedeem, and V3 slot0 again.

Candidate sizes are ranked locally using volatile constant-product integer math with the V2 fee denominator of 1,000,000. The winning size is then revalidated through the pair's authoritative getAmountOut and vault previewRedeem. All slippage, penalty, flash-fee, and USD conversions round conservatively with bigint arithmetic.

Fixed mainnet targets

  • Chain ID: 999
  • RAM: 0x555570a286F15EbDFE42B66eDE2f724Aa1AB5555
  • hyperRAM: 0x5555c2542836e7a6c8D3E133D5AA9773b65D5555
  • xRAM: 0xAE6D5FcE541216BDA471D311425B5412D9f1DEb9
  • volatile RAM/hyperRAM V2 pair: 0x4F7c506ea3cfd607A7eF7eF8dC678ca886E03e16
  • RAM/USDC V3 price/flash pool: 0xbE052ED684849311604d7a4Bc45ef291526E34A2

Startup verifies chain ID, runtime bytecode hashes, token ordering, the volatile flag, and hyperRAM's xRAM asset. A code change or proxy upgrade fails closed. Live mode additionally requires the deployed executor's exact runtime code hash and verifies that the connected wallet equals executor.operator().

Existing deployment is reference-only

The deployment at 0xBe233374e68828db9C9E3E866FEE9A59D0b94c83 has an exact_match source verification on Sourcify and is published only as a bytecode/reference deployment. It is not a shared public executor:

  • execute and executeFlash accept calls only from that deployment's owner/operator.
  • Only its owner can pause it and recover accumulated tokens.
  • Sending RAM, HYPE, or any other asset to it does not grant access and may make the asset unrecoverable to the sender.

Every user should deploy a separate executor controlled by their own owner/operator addresses. The GUI does this automatically on first use for a new wallet. Deployment metadata for the reference address is in deployments/hyperevm.json. A fresh clone intentionally does not import another machine's .local deployment records; using the same wallet from a fresh clone can therefore deploy another executor. Owner/operator changes also require corresponding keeper configuration updates.

Safety model

A transaction is impossible unless all of these are simultaneously true:

  • LIVE_MODE=true
  • DRY_RUN=false
  • valid PRIVATE_KEY, EXECUTOR_ADDRESS, and EXECUTOR_CODEHASH
  • fixed target/code checks pass
  • notional, minimum RAM profit, gas fee, block freshness, xRAM pause, and circuit-breaker checks pass
  • executor execute/executeFlash succeeds under eth_call
  • the same call succeeds under estimateGas, then succeeds under a final adjacent eth_call
  • RAM profit converted through the V3 price exceeds operator-supplied HYPE/USD gas cost

Nonce-bearing sends are serialized, explicitly signed with the pending nonce, and recorded by hash before raw broadcast. The keeper never waits indefinitely for a receipt: each loop performs one reconciliation pass capped by RECEIPT_POLL_TIMEOUT_MS and refuses every new nonce while any hash is unresolved. After PENDING_TX_TIMEOUT_MS, it sends a same-nonce, higher-fee zero-value self-cancel; cancellation bumps are capped by MAX_TX_REPLACEMENTS, REPLACEMENT_FEE_BPS, and MAX_FEE_GWEI. Exhaustion remains fail-closed for manual intervention. All original and replacement hashes are polled because either may win. Startup also fails closed if the signer already has a latest/pending nonce mismatch, preventing silent nonce drift after a restart. Three execution failures (configurable) open a cooldown circuit. SIGINT/SIGTERM stop the loop between awaited operations. Logs are newline-delimited JSON and do not print the private key.

HyperEVM's public RPC supports eth_call/estimateGas reliably only at latest. Consequently this keeper does not pretend numeric blockTag is a snapshot: it uses uncached raw eth_blockNumber fences, discards mixed-block quote snapshots, refreshes protocol state and the authoritative quote inside the signing lock, and performs a final executor eth_call immediately before signing. The provider request cache is disabled. Startup verifies raw eth_chainId; it does not trust an ethers static-network declaration.

Install and run

Requires Node.js 20 or newer.

npm ci
Copy-Item .env.example .env
npm test
npm run typecheck
npm start

Keep DRY_RUN=true while confirming RPC compatibility and executor ABI. For prefunded mode, transfer only the intended RAM working inventory to the executor. For flash mode, the included executor exposes:

executeFlash(uint256 amountBorrowed, uint256 minHyperOut, uint256 minProfitRam, uint256 deadline)

Prefunded mode uses the analogous execute(...) signature documented in src/constants.ts. The keeper ABI must match the deployed bytecode; a source file alone is not evidence of safety.

Contract build and deployment

The executor is contracts/src/HyperRamArbitrage.sol. Run both local and live-fork tests before considering deployment:

Push-Location contracts
forge build
forge test -vv
$env:HYPEREVM_RPC_URL = "https://rpc.hyperliquid.xyz/evm"
forge test --match-contract HyperRamMainnetForkTest -vvvv
Pop-Location

Without HYPEREVM_RPC_URL, the three fork tests are reported as skipped rather than silently passed. With the RPC set, the fixed-address and live flash-callback compatibility tests must pass. The prefunded full-route test runs only when the live route is profitable at the chosen amount; otherwise it is intentionally reported as skipped.

Deploy only after independent review. Use a Foundry keystore instead of putting a deployment key on the command line. The constructor takes a recovery/administration owner and a hot keeper operator:

Push-Location contracts
forge create src/HyperRamArbitrage.sol:HyperRamArbitrage --rpc-url https://rpc.hyperliquid.xyz/evm --account KEYSTORE_ALIAS --broadcast --constructor-args OWNER_ADDRESS OPERATOR_ADDRESS
Pop-Location

After deployment, calculate the exact runtime hash and copy both values into .env:

$runtime = cast code EXECUTOR_ADDRESS --rpc-url https://rpc.hyperliquid.xyz/evm
cast keccak $runtime

Set the result as EXECUTOR_CODEHASH. Leave DRY_RUN=true for initial observation. Inject the dedicated operator key through a process secret rather than committing or sharing .env; use a multisig as owner where possible. The operator EOA needs HYPE for gas. prefunded mode also needs RAM in the executor; flash mode borrows RAM from the fixed V3 pool but only works when its flash fee still leaves a profit. Realized RAM stays in the executor. To withdraw it, the owner must call setPaused(true), call rescueToken(RAM_ADDRESS, RECIPIENT, AMOUNT), and then call setPaused(false) if operation should resume.

The build is pinned to Solidity 0.8.24, optimizer enabled with 500 runs, and Cancun EVM settings in contracts/foundry.toml. The fixed addresses make this executor HyperEVM chain ID 999 only; it is not a generic arbitrage contract. Losing the owner key can permanently strand accumulated profit.

Limits and operational warning

HYPE_USD and RAM_USD_REFERENCE are operator-supplied references, not oracles. Both are blank in .env.example and mandatory for live mode. The V3 spot price must remain within MAX_PRICE_DEVIATION_BPS of the RAM reference. Gas protection and the final USD gate use the lower of spot/reference, then PRICE_HAIRCUT_BPS further inflates the RAM reserved for gas. This is deliberately conservative but not manipulation-proof: a spot pool and a stale/operator-chosen reference can both be wrong. A production deployment should replace this guard with a manipulation-resistant TWAP/oracle and a freshness check. MEV, state changes between preflight and inclusion, token upgrades, RPC faults, and executor bugs can still cause loss. Mainnet use requires independent contract review, tiny initial limits, a dedicated key, and monitoring.

See SECURITY.md for private vulnerability reporting. Do not publish private keys, seed phrases, or exploitable vulnerability details in an issue.

About

HyperEVM RAM/hyperRAM arbitrage keeper, Solidity executor, and Windows GUI

Topics

Resources

Security policy

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Used by

Contributors

Languages