About
Contract first. Metadata second. Guessing never.
VirgoGent is an evidence reader for NFTs on Robinhood Chain. It answers questions by making reads and showing them. When a read fails, the failure is the answer.
Philosophy
Most tools that talk about NFTs summarise. They take an indexer's view, a cached image, a marketplace's listing, and present the blend as fact. That blend has no provenance: you cannot tell which part came from the contract and which from a server that could answer differently tomorrow.
VirgoGent keeps the sources apart. The chain is one source and is labelled Onchain. The metadata host is a second source and is labelled External. Nothing is presented as more certain than the read that produced it, and nothing is filled in when a read fails.
It cannot tell you what it did not read.
Method
Questions are mapped to contract operations by keyword rules — a deterministic parser, not a model. The rule that fired is printed above every answer. Execution is then a fixed sequence: eth_blockNumber to pin the block, eth_getCode to confirm a contract exists, then the method itself as a plain eth_call.
| Phrase | Contract read | Meaning |
|---|---|---|
| who owns · owner · holder | ownerOf(uint256) | ERC-721 owner of a token id |
| token uri · points to · link | tokenURI(uint256) → uri(uint256) | The pointer the contract holds; uri() is tried when tokenURI returns nothing |
| metadata · attributes · image | tokenURI → guarded fetch | Follows the pointer through the resolver and parses the JSON |
| balance · how many | balanceOf(address) | Count of tokens an address holds |
| name · called | name() | Contract name (ERC-721 Metadata, optional) |
| symbol · ticker | symbol() | Contract symbol (optional) |
| supply · minted | totalSupply() | Optional in ERC-721; NOT OBSERVED when absent |
| erc721 · erc1155 · supports · standard | supportsInterface(bytes4) × 6 | ERC-165 checks: 0x80ac58cd, 0x5b5e139f, 0x780e9d63, 0xd9b67a26, 0x0e89341c, 0x01ffc9a7 |
| inspect · full · what is | all of the above | Contract identity, standard, and — with a token id — owner, URI and metadata |
Reads are pinned to the block observed at the start of the run so one evidence stack describes one moment. Owner reads are never cached: a block later, the answer may be different, and the evidence says which block it was true at.
Labels
- VERIFIED
- An eth_call returned data that decoded to the expected type, at a pinned block.
- OBSERVED
- A value was returned and recorded (used for URIs and interface checks).
- RETURNED
- Raw return data exists; shown in RAW MODE next to its decoding.
- REVERTED
- The contract reverted. The reason string, if any, is shown as-is.
- NOT OBSERVED
- The method returned no data, or a value could not be obtained. Nothing is substituted.
- UNAVAILABLE
- The RPC could not be reached or answered with an error.
- NOT READ
- The step was skipped because a prerequisite failed, or the question lacked an input.
- RESOLVED
- An external URI was fetched and parsed as a JSON object.
- UNRESOLVED
- The URI is known but its contents could not be retrieved.
- MALFORMED
- The host answered, but not with usable JSON.
- BLOCKED
- The resolver refused the request (unsupported scheme, private host, disallowed port).
There is no confidence percentage anywhere in VirgoGent. A number like that would need a methodology it does not have.
Resolver policy
A token URI is attacker-controlled input: whatever the contract returns, VirgoGent is asked to fetch. So the browser never requests it directly. The URI goes to a same-origin route that translates it, checks it, and fetches it with limits.
- Schemes followed: ipfs://, ar://, https://, http://, and data: (decoded inline, no request). Anything else is BLOCKED.
- IPFS paths are tried on each configured gateway in order: 4everland.io, gateway.pinata.cloud, ipfs.decentralized-content.com, dweb.link, ipfs.io. Every attempt is recorded.
- Refused: loopback, link-local, RFC 1918 and CGNAT ranges, cloud metadata endpoints, bare or internal hostnames, numeric-obfuscated hosts, credentials in URLs, unusual ports. Redirects are re-checked hop by hop, and the resolved address is checked again at connect time.
- Hard limits: per-request timeout, a total time budget per resolution, and a byte cap on the body. A body over the cap is reported as MALFORMED with the reason, not truncated silently.
- JSON is parsed strictly; HTML, empty bodies and arrays are reported as MALFORMED with the first bytes shown.
- Images declared by metadata go through the same guard with a media-only content-type allowlist.
What it will not do
Send a transaction
Only view calls are relayed. The RPC relay refuses everything else.
Show a global feed
There is no honest way to build one from a browser, so Activity is local.
Show a placeholder image
If the source declares no image, the panel says so.
Infer a standard
Without a supportsInterface answer, the standard is NOT OBSERVED.
Cache ownership
Owner reads are fresh every time; only resolved metadata is cached, briefly.
Score anything
No AI confidence, no rarity guesses, no volume figures.
Network
- Network
- Robinhood Chain
- Chain id
- 4663
- Native currency
- ETH
- RPC (configured)
- https://rpc.mainnet.chain.robinhood.com
- Browser path
- same-origin /api/rpc relay → configured RPC
- Wallet
- optional; EIP-6963 discovery; never required for reads
The RPC endpoint, explorer, IPFS gateways and limits are all environment variables; another provider can be substituted without a code change.
Disclosure
VirgoGent is an independent application that reads publicly available blockchain data. It is not affiliated with or endorsed by Robinhood. Nothing here is financial advice or a statement about the value of any token.
Updates: @virgogentrh on X ↗