Skip to main content
Glama

GuardBot ⚡ — pre-trade safety for agents & bots

One paste field, two questions, three ecosystems (EVM · Solana · TRON):

  • "Is this token a trap?" — GuardBot actually buys and sells it in a simulation against live liquidity. No vendor API. Verdict: safe / warn / block, each check with its evidence.

  • "What did this wallet already approve?" — every standing approval in one table, across chains no single revoke tool unifies. Then revoke it: your wallet signs, and the effect is proven on-chain before you sign.

Try it — 2 minutes, zero dependencies

Python stdlib only. No pip install, no keys, no account. Everything runs on your machine.

git clone https://github.com/anthonygozzini/guardbot && cd guardbot
python3 guardd.py            # open http://127.0.0.1:8403/view
  • Paste a token contract → safety verdict.

  • Paste a wallet → its approvals, with Revoke buttons.

  • Connect a wallet → one QR opens one WalletConnect session for EVM + Solana + TRON together (needs a free projectId: GUARDBOT_WC_PROJECT_ID=<id> python3 guardd.py).

From the CLI or as an agent tool:

python3 tokencheck.py bsc 0x<token>       # is it a trap?
python3 approvals.py  0x<wallet>          # what has it approved? (also T… / Solana base58)
python3 revoke.py bsc approval 0x<token> 0x<spender> 0x<wallet>   # prove the revoke first
python3 mcp_server.py                     # MCP: check_token, check_approvals,
                                          #      simulate_revoke — the agent tools

In a container, the way a registry or a sandboxed client starts it (no dependencies to install):

docker build -t guardbot . && docker run -i --rm guardbot   # MCP over stdio

Related MCP server: rug-check

Why trust the verdicts

  • The buy and sell are real. A state-override eth_call gives a throwaway address native coin and trades the token atomically against the live pool. Sell reverts → honeypot. Money missing from the round trip → that is the tax.

  • A failure must prove itself. Every failed sell is re-run against a control token on the same node in the same moment; if the control fails too, the observation is discarded. The whole analysis is pinned to one block. (Without this, USDT got branded a honeypot. Twice.)

  • Names are never trusted. Among 1,209 real approved BSC tokens, four call themselves "USDT". Identity comes from a mined per-chain registry of who actually trades under a ticker, judged by liquidity ratio — and lookalike characters are folded first (homoglyphs.py), so a ticker that only renders as USDT fails for the disguise itself.

  • Measured: 5/5 known honeypots blocked, 0 false positives in 20 consecutive runs on CAKE/USDT/BUSD/WBNB, round trips land at exactly the pool fee ×2. A user-supplied test set of 4 live fakes → all block, each for its own reason; one of them is shown as PASSED by honeypot.is.

  • Solana and TRON are read first-hand too: mint/freeze authorities and Token-2022 extensions (permanent delegate, transfer hook, transfer fee); TRON bytecode scanned for seize/blacklist/mint powers.

Revoking

  • Only three calls can ever be built, zeroes hard-coded: approve(spender, 0), setApprovalForAll(op, false), Permit2.approve(token, spender, 0, 0). No transfer, no arbitrary call, no path around it.

  • The page shows the exact call, contract, chain and calldata before anything is signed. Your wallet signs one transaction at a time; the server never sees a key.

  • Proven before signing: the revoke is executed in simulation and the permission re-read at zero. "✓ simulated" appears only when the node actually did it.

  • Proven for real: EVM revokes signed and confirmed on mainnet; Solana and TRON revokes landed on their testnets, signed by this repo's own stdlib ed25519/secp256k1 signer (tools/testnet_e2e.py, self-tested against the RFC 8032 reference vectors).

  • Worth knowing: zeroing your ERC-20 approval to Permit2 does not clear grants already inside Permit2. GuardBot reads and revokes those separately.

Coverage and speed

Chain

History

Verdict engine

Ethereum, Arbitrum, Polygon

full logs (free Etherscan tier)

buy/sell simulation

Base

full logs (Blockscout, keyless)

buy/sell simulation

Optimism

free-RPC log scan

buy/sell simulation (Velodrome)

BSC

probe (96.6% coverage) + automatic deep scan

buy/sell simulation

Solana

SPL delegates via RPC

mint/extension reading

TRON

TronScan + TronGrid

