Transparency
Open audit
Our own review of this site: what's in place, what's missing and what we're fixing next. It's public so you don't have to take our word for it. Secrets, keys and infrastructure internals are left out on purpose.
Review log
What the 22 September 2026 review turned up, and what we changed
Three passes: the HTTP layer, the application source and the launch path. Every finding is listed here, including the ones that happened to go in our favour. Nothing ever gets removed.
- Fixed
A launch could plant a script in its own links
A launch's X and website links were saved as free text and dropped straight into the href on the token page. A javascript: address would have run for anyone who opened that page.
The launch endpoint now only accepts http(s) URLs for the logo, X and website fields. The form checks them before the wallet signs, so nobody burns gas on a launch the site would reject, and the token page only renders a link that starts with http(s), no matter what the database holds.
- Fixed
The content security policy only covered framing
The policy blocked embedding in other sites and allowed everything else. Scripts and styles could load from any origin, and there was no Permissions-Policy at all.
Scripts and styles are locked to this origin (inline is still allowed, since Next itself needs it). Images may come from any HTTPS origin, because token logos and provider icons are hosted elsewhere. Plugins are blocked, forms can only post here, and camera, microphone, geolocation, payment and USB are all switched off.
- Fixed
Connecting a wallet asked a question it already knew the answer to
Every click on Connect opened a picker, even with only one of the two supported wallets installed, and the picker sniffed window objects that MetaMask and Phantom both spoof.
The site now asks each wagmi connector whether its provider is present. With exactly one wallet installed, the extension opens right away; with two or none, the picker shows up, and install and mobile deep links open in a new tab.
- Mitigated
The treasury isn't configured on this deployment yet
Until the operator sets it, the treasury address is the zero address. A launch made in that state would name nobody as fee recipient, and its 2% would be stuck for good.
The launch form won't submit while the treasury is unset, and it says why. Nothing can be launched from this site until the address and the keeper key are in place.
- Fixed
The root domain wasn't being served
www.walleai.ink was verified first. The bare domain had a CNAME at the zone apex, which the DNS standard discourages, so resolvers answered inconsistently and the certificate took longer to issue.
The certificate for walleai.ink is issued and the root now serves the site. An ALIAS record at the apex would still be cleaner than a CNAME, and that's the recommended change at the registrar.
Security
Nothing on the server can spend from a user's wallet. One key can spend the treasury, and the protocol underneath is unaudited.
B+- Pass
Access is a signature, not a session
Every write carries a wallet address, a timestamp and a signature over both. Signatures expire after ten minutes, and there's no cookie or session to steal. Unauthenticated calls to /api/me, /api/launch and the personality and memory endpoints get a 401.
- Pass
Only the deployer can register a launch
The launch endpoint reads the factory record from chain, checks the curve, the fee recipient and the deployer against it, and rejects anything that doesn't match. A request body can't claim a token it didn't launch.
- Pass
API keys are hashed
Keys are stored as SHA-256 with a short prefix so you can recognise them, and shown only once. Per-minute rate limits and daily caps in micro-USD limit how much any key or wallet can spend from the tank.
- Pass
Image uploads are signed, capped and sniffed
Uploading a token image takes a wallet signature, is limited to ten per minute per wallet and one megabyte each, and the file type is read from the file's own bytes, not from the request. The browser shrinks images to 512 px before sending.
- Pass
Operator routes need a secret
Cron, the tank adjustment and the spawn veto require CRON_SECRET; without it they return 401. The keeper's private key lives only in the server environment and never reaches the browser.
- Pass
Transport and browser hardening
HSTS with preload, X-Frame-Options DENY, nosniff, a strict referrer policy, a content security policy and a permissions policy go out with every response.
- Partial
Inline scripts are still allowed
The policy allows inline scripts because the framework emits them. A nonce-based policy needs middleware, and it's next on the list.
- Partial
One key spends the treasury, but the treasury stays small
The keeper is a spender, not an owner: it can claim fees and launch spawns, but it can't mint or touch locked liquidity. After every claim it forwards everything above a gas reserve to the owner's wallet, whose key is not on the server, so the key on the server never guards more than a few dollars. pons v2 itself has no third-party audit, and that's the biggest open risk.
Performance
Every public page is rendered on the server, and nothing in the request path waits long on a slow RPC.
A-- Pass
Server-rendered HTML
Home, markets, token and docs pages render on the server. Time to first byte on the live deployment is about a quarter of a second, and the home page weighs under 45 KB of HTML.
- Pass
Cached catalogue, bounded RPC
The model catalogue is cached in memory for ten minutes and in the database for an hour. Curve reads go through multicall with a timeout, and tables fall back to indexed numbers when the RPC is slow.
- Pass
Self-hosted fonts, code-drawn graphics
Instrument Sans and DM Mono are served from this origin with font-display swap. The hero chart, the background and the brand mark are drawn in code, not shipped as images.
- Partial
Third-party icons
Provider icons come from a favicon service. Caching a copy per provider would remove that dependency.
SEO and sharing
Titles, descriptions, a generated share image and a live sitemap on every route.
A- Pass
Metadata
Every page sets a title and inherits the site description from a single brand config. The Open Graph image is generated in code using the brand's own font.
- Pass
Per-token cards
Every token page builds its own title and description from the launch and uses the token logo as its share image.
- Pass
Sitemap and robots
The sitemap lists every public page plus one page per listed token, and it's rebuilt on request. robots lets crawlers into the site and keeps them out of the API and MCP.
- Pass
Canonical host
Canonical URLs point to walleai.ink, which is served with its own certificate; www.walleai.ink works too.
Accessibility
Semantic controls and tables, visible focus, and reduced motion respected. Small labels are the weak spot.
B+- Pass
Reduced motion
Under prefers-reduced-motion, the hero chart draws only its final frame and the background blobs stay still.
- Pass
Decorative graphics are hidden
The chart, the rails, the brand mark and token logos carry aria-hidden or empty alt text. Interactive elements are real buttons, links and inputs.
- Partial
Small mono labels
Labels are 11px uppercase mono at 7:1 contrast on the base, but panels lighten the background and long tables scroll sideways on phones. Nothing critical lives in labels alone.
Operations and reliability
The treasury is funded and the keeper is running. The model provider isn't configured yet, and topping it up is manual.
B-- Pass
Treasury and keeper key
Set. The keeper job confirmed its key matches the treasury address, and the form allows launches. The treasury holds ETH for gas.
- Gap
Model provider key
Chat returns a provider error until the OpenRouter key is set and topped up. The tank ledger can show money available while the provider says no; top-ups are manual.
- Pass
Scheduled jobs
A separate cron service runs the indexer, the keeper, payouts, predictions, diary entries and spawns every ten minutes. A missed tick delays work; it never loses it.
- Pass
Runs without infrastructure
Every database read copes with a missing database and returns empty, so the site renders before any infrastructure exists. Schema migrations run on every deploy and are idempotent.
Data correctness
Live numbers are read from the curve at request time; indexed numbers can lag and are labelled that way.
A-- Pass
Integer micro-USD everywhere
The tank is an append-only ledger of integers. Each claim records the ETH/USD rate it used; the display rounds, storage never does.
- Pass
Price and progress are live
Price, market cap and curve progress on token pages are read from the curve contract at request time, not from a snapshot.
- Partial
Volume and holders depend on the indexer
Swaps, 24h volume and holder counts are mirrored from chain logs by the scheduled job and can trail the chain by a few minutes.
- Pass
Answers are billed on reported usage
Costs use the provider's reported token counts, rounded up, so the ledger never under-bills.