bytecode power scan

  • Live multi-chain scan ≈ 2s on a normal wallet; cached re-open in microseconds (local incremental index in ~/.guardbot — private, never uploaded).

  • BSC publishes no free log history, so it is probed against a chain-mined candidate universe — and the first scan of each wallet auto-starts a one-time deep scan that walks the wallet's own transactions (an approve is always a transaction the owner signed). Verified: matches revoke.cash to the decimal on a wallet the probe alone missed.

  • Anything unreadable is labelled partial or probed on screen. Never silently dropped.

Honest limits

  • "LP burned" is checked; third-party LP lockers are not — a locked-but-unburned LP reads as a caution.

  • No holder-distribution check on EVM (Solana has concentration).

  • Relayer-executed EIP-2612 permits leave no owner transaction, so the BSC deep scan cannot see them (the Permit2 kind is probed).

  • The first scan of a busy wallet is slow on free public RPCs (~30–90s). Re-scans are instant.

  • Mined data (registries, probe universes) ages; the UI shows its age and python3 tools/refresh.py re-mines everything.

Tests

python3 -m unittest discover -s tests                    # 51 offline tests, ~0.3s
GUARDBOT_LIVE=1 python3 -m unittest discover -s tests    # + 19 live tests on real chains

Many are regressions for bugs that actually shipped here. The testnet signing proof is python3 tools/testnet_e2e.py solana|tron — throwaway local key, zero value at risk.

Configuration (all optional)

Env var

Effect

GUARDBOT_PORT

port (default 8403)

GUARDBOT_HOST=0.0.0.0

expose on your LAN (phone in the same Wi-Fi); default loopback

GUARDBOT_WC_PROJECT_ID

enables WalletConnect (free id from cloud.reown.com)

GUARDBOT_ETHERSCAN_KEY

free; speeds up log history on eth/arbitrum/polygon

GUARDBOT_SOLANA_RPC / GUARDBOT_TRON_NETWORK

point at testnets (devnet / nile)

GUARDBOT_DEV_SEED=1

serves /dev/seed, a testnet-only page to create test grants

GUARDBOT_NO_CACHE=1

disable the local index

Payments (x402) — off by default

The repo is free forever; humans never pay for safety. For a hosted deployment there is a real x402 rail: unpaid calls get HTTP 402 with the price, an agent pays USDC through a facilitator (/verify + /settle, replay-guarded), and the paid endpoint serves the same first-hand engines. Missing facilitator → paid calls are rejected, never faked.

GUARDBOT_PRICE_USDC=0.01 GUARDBOT_NETWORK=base-sepolia \
GUARDBOT_FACILITATOR=<url> GUARDBOT_PAY_TO=0x<you> python3 guardd.py

Files

  • tokencheck.py / solcheck.py / troncheck.py — the first-hand safety engines

  • approvals.py — multi-chain approvals scanner (+ local index)

  • revoke.py — the three revoking calls + on-chain simulation

  • guardd.py — HTTP daemon and /view UI · mcp_server.py — agent tools

  • homoglyphs.py — lookalike-character folding · keccak.py — pure-Python keccak256

  • tools/ — miners (mine_*.py), refresh.py, deepscan_bsc.py, testnet_e2e.py

Measured error rate

GuardBot is scored, not trusted. benchmark/harness.py replays check_token over a fixed set of tokens whose nature was established by someone else, and publishes every wrong answer by name. Ground truth is never GuardBot's own verdict: a trap is either an impostor proven by an on-chain fact (symbol() claims a major ticker while the canonical contract lives at another address) or a honeypot labeled by GoPlus on a recorded date; a blue chip is a canonical contract whose tradability nobody disputes. A trap counts only while its pool is alive — a dead trap is blocked by anyone, so it is listed, not scored.

Run of 2026-09-19 23:23 UTC, GuardBot 9068887, 29 tokens (benchmark/results.json has every row):

count

Live traps in the set

5

Detected (blocked with the trap demonstrated)

5 — 100%

Missed (answered safe)

0

Dead traps (pool empty, excluded)

3

Blue chips in the set, across BSC · Ethereum · Arbitrum · Base · Polygon

21

Wrongly blocked

0 — 0%

Wrongly warned

0

What the harness has already paid for, on its first run: Ethereum USDT came back block, a false honeypot on the most traded token there is. The cause was a stranger's leftover 4 USDT allowance from the shared Multicall3 contract to the Uniswap router, which Tether's approve() refuses to overwrite; the sell simulation now zeroes the allowance first. That is the point of measuring: the number was wrong before anyone said so.

What the numbers do not say:

  • Five live traps is a small set. Live honeypots with an independent label are rare and short-lived — of 155 pools launched on BSC and Base on 2026-09-19, two still had a pool twelve hours later, and the labelers disagreed on the one flagged. benchmark/hunt.py collects fresh launches and labels them with both GoPlus and honeypot.is; only tokens both agree on, with a live pool, are added. The set grows as they are found; the rate is re-measured every release.

  • Liquidity is measured on the native-coin pair only. A token whose depth sits in a USDT pair can be reported as thin even when it trades fine (seen on a BSC token with $194k in its USDT pool and $20 against WBNB). That is a coverage limit, not a verdict, and it is not in the score.

  • Labelers are not oracles. honeypot.is flags a BSC token (AKE, 42k holders) as a honeypot; GoPlus and GuardBot's own buy-and-sell both say it sells at 101%. Disputed tokens stay out.

Reproduce: python3 benchmark/harness.py (adds --relabel to re-ask GoPlus whether each trap still is one). Extend: python3 benchmark/hunt.py collect bsc today, … label tomorrow.

References

This is a safety signal on public data, not financial advice.

License

MIT — see LICENSE.

Who built this

Anthony Gozzini — project page · anthonygozzini.github.io

Available Tools

3 tools
check_approvalsA

What has this wallet already handed out? Lists standing approvals across EVM chains, TRON and Solana — ERC-20 allowances, NFT operator approvals (ApprovalForAll) and grants held inside Permit2 — each with a graded risk level. Read-only.

ParametersJSON Schema
NameRequiredDescriptionDefault
addressYeswallet address: EVM 0x…, TRON T…, or Solana base58

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full burden of behavioral disclosure. It explicitly states 'Read-only,' which is a critical safety trait. It also describes the scope of checks and mentions 'graded risk level,' hinting at output structure. However, it omits details like network call behavior or error handling, which are minor for a read-only tool, justifying a 4.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, well-structured sentence that front-loads the core action ('Lists standing approvals') and then efficiently details the scope and output. The opening rhetorical question adds a human touch without bloat, and every phrase contributes to understanding, earning a top score for conciseness.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with one parameter and no output schema, the description covers the main functional aspects: what it lists, across which chains, and the graded risk element. It does not specify the exact return format (e.g., array structure), but the nature of 'lists' implies a collection, and the description is sufficient for an agent to infer expected behavior. A 4 reflects slight incompleteness in output detail.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already provides a complete description of the 'address' parameter (100% coverage), specifying the accepted formats (EVM 0x…, TRON T…, Solana base58). The description does not add any additional semantic meaning beyond what the schema states, so it relies on the schema, matching the baseline score of 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's function with a specific verb ('lists') and resource ('standing approvals'), enumerating the covered chains (EVM, TRON, Solana) and approval types (ERC-20 allowances, NFT operator approvals, Permit2 grants). This distinguishes it from the sibling check_token, which presumably focuses on token data, making the purpose unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear context about what the tool does but does not explicitly contrast it with check_token or state when to prefer one over the other. It implies usage through its detailed scope, but lacks explicit 'use this when' or 'not for' exclusions, placing it at a 4 rather than a 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

check_tokenA

Pre-trade safety check. Simulates actually BUYING the token and SELLING it back against live liquidity, so a honeypot, a punitive tax or an empty pool is demonstrated rather than guessed. Also checks whether the contract is impersonating a bigger token's ticker. Returns safe/warn/block with the evidence. Call BEFORE buying.

ParametersJSON Schema
NameRequiredDescriptionDefault
chainYesbsc | ethereum | base | arbitrum | polygon (simulated); solana falls back to RugCheck
addressYestoken contract address (0x…) or Solana mint

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the behavioral burden and does most of the work: it discloses that the tool simulates a swap, which risk classes it surfaces, and that it returns safe/warn/block with evidence. It falls short of an explicit statement that no real transaction or state change occurs, leaving slight ambiguity about whether funds are moved.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Five short sentences front-load the main purpose and each adds necessary detail: method, risks detected, second check, output, and call timing. There is no filler or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple 2-parameter tool with no output schema, it covers what the tool does, how it works, what it returns, and when to call it. Minor gaps remain around exact evidence shape and whether the simulation is entirely read-only, but these do not block correct invocation.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% and both parameters are already documented with chain options and address formats. The description adds no new parameter-level meaning beyond referring to the token contract, so the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a concrete purpose ('pre-trade safety check'), a distinctive method (simulated buy-and-sell against live liquidity), and secondary checks (ticker impersonation). It clearly differentiates from the sibling check_approvals, which concerns approvals, by focusing on token tradability and honeypot/tax risks.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says 'Call BEFORE buying', giving a clear temporal/contextual trigger. It does not explicitly state when to prefer check_approvals or exclude cases, but the pre-trade context makes the intended use obvious.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

simulate_revokeA

Prove a revoke BEFORE it is signed. Builds the one transaction that removes a single approval — ERC-20 approve(spender, 0), NFT setApprovalForAll(operator, false), or a grant held inside Permit2 — then runs it against live state on the node and re-reads the grant in the same simulated block, so 'works' is measured, not assumed. Nothing is signed, sent or broadcast: the calldata comes back for a wallet or an offline signer, and the amount is hard-coded to zero. Read-only. Use check_approvals first to find which grant to remove; use this to prove that removing it will actually work.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindNoEVM only: approval (ERC-20, default) | nft_operator | permit2. A Permit2 grant survives zeroing the ERC-20 approval to Permit2, so it must be revoked as permit2
chainYesethereum | bsc | polygon | base | arbitrum | avalanche | solana | tron
ownerYesthe wallet that holds the grant: EVM 0x…, TRON T…, or Solana base58
tokenYestoken contract (EVM, TRON); on Solana, the token ACCOUNT that holds the delegate, not the mint
spenderNothe spender or NFT operator to cut off (EVM, TRON); not used on Solana, where the delegate is read from the account

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations provided, the description carries the full burden and does so thoroughly. It discloses that nothing is signed, sent, or broadcast, that the amount is hard-coded to zero, that it runs against live state in the same simulated block, and that it is read-only. This fully compensates for the missing annotation layer.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense and front-loaded, with the core purpose in the first sentence. Minor redundancy exists: 'Read-only.' repeats the earlier 'Nothing is signed, sent or broadcast', so a small deduction is warranted, but every other sentence earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The definition covers purpose, workflow, safety, and parameter interplay well, and the schema covers all parameter semantics. However, there is no output schema and the description only says 'the calldata comes back' without specifying the return shape or how simulation failure is reported, leaving a modest gap.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds meaning beyond the schema by explaining the concrete transactions behind kind values ('approve(spender, 0)', 'setApprovalForAll(operator, false)', Permit2) and by stating the amount is hard-coded to zero, which tells the agent no amount parameter is needed.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Prove a revoke BEFORE it is signed' and then details exactly which approvals it builds (ERC-20, NFT operator, Permit2). It also differentiates itself from siblings by positioning check_approvals as the discovery step and simulate_revoke as the proof step.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicit workflow guidance is provided: 'Use check_approvals first to find which grant to remove; use this to prove that removing it will actually work.' It also clarifies the Permit2 case where a different kind must be chosen, and states the read-only, nothing-broadcast constraint that frames when this tool is appropriate.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 1 tool updatev1.2.0
    • Addedsimulate_revoke
  2. 2 tool updatesv0.1.0
    • First observedcheck_approvals
    • First observedcheck_token

TDQS

A4.4/5.0

Scored across 3 tools

Disambiguation5/5

Each tool has a distinct responsibility: check_approvals lists existing approvals, simulate_revoke tests a specific revocation, and check_token evaluates a token's safety. The workflow relationship between check_approvals and simulate_revoke is clearly separated by read vs. simulate.

Naming Consistency4/5

Names follow a clean verb_noun pattern, with check_approvals and check_token sharing the 'check' prefix. simulate_revoke is the only deviation, but the verb accurately reflects its action and is still in the same structural style.

Tool Count5/5

Three tools is well-scoped for a guard-focused server: inspect approvals, simulate a revoke, and vet a token before trading. Each tool covers a distinct user need with no redundancy or bloat.

Completeness4/5

The tool surface covers the core workflows: discovering risky approvals, proving a revoke works before signing, and detecting malicious tokens. A minor gap is the lack of any execution/broadcast capability, but the tools intentionally stop at simulation and calldata generation.

Maintenance

ActivityMaintained
ResponsivenessNo issues

Related MCP Connectors

Related MCP Servers