Experiment A
Bolo's Fomo-feed experiment: pipeline state, the signal, wallets and behaviours worth following, the latency edge, what to run tonight.
A3-TAPE-DIAGNOSIS-2026-09-06.md · updated 06/09/2026 20:04:59Rook, 2026-09-06 20:25 Beirut. Read-only diagnosis for Bolo. Nothing under research/call-sourcing/ was edited, no process was started, stopped or signalled. Every number below cites its file.
TLDR
- Nothing is running. No
mark,crowd,joinorcollectprocess exists on the box (ps -eo pid,cmd | grep experiment-a, empty at 20:10). Last write todata/experiment-a/mark-state.jsonwas 19:29 Beirut.mark.lockandcrowd.lockare gone,collector.lockandjoin.lockare stale. Restart is step zero. - The tape leg is dead, not slow. All 6 files in
data/experiment-a/tapes/were written between 00:34 and 00:50 Beirut, by the build that preceded the currentscripts/mark-experiment-a.mjs(mtime 01:03). Since 01:03 the tape has made 3,269 attempts and 0 successes. - Root cause, one line:
research/smartmoney/rpc.mjs:50treats the node's ownlog query timed outas a transient error and burns ~64 s of retry beforegetLogsis allowed to split the range.mark-experiment-a.mjs:195kills the tape child at 15 s. On any busy pool the child can never reach the first split. It is killed, forever. - Head-of-line blocking makes it total.
mark-experiment-a.mjs:292takes.slice(0, 1): one tape per cycle, sorted bytapeThrough(0 for never-taped rows, stable sort). Two rows on one pool,alrt_1788637873065_466andalrt_1788637953286_478(both token0x275bd09e, pool0x6f5b061f), hold the head and have 1,525 and 1,518 attempts, 93% of all tape work. The other 197 candidates have never been attempted once. - The one
up60Atwe have is garbage.alrt_1788644433727_1896recordspeak60mPct: 6.713068891519107e+55because a swap drove the pool tosqrtPriceX96 = 4295128740(MIN_SQRT_PRICE + 1, a drained pool) andbuildCandidateTapehas no sanity clamp. - D4 is trending to kill on a leg that never ran. Counting
fomo-events-materialized.jsonlfirst-buys under 6 h withprovenBefore === false: 80 rows, of which 14 have a proven wallet within 15 min after. D4 count = 14 against a threshold of 30, and the +60% leg contributes 0. 80 rows are unmeasured on that leg. - The crowd worker is a different bug with the same shape.
crowd-experiment-a.mjs:65callsrpcLogs('eth_getLogs', ...)directly instead ofgetLogs(...), so it gets no adaptive splitting. Nine cells fail forever onlogs matched by query exceeds limit of 10000.
Evidence
The error counter reconciles exactly
data/experiment-a/mark-state.json: cycles 3428, errors 3281, tapes 25, lastError {"at":"2026-09-06T15:49:24.436Z","message":"fetch failed"}.
Summing tapeAttempts over data/experiment-a/marks.json: 3,269 across 9 rows. 3281 - 3269 = 12. So 12 of 3,281 errors are fetch failed (top-level throws from runMarkOnce, the only uncaught network call in it being ethPrice() against api.dexscreener.com, which is reachable now: HTTP 200, 31,778 bytes, 1.1 s). The remaining 3,269 are tape-child kills. The brief's fetch failed is a red herring; it is 0.4% of the errors.
Errors do not stop the cycle count because mark-experiment-a.mjs:258 does state.cycles++ and writes state before any network call, and the tape failure at line 295 is caught inline and never throws. Progress lines confirm the cadence: errors=3232 at 19:12 and errors=3276 at 19:27 in progress-experiment-a.md, 44 errors in 900 s, one per ~20 s, which is exactly one 15 s child kill plus the 5 s LOOP_MS. Every cycle for the last 19 hours has done one thing: kill one tape child.
The fetch, reproduced by hand
Row alrt_1788637873065_466, pool 0x6f5b061f24b34f0166c5c4c8c97d7ff4dc4634cc84975a7a1b989b15ee1bb194, observedBlock 55384286. Chain rate measured from two candidate rows 80 s apart (blocks 55384286 and 55385072) is 9.8 blocks/s, so one hour is about 35,300 blocks. One request each, against https://rpc.mainnet.chain.robinhood.com (the endpoint getLogs uses):
| range | blocks | wall | result |
|---|---|---|---|
| 55384286 to 55419586 (full hour) | 35,300 | 2.26 s | {"code":-32000,"message":"log query timed out"} |
| 55384286 to 55401936 (half) | 17,650 | 2.34 s | log query timed out |
| 55384286 to 55393111 (quarter) | 8,825 | 3.05 s | log query timed out |
| 55384286 to 55385389 | 1,103 | 2.20 s | 1,942 swap logs |
The endpoint is healthy. The range is too wide, and it says so. rpc.mjs:50 is if (e.rpc && !/timed out|timeout/i.test(e.message)) throw e, so log query timed out is not rethrown: it loops 8 times with backoff 500, 1000, 2000, 4000, 8000, 10000, 10000, 10000 ms, about 45.5 s of sleeping plus about 18 s of server time, roughly 64 s per level, before throwing rpcLogs failed after retries and letting getLogs (rpc.mjs:81) halve the range. Halved, it repeats. The first three levels of the tree alone cost 7 x 64 s. runTapeIsolated kills the child at 15 s. It cannot ever succeed on a busy pool.
Corroborating: the request rate matters too. Four probes at 1.4 rps returned Too Many Requests while the live follower was on the same endpoint. That is the README's 2 rps limit biting, and rpcLogs treats 429 as retryable as well.
25 tapes in state, 6 files, 5 rows
state.tapescounts successful child returns, not files. The retape gate (mark-experiment-a.mjs:291) re-runs a row every cycle whiletapeThrough < min(now, sourceTs + 60 min) - 30 s, andwriteTape(line 154) rewrites the whole file. 25 successes over 6 event ids is about 4 passes each.- All 6 files have mtimes 00:34 to 00:50; the script is 01:03. The current build has written zero tape files. All 5
tapePathmarks carrytapeThrough: 2026-09-05T21:46:27.331Z, the moment the old build stopped. - The sixth file,
3d7f43a7-85c4-43ea-a32e-32b40b110ebf.jsonl, belongs toalrt_1788643305005_1648, which istype: "thesis", not"buy". The current filter (line 253) excludes it, so no mark record points at it. It is an orphan from the pre-01:03 build. - What was different about the 5 that produced
peak60mPct: nothing about the rows, only the clock. They ran under the old build in a 16-minute window before the 15 s isolation was in place. Their pools were also quiet or short: the tapes are 10, 2, 6, 686, 8,121 and 8,243 lines.
The 5 values are 32.3, 12.46, 0, 3.73 and 6.713068891519107e+55. The last is alrt_1788644433727_1896, token 0x7cbecee5, and its tape's final row is sqrtPriceX96 = 4295128740. That is MIN_SQRT_PRICE + 1: the pool hit its price limit, i.e. it was drained. With tokenIs0 === false, buildCandidateTape:163 computes (baseline / sqrt) ** 2 = 6.7e53, times 100. It is the only up60At in the dataset and it is an artifact. n = 5 is an anecdote; n = 1 for the outcome that decides D4 is not evidence at all.
The crowd worker: different cause, same shape
crowd.json has 823 completed horizon cells and 9 failing cells, all with the same error: logs matched by query exceeds limit of 10000. Total attempts across all cells is 6,166, so 5,343 failures, which is exactly crowd-state.json errors. That counter is per task, not per cycle, so "5,343 of 5,486 cycles" reads worse than it is. But measurements sat at 823 at 18:54, 19:10 and 19:25: the crowd worker has also made zero progress for hours. One cell has 588 attempts. The cause is crowd-experiment-a.mjs:65, which calls rpcLogs('eth_getLogs', ...) directly rather than getLogs(filter, from, to), so it never splits; and dueCrowdHorizons (line 28) only stops on status terminal, which the catch at line 88 never sets, so a poison cell retries every 60 s forever and eats 9 of the 16 task slots per cycle. Same disease as the tape (no terminal state, no backpressure), different immediate trigger (the 10k log cap rather than the server-side range timeout).
What is actually available to backfill
From fomo-events-materialized.jsonl: 211 D3 candidates, and all 211 already have observedBlock, poolId and alertSqrtPriceX96 set, and all 211 have c0/c1 in tokens.json. The gate at line 291 is not the blocker; nothing is missing from the inputs. All 211 first hours are fully in the past. The 211 rows sit on only 21 distinct pools and 29 merged first-hour block windows: 1,487,149 union blocks against 7,444,080 if taped per event, an 80% saving from keying the tape on the pool window instead of the event id.
The fix
Ordered. Steps 1 to 3 are what make the leg run at all; 4 to 6 are what make the number trustworthy.
- Restart the four workers. Clear the stale
collector.lockandjoin.lockfirst (acquireSingletonfails closed), then start collect, join, crowd, mark. Nothing else in this list matters until this is done. - Do not fix
rpc.mjs. It is shared with the live watchtower and smartmoney lanes and D6 keeps Bolo insideresearch/call-sourcing/. Instead add a localtapeGetLogs(filter, from, to)inmark-experiment-a.mjsthat never issues a wide query: fixed 1,000-block chunks, sequential, at most 2 requests per second, halving a chunk once onexceeds limitand rethrowing on anything else. Measured: 1,103 blocks returns 1,942 logs in 2.2 s on the busiest candidate pool. Replace thegetLogs(...)call at line 159 with it. - Kill the head-of-line block. In
runMarkOnce(line 291): sort the tape queue bytapeAttemptsascending, thentapeThrough, so a failing row can never re-take the head; and at line 295 settapeStatus: 'terminal'after 5 attempts, excluded from the queue and reported in the progress line astapeTerminal=N. RaiserunTapeIsolated'stimeoutMsfrom 15,000 to 180,000. Apply the identical terminal rule todueCrowdHorizonsincrowd-experiment-a.mjs:28, and change line 65 togetLogs(filter, from, to). That one word is the whole crowd fix. - Key the tape by pool window, not event id.
tapes/<poolId>-<startBlock>.jsonl, one per merged window; each event reads its own offset. 29 fetches instead of 211. - Stop paying for per-swap timestamps.
attachExactBlockTimes(crowd-experiment-a.mjs:42) fetches a header for every distinct swap block, 100 per batch.peak60mPctis a maximum over the window and needs no time axis at all. Fetch headers only for the window's two endpoints, the peak block and the first block crossing +60%: about 4 per window, about 120 total, on the fast lane. Today's design would need roughly 600 batched calls for the same answer. Also make a nulltsa hard error rather than a silent drop:buildCandidateTape:165filters onx.ts >= startMs, andnull >= startMsis false, so a partially failed batch silently deletes swaps. - Clamp the price. In
buildCandidateTape, reject any point withsqrtPriceX96 <= 4295128739 + 16or>= 1461446703485210103287273052203988822378723970342 - 16and recordpoolDrained: truewithpricePct: null. Flag anypeak60mPctabove 100,000% asimplausibleand exclude it from the D4 count. WiresamplePeak/updatePeak(lines 145 and 209) intorunMarkOnceor delete them: they are dead code today,state.peakOpenis always 0, and the tape is a single point of failure with no fallback.
Backfill cost against the README budget
The unit of work is 29 pool-hour windows, not 211 events. Per-pool swap density was probed once each over 300 blocks at the alert (analysis-2026-09-06/data/a3/pool-swap-rates.json, 20 of 21 pools returned, one hit a 429): 0 to 1,798 logs per 300 blocks, median 240. Extrapolating the alert-moment rate to a full hour gives 855k logs, but that overstates badly: the same probe says pool 0x1badd61a should hold 106,606 logs in its first hour while its actual tape holds 8,243 points over the first 22 minutes, a decay of about 5x. A defensible range is 100k to 250k swap logs across all 29 windows.
eth_getLogs, public RPC at 2 rps: chunking at 1,000 blocks costs 36 calls per busy window and 1 to 4 per quiet one. Expect 220 to 350 calls, about 3 minutes of pacing and 10 to 15 minutes of wall clock for all 211 candidates. Within the README's 2 rps rule, but it is the endpoint the live follower shares, so run it as one sequential process and watch for 429s.eth_getBlockByNumber: about 120 calls on the fast lane under step 5, versus roughly 60,000 block headers under the current per-swap design.- Alchemy: zero. No
eth_getLogson Alchemy, per README rule 2. Blockscout: zero.
Cheaper still, and worth it if the 2 rps lane feels tight against the follower: getLogsBM in research/smartmoney/rpc.mjs:122 serves eth_getLogs from rpc-robinhood.blockmachine.io in 9,999-block chunks on its own lane, which would cut the 29 windows to 149 chunks on a host the follower does not touch. That endpoint is not in the README's budget table, so it needs Thomas or Rook to bless it before use.
What this decides
D4 is counted at 23:00 tonight. Right now the count is 14 of 30, from 80 first-buys with no proven wallet before them, and the +60% leg contributes 0 rows out of 80 unmeasured. A kill taken tonight would be a kill on a leg that has never run for a single candidate. Steps 1 to 3 plus the backfill are a 10 to 15 minute job on the RPC and should be finished before the count is taken, or the count should be deferred and the deferral written into the freeze file as a coverage failure rather than a population result.
Sources
research/call-sourcing/scripts/mark-experiment-a.mjslines 154, 156 to 175, 192 to 200, 251 to 310research/call-sourcing/scripts/crowd-experiment-a.mjslines 27 to 29, 42 to 48, 62 to 71, 86 to 90research/smartmoney/rpc.mjslines 40 to 58 (rpcLogs, guard at 50), 81 to 95 (getLogs), 122 to 131 (getLogsBM)research/call-sourcing/data/experiment-a/:mark-state.json,crowd-state.json,marks.json(tapeAttempts,tapeError,peak60mPct,up60At,tapePath,tapeThrough),crowd.json(crowd<H>sError,crowd<H>sAttempts),fomo-events-materialized.jsonl(observedBlock,poolId,alertSqrtPriceX96,provenBefore,provenAfterSec,ageAtAlertSec,mcapAtAlert),tokens.json,tapes/*.jsonlresearch/call-sourcing/progress-experiment-a.mdlines for 18:44 to 19:27research/call-sourcing/EXPERIMENT-A-ORDERS-2026-09-06.mdsections 2 (D2, D3, D4) and 3 (steps 3 and 4)- Live probes 20:03 to 20:16 Beirut against
https://rpc.mainnet.chain.robinhood.comandhttps://api.dexscreener.com, raw per-pool result inanalysis-2026-09-06/data/a3/pool-swap-rates.json
/home/botbox/.openclaw/workspace/projects/crypto-2026-09/research/call-sourcing/EXPERIMENT-A-ORDERS-2026-09-06-EVENING.md · updated 06/09/2026 20:57:00Rook, 2026-09-06 21:00 Beirut. I lead the experiment. This file supersedes the night-one orders (EXPERIMENT-A-ORDERS-2026-09-06.md) where they conflict and stands on the A3 diagnosis (analysis-2026-09-06/A3-TAPE-DIAGNOSIS-2026-09-06.md), which cites every number. Bolo writes only under research/call-sourcing/. Nothing under executor/, watchtower/, data/executor/, data/watchtower/, services, crontab or git is touched. research/smartmoney/rpc.mjs is shared with live lanes and is not edited.
The one decision on the table tonight
D4 (the day-one population kill) is deferred, not taken, at 23:00. The kill rule from night-one orders counts young first-buys with no proven wallet before them that either had a proven wallet within 15 min after or printed +60% within 60 min. The +60% half of that rule has never produced a single measurement: the tape leg made 3,269 attempts and 0 successes since the 01:03 build. The count right now is 14 of 30 on the lead-lag half alone, with 80 rows unmeasured on the +60% leg.
Killing tonight would close the experiment on a leg that never ran. That is not the coverage result D4 was written to protect against; it is an instrumentation failure wearing a population result's clothes.
So: at 23:00, write the deferral into the freeze file as a coverage failure, not a population verdict. Record the 14-of-30 lead-lag count as-is, mark the +60% leg uninstrumented, and set the real kill decision for after the backfill lands (target: before Monday morning). The clock does not reset (D1 stands); we are extending only the measurement, not the window.
Bolo, in this order
Steps 1 to 3 make the leg run at all. Steps 4 to 6 make the number trustworthy. All of this lives under research/call-sourcing/.
Step 1. Restart the four workers. Nothing else matters until this is done. Clear the stale data/experiment-a/collector.lock and join.lock first (acquireSingleton fails closed), then start collect, join, crowd, mark. mark.lock and crowd.lock are already gone. Confirm with a progress line inside 5 minutes.
Step 2. Do not touch rpc.mjs. It is shared with the live watchtower and smartmoney lanes and D6 keeps you inside research/call-sourcing/. Instead add a local tapeGetLogs(filter, from, to) inside scripts/mark-experiment-a.mjs that never issues a wide query: fixed 1,000-block chunks, sequential, at most 2 requests per second, halving a chunk once on exceeds limit and rethrowing on anything else. Measured on the busiest candidate pool: 1,103 blocks returns 1,942 logs in 2.2 s. Replace the getLogs(...) call at line 159 with it.
Step 3. Kill the head-of-line block and add a terminal state. In runMarkOnce (line 291): sort the tape queue by tapeAttempts ascending, then tapeThrough, so a failing row can never re-take the head. At line 295, set tapeStatus: 'terminal' after 5 attempts, exclude it from the queue, and report it in the progress line as tapeTerminal=N. Raise runTapeIsolated's timeoutMs from 15,000 to 180,000. Apply the identical terminal rule to dueCrowdHorizons in crowd-experiment-a.mjs:28, and change line 65 from rpcLogs('eth_getLogs', ...) to getLogs(filter, from, to). That one word is the whole crowd fix.
Step 4. Key the tape by pool window, not event id. tapes/<poolId>-<startBlock>.jsonl, one file per merged first-hour window; each event reads its own offset. The 211 D3 candidates sit on only 21 distinct pools and 29 merged windows, so this is 29 fetches instead of 211, an 80% saving in union blocks.
Step 5. Stop paying for per-swap timestamps. peak60mPct is a maximum over the window and needs no time axis. Fetch block headers only for the window's two endpoints, the peak block and the first block crossing +60%, about 4 per window and ~120 total, on the fast lane. Also make a null ts a hard error rather than a silent drop: buildCandidateTape:165 filters on x.ts >= startMs, and null >= startMs is false, so a partially failed batch silently deletes swaps.
Step 6. Clamp the price. In buildCandidateTape, reject any point with sqrtPriceX96 <= 4295128739 + 16 or >= 1461446703485210103287273052203988822378723970342 - 16 and record poolDrained: true with pricePct: null. Flag any peak60mPct above 100,000% as implausible and exclude it from the D4 count. Wire samplePeak/updatePeak (lines 145 and 209) into runMarkOnce or delete them: they are dead code today.
Backfill and budget
The unit of work is 29 pool-hour windows, not 211 events. Expect 100k to 250k swap logs across all 29 windows.
eth_getLogs, public RPC at 2 rps: ~220 to 350 calls, about 3 minutes of pacing and 10 to 15 minutes of wall clock for all 211 candidates. Within the README's 2 rps rule, but it is the endpoint the live follower shares, so run it as one sequential process and watch for 429s. The live watchtower is already seeing intermittent 429s on this endpoint tonight; do not run the backfill and a burst of live detection into the same rate ceiling.eth_getBlockByNumber: ~120 calls on the fast lane under step 5.- Alchemy and Blockscout: zero
eth_getLogs, per README rule 2.
Blessed alternative if the 2 rps lane feels tight against the follower: getLogsBM in research/smartmoney/rpc.mjs:122 serves eth_getLogs from rpc-robinhood.blockmachine.io in 9,999-block chunks on its own lane the follower does not touch, cutting the 29 windows to 149 chunks. Rook blesses its use for the Experiment A backfill only, read-only, because it removes contention with live money on the shared RPC. Do not add it to any live lane.
What stays from night-one orders
D1 (clock does not reset), D2 (young = under 6h with a known launch time), D3 (quote budget to the candidate population only), D5 (repair scope) and D6 (kickoff non-negotiables, Bolo confined to research/call-sourcing/) all stand unchanged. Only D4's timing moves, and only because its instrument was never live.
Sources
analysis-2026-09-06/A3-TAPE-DIAGNOSIS-2026-09-06.md(full evidence, live probes 20:03 to 20:16 Beirut)EXPERIMENT-A-ORDERS-2026-09-06.mdsections 2 (D1 to D6) and 3 (steps 1 to 4)scripts/mark-experiment-a.mjslines 154, 159, 192 to 200, 251 to 310;scripts/crowd-experiment-a.mjslines 28, 42 to 48, 65, 86 to 90data/experiment-a/:mark-state.json,crowd-state.json,marks.json,crowd.json,fomo-events-materialized.jsonl,tokens.json
REPORT-experiment-a.md · updated 06/09/2026 10:40:33Lane: Rook. Written: 2026-09-06, 10:30 to 11:00 Beirut (07:30 to 08:00Z).
Snapshot boundary: every number below is computed against the frozen copy at
analysis-2026-09-06/data/experiment-a/snap/ taken at 2026-09-06T07:30:19Z (snap/SNAPSHOT-AT.txt).
Bolo's live pipeline kept running past that point; nothing here reads or writes the live directory except read-only re-checks that are labelled as such.
Scorer boundary: --before 2026-09-06T07:33:12Z, explicit ISO. See section 3 for why --before now cannot be used.
TLDR
- The pipeline is healthy on capture and broken on outcomes. 7,040 rows, 0 holes, 0 collector errors, ingest lag 8.6 s median. But 148 of 184 candidates are marked, and only 5 of 185 marks have
peak60mPct, because the A3 tape worker is still stuck. Every path-dependent question in this brief is unanswerable as a result. - 144 marks sit on 14 tokens. Four tokens (LIGER 40, 🅿️ 31, UNIPCS 24, BELL 20) carry 115 of the 144. Every event-level cross-tab below is really about 14 observations. Nothing here is statistically real. Treat all of section 2 as hypothesis generation.
- The strongest event-level signals are token age under 15 min (n=14 marked, median mark60 -1.5%, 43% at or over +60%) and alert ticket at or over $10k (n=32, median -2.6%, 25% at or over +60%), against a baseline of median -44.8% and 19% at or over +60%. Both survive only because they select for the two good tokens.
- The 5.4 minute lead is a conditional number, not the population lead. Measured unconditionally against
feed.jsonlon the 55 tokens both feeds touched: Fomo is first on 45 of 55, median lead 38.2 min, but on tokens under 6 h old the median lead collapses to +13 s, and on tokens under 60 min old the proven wallets actually lead by 40 s. The Fomo edge is in stale mid-cap tokens, which are exactly the ones Gold v2 refuses. - On the 15 young tokens both feeds hit, Gold v2's own gates skipped 12 and let 3 through. Skip reasons: heat ceiling 7, mcap over $1M cap 4, age over 60 min 2, liquidity floor 1, band 1. The bottleneck is not detection, it is the universe.
- No scout survives the scorer. 516 young first-buys, 409 traders, 102 with any mark, and 0 eligible at
--min 2or higher. Seven pass at--min 1, which is one token each and is not a follow list. - The smartmoney cohort re-ranked at 8 or more entries gives 6 wallets that clear rug rate under 0.15, m60 hit at or over 50% and m60 median above 0:
bluntz_capital,NotARandomUser,macdegods,threem,econoar,FullPinkYak. Three of the 24 wallets with 8 or more entries are not inFOLLOW-LIST.json:ethersole,threem,macdegods. - D4 passes on a technicality. 34 events, 33 traders, but only 5 tokens, and 24 of 34 sit on PEZ and 🅿️. All 34 qualify through the
proven15mleg; 0 qualify through the +60%-in-60-min leg, because that leg needspeak60mPct, which the stuck tape worker has not produced. Judge D4 at 23:00 on token count, not event count.
1. Pipeline state now
Verified from the frozen files, not from Bolo's progress lines. Re-check commands in Sources.
| item | value | where from |
|---|---|---|
| raw rows / materialized rows | 7,047 / 7,040 | snap/fomo-events.jsonl, snap/fomo-events-materialized.jsonl |
| window | 2026-09-05T19:45:52Z to 2026-09-06T07:29:17Z (11.72 h) | min/max sourceTs |
| type mix | buy 3,221 · sell 3,225 · thesis 523 · alert 71 | Counter over type |
| distinct traders / buy traders | 2,038 / 1,280 | distinct trader |
| distinct tokens (events / tokens.json) | 200 / 194 | tokenAddress, snap/tokens.json |
| ingest lag median (all) | 8,746 ms, p90 14,867 | receivedAt - sourceTs |
| ingest lag excl. the backfill batch | 8,599 ms, n=6,920, p90 14,603, p99 16,487 | same, backfill batch dropped |
| ingest lag last 60 min | 8,022 ms, n=346 | same |
| holes / duplicate ids / collector errors | 0 / 0 / 0 | collector-state.json, id Counter |
| seq range / distinct | 1 to 7,471, 5,417 distinct | seq field |
sourceTs monotonic in file |
true | file order check |
rows with traderWallet / buys with wallet |
1,744 / 908 | materialized rows |
| handle to wallet map | 457 entries, 311 handles resolved | snap/handle-wallet.json |
| wallet confidences | unique-match 153 · ambiguous 117 · leaderboard 86 · known-agreement 55 · conflict 29 · intersection-match 13 · smartmoney 4 | same |
| D3 candidates | 184 (marks 184, crowd 181) | recomputed from rows, snap/marks.json, snap/crowd.json |
| entry status | complete 148 · missed 36 | entryStatus in marks |
| marks populated | mark15m 148 · mark60m 144 · mark240m 99 | marks |
| peak60mPct / up60At | 5 / 1 | marks. This is the blocker |
| tape status | 9 rows retry_at, 0 anything else. 1,693 total attempts |
marks |
| tape files on disk | 6 (data/experiment-a/tapes/) but mark-state.json claims tapes: 25 |
ls, mark-state.json |
| D4 population | 34 events, 33 traders, 5 tokens | recomputed, see section 1c |
| upstream count (Bolo's own) | 25, flat since 07:59 Beirut | progress-experiment-a.md |
1a. The A3 tape worker is still stuck, and it is the single biggest hole
mark-state.json at the snapshot: cycles 1840, errors 1692, lastProgressAt 07:20:21Z, lastRunAt 07:32:24Z, phase "tape:alrt_1788637873065_466". That is 92% of marker cycles ending in an error, and the phase is pinned to one alert.
Two alerts account for 1,467 of the 1,693 tape attempts:
| alert id | attempts | status |
|---|---|---|
alrt_1788637873065_466 |
736 | retry_at |
alrt_1788637953286_478 |
731 | retry_at |
alrt_1788639334049_675 |
104 | retry_at |
alrt_1788638831982_600 |
106 | retry_at |
| 5 others | 1 to 6 each | retry_at |
Every error is the same string: isolated tape worker failed: Command failed: node .../mark-experiment-a.mjs --tape-worker <id> 1788643281055 <end>. The child exits non-zero and the parent re-queues it with no attempt ceiling, so two dead alerts have consumed the whole tape budget for four hours. There is no terminal_no_route state on any tape row even though D5 pre-registered one.
Consequence: peak60mPct on 5 of 185 marks. No peak path, no drawdown path, no time-to-peak. That kills the Gold v2 ladder replay (section 5) and it kills the second leg of D4 (section 1c).
1b. Error trends, from Bolo's 15-minute progress lines
| worker | 07:59 | 10:17 to 10:20 | rate |
|---|---|---|---|
| joins-v3 errors | 1,428 | 2,220 | ~344/h, linear |
| crowd-v3 errors | 140 | 1,174 | ~456/h and accelerating (each 15 min block adds ~118, up from ~60) |
| marks-v3 errors | 1,255 | 1,657 | ~176/h, linear |
| collector errors / holes | 0 / 0 | 0 / 0 | flat |
quoteMisses is pinned at 36 (joins/marks) and 33 (crowd) and has not moved since 07:59, so the D3 quote gate is holding. walletResolved is pinned at 228 to 229 since 08:45, so handle-to-wallet resolution has stalled too.
1c. D4, both legs
D4 (ORDERS section 2): day-one first-buys that are young (under 6 h, known launch time), had no proven wallet before them, and either a proven wallet within 15 min after or +60% within 60 min. Kill if the count is under 30 or it spans fewer than 10 traders.
| leg | count |
|---|---|
| proven wallet within 15 min | 34 |
printed +60% within 60 min (peak60mPct >= 60 or up60At set) |
0 |
| union | 34 events, 33 traders, 5 tokens |
Token spread of the 34:
| token | events | distinct traders |
|---|---|---|
| PEZ | 13 | 13 |
| 🅿️ | 11 | 11 |
| RKST | 5 | 5 |
| UNIPCS | 4 | 4 |
| TEST | 1 | 1 |
Capped at 5 events per token, D4 falls to 20 events, 19 traders, which fails the count threshold and barely clears the trader threshold. The pre-registered rule counts events and traders and says nothing about tokens, so as written D4 passes. It passes because 24 of 34 rows are 24 different people piling into the same two tokens inside a few minutes. That is one observation of a crowd, twice, not 34 observations of an upstream population.
The +60% leg reads zero purely because of section 1a. If the tape worker were running, that leg would be the one that actually tests "the Fomo feed is upstream of price", and it is the one currently unmeasured.
2. The signal
Leakage boundary used: rows are only those with sourceTs before the snapshot at 07:30:19Z; marks were written by Bolo's marker at wall-clock times after each horizon elapsed (leakage-check.mjs verifies markedAt against the horizon, and it does not flag any mark). leakage-check.mjs returns FAIL on the materialized file, with exactly 2 problems, both receivedAt before sourceTs (alrt_1788645437839_2177 at -2,012 ms, alrt_1788645484433_2187 at -3,611 ms). Those are clock-skew rows in the ingest path, not forward-mark leakage. No duplicate ids, no negative provenAfterSec.
Outcome distributions (all marked candidates, net of the $50 executable quote both sides):
| mark | n | min | p10 | p25 | med | p75 | p90 | max | %>0 | %>=+20 | %>=+60 | %>=+100 | %<=-50 |
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| mark15m | 148 | -101.2 | -55.4 | -41.9 | -9.5 | 20.5 | 70.8 | 253.7 | 37 | 25 | 11 | 7 | 15 |
| mark60m | 144 | -101.4 | -90.1 | -66.4 | -44.8 | 28.5 | 117.1 | 304.4 | 29 | 27 | 19 | 14 | 47 |
| mark240m | 99 | -96.5 | -89.4 | -80.2 | -65.0 | -14.3 | 138.5 | 570.0 | 23 | 23 | 17 | 13 | 70 |
| mark0mNet (entry slip) | 148 | -99.9 | -17.1 | -11.5 | -7.8 | -5.7 | -3.4 | 1.2 | 2 | 0 | 0 | 0 | 3 |
Read: the median Fomo alert is down 9.5% at 15 min and 44.8% at 60 min after paying a median 7.8% round-trip cost to get in. The tail is real (19% clear +60% at 60 min) but the body is a bleed.
Cross-tabs, event level, mark60m. Every one of these is 14 tokens wearing 144 hats.
| cut | bucket | rows | marked | med mark60 | %>0 | %>=+60 |
|---|---|---|---|---|---|---|
| token age at alert | under 15 min | 20 | 14 | -1.5 | 43 | 43 |
| 15 to 30 min | 28 | 21 | -66.6 | 0 | 0 | |
| 30 to 60 min | 50 | 47 | -51.9 | 26 | 4 | |
| 1 to 3 h | 63 | 46 | -6.4 | 46 | 37 | |
| 3 to 6 h | 23 | 16 | -15.3 | 19 | 12 | |
| mcap at alert | 300k to 600k | 17 | 9 | -51.0 | 0 | 0 |
| 600k to 1.2M | 65 | 44 | -62.5 | 18 | 16 | |
| 1.2M to 3M | 102 | 91 | -13.0 | 37 | 22 | |
| alert ticket | $2k to $10k | 147 | 112 | -55.8 | 24 | 17 |
| $10k to $50k | 37 | 32 | -2.6 | 47 | 25 | |
| crowd, buyers in 30 s | 0 | 28 | 25 | -45.1 | 24 | 24 |
| 1 to 49 | 107 | 81 | -51.8 | 27 | 21 | |
| 50 to 149 | 43 | 36 | -31.1 | 33 | 8 | |
| 150 to 299 | 3 | 2 | 58.8 | 100 | 50 | |
| net quote flow, 30 s | under -$2k | 11 | 8 | 57.6 | 75 | 50 |
| -$2k to 0 | 14 | 7 | 26.9 | 71 | 14 | |
| $0 to $2k | 138 | 114 | -58.1 | 20 | 15 | |
| over $2k | 18 | 15 | 23.9 | 53 | 33 | |
| proven wallet before | no | 75 | 60 | -54.9 | 22 | 18 |
| yes | 109 | 84 | -38.9 | 35 | 19 | |
| proven wallet within 15 min | no | 48 | 28 | 88.7 | 71 | 61 |
| unknown | 81 | 68 | -66.1 | 6 | 3 | |
| yes | 55 | 48 | -12.9 | 38 | 17 | |
| execution impact | under 100 bps | 13 | 13 | -6.0 | 15 | 15 |
| 100 to 300 bps | 19 | 17 | -2.7 | 47 | 18 | |
| 300 bps or more | 116 | 114 | -55.0 | 28 | 19 |
Four things to say honestly about that table:
- Age under 15 min is the best cut and it is 7 tokens. All 14 marks come from 7 distinct tokens, and the 15-to-30 and 30-to-60 buckets directly beneath it are the worst two buckets in the table. A monotone age story does not exist here; what exists is that two of the seven very young tokens ran.
- Net quote flow is U-shaped, which is a measurement artefact, not an edge. The winning tails are outflow under -$2k (n=8) and inflow over $2k (n=15); the losing body is the near-zero bucket (n=114). Near-zero net flow almost certainly means "the crowd measurement found nothing", so this cut separates tokens with real order flow from tokens without, in both directions. Do not build a rule on it.
proven15m = falsebeatingproven15m = trueis a token effect, not an inversion. The 28 marks in thefalsebucket sit on UNIPCS and 🅿️. It says nothing about proven wallets.- Wallet confidence tracks nothing.
ambiguous(n=12) has the best median at +117 andunique-match(n=20) has -55.5. That is the concentration again, and it means resolution quality is not usable as a filter yet.
Token level, which is the only level with independent observations. 14 tokens.
| token | marked events | med mark60 | min | max | age at alert | mcap at alert |
|---|---|---|---|---|---|---|
UNIPCS 0x7df5daaf |
24 | +112.0 | -36.5 | 304.4 | 71.1 m | 606,824 |
🅿️ 0xe1e5f00a |
31 | +24.6 | -20.7 | 133.0 | 7.1 m | 880,274 |
hoodrat 0x275bd09e |
2 | -17.8 | -34.1 | -1.4 | 207.5 m | 811,466 |
MUPPETS 0x5e7516be |
2 | -36.1 | -60.8 | -11.4 | 153.8 m | 543,169 |
DUMBCRAYONEATER 0x13e2fb78 |
3 | -45.6 | -55.4 | -32.7 | 39.8 m | 542,334 |
HD 0x17c35105 |
2 | -45.7 | -51.8 | -39.7 | 240.1 m | 985,683 |
HODL 0x7cbecee5 |
1 | -56.3 | 85.2 m | 488,356 | ||
RWA 0x399bf176 |
1 | -58.1 | 182.3 m | 617,375 | ||
BELL 0x218d0dc5 |
20 | -60.2 | -91.6 | 130.9 | 10.1 m | 790,105 |
LIGER 0x6102d810 |
40 | -63.1 | -72.0 | -10.0 | 24.0 m | 452,382 |
p402 0xac9a8dc5 |
1 | -69.8 | 70.0 m | 743,617 | ||
GRACE 0xce221b17 |
12 | -91.4 | -93.7 | -75.3 | 70.2 m | 1,041,901 |
STOCKKIT 0x7161fc17 |
1 | -96.3 | 19.9 m | 2,432,533 | ||
SHARES 0x09b3d5a2 |
4 | -101.1 | -101.4 | -100.7 | 19.3 m | 535,203 |
Three of 14 tokens closed the 60-minute mark above zero. One cleared +60%. That is the whole signal, and n=14 tokens over 11.7 hours is not enough to reject or accept anything. Aggregated by token, no cut separates: youngest-age bucket under 15 min gives 2 tokens with a median-of-medians of -17.8 and 0% at or over +60; the buyers-30s and mcap cuts have 1 to 8 tokens per bucket. The only cut that survives at token level is proven15m (3 tokens with a proven wallet inside 15 min, 67% positive, versus 11 tokens without, 0% positive), which is small enough to be a coin flip and is also circular, since it uses the outcome feed as the predictor.
3. Wallets we could start following
3a. Experiment A scouts: the scorer returns nothing
scripts/score-scouts.mjs was run against the frozen materialized file.
--before now does not work. The script does Date.parse(opt('--before')), and Date.parse('now') is NaN, so BEFORE = NaN, every tsMs(r) < NaN is false and the run reports rowsBeforeBoundary: 0, boundary: null, traders: 0. That is a silent zero, not an error. The brief asked for --before now; I ran it, recorded the result, and then used an explicit ISO boundary. This is a bug worth fixing before the 23:00 scoring run, because the freeze at 23:59 would silently freeze an empty scout set.
With --before 2026-09-06T07:33:12Z:
--min |
inputRows | rowsBeforeBoundary | youngFirstBuys | traders | tradersWithMarks | eligible |
|---|---|---|---|---|---|---|
| 3 (default) | 7,040 | 7,040 | 516 | 409 | 102 | 0 |
| 2 | 7,040 | 7,040 | 516 | 409 | 102 | 0 |
| 1 | 7,040 | 7,040 | 516 | 409 | 102 | 7 |
Eligibility requires nScored >= min, mark60Median > 0, rugRate < 0.34, lateShare < 0.5. No trader in the experiment has two scored young first-buys with a positive median. The seven at --min 1:
| handle | n | tokens | lead med (s) | mark60 median | rug rate | pProven15m | crowd60 med | age med (min) | wallet |
|---|---|---|---|---|---|---|---|---|---|
| fmpumpguy | 1 | 1 | 549.8 | +135.5 | 0 | 1.0 | 51 | 91.1 | 0xb0e9dcce59a1… |
| massonlybug | 1 | 1 | 111.3 | +119.7 | 0 | 1.0 | 0 | 9.4 | unresolved |
| northking | 1 | 1 | 136.4 | +117.1 | 0 | 1.0 | 0 | 8.9 | unresolved |
| zackory | 1 | 1 | 154.9 | +68.8 | 0 | 1.0 | 0 | 8.6 | unresolved |
| dakram | 1 | 1 | 207.7 | +0.1 | 0 | 1.0 | 96 | 96.8 | 0xada5bb90d0de… |
| brezscales | 2 | 2 | 875.0 | +124.1 | 0 | 0.5 | 50 | 41.1 | unresolved |
| nftking15 | 1 | 1 | none | +37.3 | 0 | 0 | 18 | 334.9 | unresolved |
Do not follow any of these. Six of the seven have exactly one scored event, four have no resolved wallet, and fmpumpguy is already in FOLLOW-LIST.json as a proven wallet, so it is not a scout discovery at all. pUp60 is null on all seven, again because of the tape worker.
The wider scout table (young first-buys, no proven wallet before, proven within 15 min) shows the same shape: 25 handles with an upstream count of 1 or more, and only xfilesboy has 2. The lead times are noisy and short: skoqv 9 s, googoo22 28 s, dingalingts 56 s, Yoshinvests 58 s, up to macdegods at 1,211 s. Handles with 4 or more young first-buys: xfilesboy (n=4, 75% first, upstream 2, 1 mark at -36.5), Binkieee (n=4, 25% first, upstream 0, 2 marks median +44.2), frankdegods (n=5, 20% first, upstream 0, 1 mark at -51.0, and already on handlesDeny after last night's rugs).
Verdict on 3a: there is no scout list yet. Come back after the tape worker is fixed and 24 more hours have run.
3b. Smartmoney cohort, re-ranked for a follow decision
From snap/smartmoney.json (updatedAt 07:28:02Z, 40 wallet rows, 100 tracked). hit is the percentage of marks above zero (watchtower/smartmoney.mjs:180), not a count. 24 wallets have 8 or more entries.
| handle | entries | scored | rugs | rug rate | avg $ | m15 n/hit/med | m60 n/hit/med | m240 n/hit/med | h24 n/hit/med | in FOLLOW-LIST |
|---|---|---|---|---|---|---|---|---|---|---|
| bluntz_capital | 8 | 6 | 0 | 0.00 | 134,500 | 6/83/+36.4 | 6/67/+22.7 | 6/67/+14.7 | 5/40/-10.9 | yes |
| NotARandomUser | 9 | 9 | 0 | 0.00 | 104,222 | 9/44/-0.7 | 9/67/+8.4 | 9/44/-2.8 | 6/50/+92.4 | yes |
| macdegods | 8 | 8 | 0 | 0.00 | 6,750 | 8/88/+5.3 | 8/63/+18.8 | 8/38/-15.2 | 2/50/+50.0 | no |
| threem | 9 | 8 | 0 | 0.00 | 7,556 | 8/50/-0.2 | 8/63/+6.7 | 8/50/+2.1 | 2/50/+1.2 | no |
| facap | 10 | 9 | 2 | 0.20 | 27,400 | 9/44/-0.0 | 9/56/+11.7 | 9/33/-4.5 | 8/50/-17.6 | yes |
| econoar | 19 | 16 | 1 | 0.05 | 118,264 | 16/44/-1.5 | 15/53/+1.6 | 13/23/-13.2 | 12/33/-20.2 | yes |
| FartmanSacks | 10 | 8 | 2 | 0.20 | 49,400 | 8/25/-14.9 | 8/50/+5.1 | 8/50/+5.8 | 6/50/-9.1 | yes |
| FullPinkYak | 12 | 12 | 1 | 0.08 | 13,583 | 12/50/+2.9 | 12/50/+0.7 | 12/25/-7.5 | 9/22/-15.7 | yes |
| ethersole | 9 | 8 | 0 | 0.00 | 74,444 | 8/50/+0.2 | 8/50/-0.3 | 8/50/-3.2 | 7/57/+7.3 | no |
| SolSwizzle | 11 | 10 | 1 | 0.09 | 528,909 | 10/60/+1.0 | 10/50/-1.4 | 10/30/-11.0 | 8/13/-51.6 | yes |
| iruletrenches | 10 | 9 | 0 | 0.00 | 77,600 | 9/33/-2.4 | 9/44/-3.9 | 8/25/-9.1 | 6/67/+44.8 | yes |
| ericzhong | 8 | 7 | 2 | 0.25 | 4,875 | 7/43/-0.4 | 7/43/-16.6 | 6/33/-25.1 | 6/17/-45.5 | yes |
| TheHappySwan | 8 | 5 | 2 | 0.25 | 9,875 | 5/20/-26.1 | 5/40/-10.8 | 5/40/-20.5 | 5/40/-43.0 | yes |
| Binkieee | 17 | 17 | 4 | 0.24 | 8,000 | 17/41/-7.8 | 17/35/-16.0 | 15/40/-26.8 | 9/11/-53.8 | yes |
| Milliardi | 10 | 9 | 1 | 0.10 | 14,200 | 9/44/-1.6 | 9/33/-3.4 | 9/11/-23.6 | 5/20/-56.0 | yes |
| Aurelius0121 | 9 | 6 | 2 | 0.22 | 77,333 | 6/33/-7.5 | 6/33/-5.2 | 6/33/-32.5 | 5/40/-28.6 | yes |
| m0f0 | 9 | 9 | 1 | 0.11 | 212,667 | 9/44/-0.1 | 9/33/-25.6 | 9/11/-46.3 | 7/0/-44.9 | yes |
| seralberttrades | 11 | 10 | 3 | 0.27 | 9,545 | 10/50/+0.5 | 10/30/-8.6 | 10/40/-24.3 | 8/50/-10.1 | yes |
| fr3ak | 12 | 10 | 2 | 0.17 | 3,750 | 10/30/-14.5 | 10/30/-40.9 | 10/30/-49.8 | 9/33/-9.5 | yes |
| elliotrades | 9 | 7 | 2 | 0.22 | 12,444 | 7/43/-5.5 | 7/29/-10.1 | 7/29/-24.8 | 6/17/-38.2 | yes |
| frankdegods | 39 | 38 | 6 | 0.154 | 13,718 | 38/34/-4.9 | 38/29/-22.4 | 38/32/-19.9 | 24/33/-22.0 | yes |
| Rowdy | 26 | 23 | 6 | 0.23 | 11,077 | 23/26/-11.0 | 23/22/-21.8 | 22/27/-29.9 | 13/23/-33.7 | yes |
| 0xdedrater | 9 | 5 | 0 | 0.00 | 17,444 | 5/20/-6.8 | 5/20/-10.7 | 4/0/-17.3 | 4/0/-72.6 | yes |
| rasmr | 8 | 7 | 3 | 0.375 | 66,125 | 7/29/-2.2 | 7/14/-30.8 | 7/14/-30.2 | 3/33/-84.8 | yes |
All 24 are inside Gold v2's universe today in the sense that Gold v2 triggers on the first on-chain buy by any proven wallet and takes its cohort from FOLLOW-LIST.json. 21 of the 24 are in that file. ethersole, threem and macdegods are not, so Gold v2 does not currently see their buys at all. Two of those three (threem, macdegods) sit in the top 4 by m60 hit rate with zero rugs, which makes them the only actionable "add" on this page.
Who survives a 0.15 rug-rate ceiling (which is already live: universe.maxWalletRugRate: 0.15, minWalletEntriesForRugRate: 8, shipped this morning by the rug lane, fixes-2026-09-05/FIELDS.md):
- Survive at 8 or more entries:
bluntz_capital(0/8),NotARandomUser(0/9),macdegods(0/8),threem(0/9),econoar(1/19),FullPinkYak(1/12),ethersole(0/9),SolSwizzle(1/11),iruletrenches(0/10),Milliardi(1/10),m0f0(1/9),0xdedrater(0/9). 12 of 24. - Blocked by the ceiling:
facap(0.20),FartmanSacks(0.20),ericzhong(0.25),TheHappySwan(0.25),Binkieee(0.235),Aurelius0121(0.222),seralberttrades(0.273),fr3ak(0.167),elliotrades(0.222),frankdegods(0.154, just over),Rowdy(0.231),rasmr(0.375). 12 of 24.frankdegodsis also onhandlesDenyinexecutor/follower.json, so it is now blocked twice. - Wallets with fewer than 8 entries are not judged by the gate and pass. That includes
0xAvast(m60 5/60/+13.1),ogle(6/67/+12.1),BTCdayu(6/67/+8.6),brrrgrrrz,AvgJoesCrypto,Tsukikage,soby0x.soby0xat m60 5/80/+2.9 is the best hit rate on the whole board and has 6 entries.
The follow shortlist, wallets clearing rug rate under 0.15 and m60 hit at or over 50% and m60 median above zero:
| handle | entries | rugs | m60 | note |
|---|---|---|---|---|
| bluntz_capital | 8 | 0 | 6/67/+22.7 | avg ticket $134k, our $50 clip is invisible next to it |
| NotARandomUser | 9 | 0 | 9/67/+8.4 | best h24 on the board (+92.4) |
| macdegods | 8 | 0 | 8/63/+18.8 | not in FOLLOW-LIST, small ticket ($6.7k), best m15 hit at 88% |
| threem | 9 | 0 | 8/63/+6.7 | not in FOLLOW-LIST, small ticket ($7.6k) |
| econoar | 19 | 1 | 15/53/+1.6 | the deepest sample that stays positive |
| FullPinkYak | 12 | 1 | 12/50/+0.7 | marginal, median is inside the noise |
n is 6 to 19 marks per wallet. This is a shortlist, not a proof.
4. Behaviours worth following
Patterns, not people. Evaluated over all 3,221 Fomo buy rows, with the mark subset attached. provenIn5m is the fraction of rows where a proven wallet bought the same token within 5 minutes after; the unconditional base rates are 7.1% at 5 min and 14.8% at 15 min.
| # | behaviour | n rows | tokens | marked | med mark60 | %>=+60 | provenIn5m | detectable at signal time? |
|---|---|---|---|---|---|---|---|---|
| B0 | any Fomo buy (baseline) | 3,221 | 159 | 144 | -44.8 | 19% | 230 (7%) | yes |
| B1 | token age under 15 min | 168 | 7 | 14 | -1.5 | 43% | 22 (13%) | yes, needs the launchTs join |
| B2 | age under 15 min and mcap under $300k | 0 | 0 | 0 | n/a | n/a | 0 | partial, mcapAtAlert on 2,340 of 3,209 buys |
| B3 | age under 60 min and mcap under $1M | 38 | 7 | 25 | -63.0 | 8% | 8 (21%) | partial |
| B4 | first Fomo alert on the token, age under 6 h | 24 | 24 | 9 | -58.1 | 11% | 5 (21%) | yes |
| B5 | 3+ distinct Fomo traders on the token in the previous 10 min | 1,553 | 35 | 87 | -46.9 | 16% | 160 (10%) | yes, no chain call |
| B6 | 5+ distinct Fomo traders in the previous 10 min | 1,130 | 21 | 51 | -58.1 | 10% | 134 (12%) | yes, no chain call |
| B7 | B5 and age under 6 h | 661 | 13 | 87 | -46.9 | 16% | 82 (12%) | yes |
| B8 | ticket $10k or more and age under 6 h | 354 | 9 | 32 | -2.6 | 25% | 36 (10%) | yes |
| B9 | net quote flow over $2k in 30 s | 18 | 3 | 15 | +23.9 | 33% | 7 (39%) | yes, but 30 s late |
| B10 | 150+ independent buyers in 30 s | 3 | 2 | 2 | +58.8 | 50% | 1 (33%) | yes, but 30 s late |
| B11 | no proven wallet before, age under 6 h | 287 | 15 | 60 | -54.9 | 18% | 36 (13%) | yes |
| B12 | B11 and ticket $5k or more | 213 | 13 | 34 | -60.0 | 12% | 26 (12%) | yes |
Reading:
- The brief's example behaviour, B2 ("first Fomo alert on a token under 15 min old and under $300k, followed by a proven-wallet buy within 5 min"), has n = 0. Not a weak result: it never happened once in 11.7 hours. The Fomo feed's alerts on sub-15-minute tokens all landed at mcaps of $450k or above. That rule cannot be tested on this data and should be widened or dropped.
- B1 and B8 are the two candidates worth carrying forward. Both roughly double the proven-follow rate over baseline (13% and 10% versus 7.1%) and both lift the +60% rate (43% and 25% versus 19%). Both are computable from what we already log at the instant the alert arrives, no chain call, no 30-second wait. B1's n of 14 marks across 7 tokens is the whole caveat.
- Crowd-count behaviours (B5, B6, B7) are anti-signals. Requiring more Fomo traders makes the median outcome worse (-46.9 at 3+, -58.1 at 5+) while barely moving the proven-follow rate. The crowd arrives after the move, which matches the token table: LIGER had 40 marked events and a -63% median.
- B9 and B10 are the only cuts with a genuinely elevated proven-follow rate (39% and 33%), but they need a 30-second chain measurement, which is 30 seconds of the 8.6-second edge spent, and their n is 18 and 3.
- B11/B12 ("we saw it first") do not pay. Being upstream of the proven wallets is worth nothing at these medians: -54.9 and -60.0.
5. The latency edge
5a. What the lead actually is
REPORT-capture.md states a 5.4-minute median Fomo lead. That number is the median of provenAfterSec over the 23 D4 rows, and D4 conditions on a proven wallet arriving within 15 minutes. It is a truncated distribution bounded at 0 to 900 s, so 5.4 min is "given that a proven wallet showed up soon, it showed up 5.4 minutes later". It is correct as written and it is not the population lead.
Measured unconditionally against data/watchtower/feed.jsonl (1,421 proven-wallet rows, 200 of them in the Fomo window on 112 tokens):
| population | tokens in both feeds | Fomo first | median lead | median of positive leads |
|---|---|---|---|---|
| all overlapping tokens | 55 | 45 | +38.2 min | +55.1 min |
| tokens under 6 h old at the Fomo alert | 15 | 8 | +13 s | +39.1 min |
| tokens under 60 min old | 11 | 5 | -40 s (proven wallets first) | +4.7 min |
| age unknown or over 6 h | 40 | 37 | +52.9 min | +68.4 min |
Lead buckets across the 55: over 15 min 32 · negative 10 · under 60 s 8 · 1 to 5 min 3 · 5 to 15 min 2.
The Fomo feed's real lead lives entirely in old tokens. The top of the lead table is HOTDOG (+464 min, token age 72 h), PROLOGUE (+421 min, age 19 days), MOO (+372 min), CHROME (+314 min, age 45 h). On young tokens the two feeds are simultaneous, which makes sense: both are watching the same launches.
There are also 104 tokens the Fomo feed saw that the proven wallets never touched, and 57 the proven wallets touched that never appeared in the Fomo feed. The overlap is 55 of 216. These are largely different universes, not one leading the other.
5b. Where the edge actually is: Gold v2's own gates
Every one of the 15 young overlapping tokens carries a Gold verdict from feed.jsonl:
| token | lead (min) | Fomo trader | age at alert | proven handle | Gold verdict | live |
|---|---|---|---|---|---|---|
| POOH | -34.9 | tranquiloguey | 39.4 m | picadura | 1h run +2445%, over heat ceiling | skipped |
| HODL | -24.8 | Mikey__Mangia | -7.2 m | 0xdedrater | 1h run +866%, over heat ceiling | skipped |
| MUPPETS | -24.6 | econoar | 62.2 m | fr3ak | 1h run +222%, over heat ceiling | eligible |
| LIQLORACLE | -4.4 | figaro | 11.6 m | picadura | 1h run +298%, over heat ceiling | eligible |
| RSTR | -2.9 | MomoOnChain | 15.7 m | fr3ak | 1h run +633%, over heat ceiling | skipped |
| hoodrat | -0.8 | Clark10x | 4.6 m | fr3ak | 1h run +480%, over heat ceiling | eligible |
| LIGER | -0.7 | 0xscripting | 24.0 m | justtesting | liquidity $279, under the $25k floor | skipped |
| TEST | +0.2 | wwayfboss | 8.3 m | fr3ak | 1h run +1040%, over heat ceiling | skipped |
| 🅿️ | +4.2 | Gs97z | 7.1 m | 0xdedrater | band 1M to 3M, not in the allowed bands | skipped |
| RKST | +4.7 | FineTealToad | 55.5 m | frankdegods | mcap $5.1M over the $1.0M cap | skipped |
| UNIPCS | +38.2 | ResellCalendar | 62.1 m | frankdegods | mcap $3.5M over the $1.0M cap | skipped |
| PEZ | +40.0 | frankdegods | 0.8 m | paidinfullintel | mcap $9.2M over the $1.0M cap | skipped |
| Ponsan | +103.3 | ProphecyXBT | 149.2 m | 0xdedrater | mcap $6.2M over the $1.0M cap | skipped |
| DUMBCRAYONEATER | +105.5 | ocrxa | 39.8 m | 81_tom | age 145 m over the 60 m ceiling | skipped |
| FSD | +133.2 | GemsOnly | 166.3 m | soby0x | age 299 m over the 60 m ceiling | skipped |
Skip reasons: heat ceiling 7, mcap cap 4, age ceiling 2, liquidity floor 1, band 1. Three went eligible, and the three are exactly the ones whose 1-hour run was under the 500% ceiling Gold v2 now carries (MUPPETS +222%, LIQLORACLE +298%, hoodrat +480%). The verdict strings quote a +200% ceiling because they were written by the feed under the older config; the current universe.maxRunH1Pct is 500.
So the latency edge does not convert today. Even if a Fomo trigger were wired straight into the executor, 12 of 15 co-occurring young tokens would still be refused, and the refusals are dominated by the two gates that were both fitted on last week's tape: the heat ceiling and the $1M mcap cap. UNIPCS, the single best token in the whole experiment at +112% median over 24 marked events, is refused for mcap $3.5M.
5c. The replayed outcome distribution
Ticket $50, hold to the mark, marks already net of the executable quote both sides. netUsd is the mean outcome times the ticket times n, that is, what the book would have made or lost across every trigger it fired.
| trigger | signals | tokens | mark15m n / med / %>=+60 | mark60m n / med / mean / %>=+60 / %<=-50 | net $ at 60 m |
|---|---|---|---|---|---|
| T0 every Fomo buy | 3,221 | 159 | 148 / -9.5 / 11% | 144 / -44.8 / -10.8 / 19% / 47% | -779 |
| T1 age under 6 h | 868 | 24 | 148 / -9.5 / 11% | 144 / -44.8 / -10.8 / 19% / 47% | -779 |
| T2 age under 60 m | 405 | 14 | 82 / -7.1 / 13% | 82 / -59.6 / -33.4 / 10% / 57% | -1,368 |
| T3 age under 15 m | 168 | 7 | 14 / +16.9 / 36% | 14 / -1.5 / +28.0 / 43% / 21% | +196 |
| T4 age under 6 h and ticket $10k+ | 354 | 9 | 33 / +4.0 / 9% | 32 / -2.6 / +27.1 / 25% / 25% | +434 |
| T5 age under 6 h, no proven wallet before | 287 | 15 | 62 / -19.4 / 13% | 60 / -54.9 / -30.0 / 18% / 52% | -900 |
| T6 net quote flow over $2k in 30 s | 18 | 3 | 15 / +13.1 / 27% | 15 / +23.9 / +31.9 / 33% / 0% | +239 |
| T7 50 or more buyers in 30 s | 46 | 10 | 38 / -19.1 / 5% | 38 / -25.1 / -23.4 / 11% / 37% | -445 |
| T8 age under 6 h and impact under 300 bps | 32 | 6 | 32 / -7.7 / 12% | 30 / -4.3 / -4.2 / 17% / 23% | -63 |
| T9 age under 6 h and mcap $250k to $1M | 70 | 14 | 46 / -5.4 / 15% | 44 / -56.4 / -32.3 / 16% / 64% | -710 |
| T10 Gold-v2-like: age 2 to 60 m, mcap under $1M, no proven before | 15 | 5 | 14 / -12.4 / 14% | 14 / -74.9 / -48.7 / 14% / 71% | -341 |
With a 120-minute per-token cooldown applied (the same entry.cooldownMinPerToken Gold v2 uses), every book collapses to a handful of trades because there are only 14 marked tokens: T0 goes to 351 signals and 14 marked, median -53.6, net -208. T3 goes to a single marked trade. The cooldown is the honest view and it says the sample is 14 trades, not 3,221.
Three books are positive at 60 minutes (T3, T4, T6) and all three are positive because of UNIPCS and 🅿️. T10, the closest thing to a Fomo-triggered Gold v2, is the worst of the filtered books at -74.9% median with 71% of trades at or below -50%.
5d. What is missing for a Gold v2 ladder replay
A Gold v2 ladder replay is not computable from the marks on disk. The ladder is a path-dependent policy: exit.stopLossPct -45, exit.noProgressMin 30 at noProgressPct 10, clips at +60% (half) and +200% (a quarter), trailingStopPct 40 relative stepping to 25 after +200% is seen, timeStopMin 90, breakevenAfterClip. Evaluating it needs a price series between the entry and the exit. The marks are three point samples at 15, 60 and 240 minutes.
Precisely, the missing field is peak60mPct, which is set on 5 of 185 marks, and its companions up60At (1 of 185) and poolTick15m (2 of 185). The intended source is the per-alert tape under research/call-sourcing/data/experiment-a/tapes/, and there are 6 tape files for 148 complete entries. Without the tape there is no way to know whether a trade that shows -44.8% at 60 minutes touched +60% at minute 12 and would have clipped half the position, or whether it fell straight through the -45% stop at minute 3. Those two histories produce opposite books from the same mark.
Fix the tape worker and this section can be rerun properly. That is the one dependency.
6. What to run tonight
6a. The single unblocking change: the A3 tape worker
Highest value change on the whole page, and it is small:
- Cap tape attempts.
alrt_1788637873065_466has 736 attempts andalrt_1788637953286_478has 731. Add an attempt ceiling (5 is plenty) that moves a row toterminal_no_route, which D5 already pre-registered as one of the four legal mark states and which currently appears on zero rows. Two dead alerts have consumed 87% of the tape budget for four hours. - Surface the child's stderr. Every one of the 9 errors is the same truncated
Command failed: node ... --tape-worker <id> <from> <to>with no captured stderr, so nobody can tell whether this is an RPC problem, a pool problem or a decode problem. One line ofe.stderrin the catch is the whole diagnosis. - Reconcile the counter.
mark-state.jsonreportstapes: 25;tapes/holds 6 files. One of the two is lying, and the progress digest reads the counter.
Everything else on this page (the +60% D4 leg, pUp60 in the scorer, the ladder replay, peak-based exits) is downstream of these three.
6b. Two shadow sets to run on paper tonight
Both are expressible in the existing watchtower/rules-v2.json vocabulary. Neither is live, neither alerts, both are logSkips: true so the refusals are countable in the morning.
Set A, "Gold-wide". kind: "wallet". Tests section 5b directly: is Gold v2's universe, not its detection, what is costing us the Fomo-adjacent tokens? Identical to Gold v2 except three gates:
universe.maxMcapUsd 1000000 -> 4000000 (would admit UNIPCS $3.5M, RKST $5.1M stays out)
universe.bands + "1M to 3M" (would admit the 🅿️ skip)
universe.maxRunH1Pct 500 -> 1200 (would admit RSTR +633%, hoodrat +480%, TEST +1040%)
Everything else held: minAgeMin 2, maxAgeMin 60, minLiquidityUsd 25000, maxLiquidityUsd 400000, rugRatio {maxLiqToMcap 0.85, underAgeMin 60}, maxWalletRugRate 0.15, minWalletEntriesForRugRate 8, entry.maxOtherCohortWallets 1, entry.maxChasePct 25, entry.minBuyUsd 100, and the Gold v2 exit ladder unchanged. The feed.jsonl verdict string records only the first failing gate, so the exact number of extra entries this set would have taken on the 15 co-occurring tokens cannot be read off the table; what can be read is that 12 of the 15 refusals cite one of these three gates as the first failure. Reading it in the morning: if Gold-wide's paper median beats Gold v2's over the same night, the universe is the binding constraint and the mcap cap is the first thing to move.
Set B, "Fresh-flow". kind: "momentum". Tests B1 (age under 15 min) without needing a wallet trigger, because shadow.mjs already supports kind: "momentum" and fires it from the pair scan (evaluateMomentum, shadow.mjs:920), no new plumbing:
universe: { minAgeMin: 2, maxAgeMin: 15, minLiquidityUsd: 25000, maxMcapUsd: 1500000, quoteAllow: ["WETH","USDG"] }
entry: { minM5VolumeUsd: 15000, m5PaceX: 2.0, m5MovePctMin: 5, m5MovePctMax: 400,
minBuyShareM5: 0.60, maxAboveLowPct: 120, minHistSamples: 3, cooldownMinPerToken: 120 }
exit: Gold v2's ladder verbatim
The minBuyShareM5: 0.60 is the tuning lane's buys-to-sells idea in the one place it is already implemented. Known gap, say it out loud: momentum sets do not run rugRatioSkip() or walletRugRateSkip() because there is no wallet on the signal, so Set B has no rug gate beyond the liquidity floor. It must stay live: false until that is addressed. Given last night's ZEP/PEZZED/PEZ write-offs, that is not a formality.
6c. What the D4 kill decision at 23:00 should be judged on
The pre-registered rule (ORDERS D2/D4) is count 30 and traders 10, and it was written so it could not move. It should not move. But the count it produces should be reported next to what it is actually made of:
- Report the token count alongside the event count. Right now D4 reads 34 events / 33 traders / 5 tokens, with 24 of 34 on PEZ and 🅿️. Capped at 5 events per token it is 20 events / 19 traders, which fails. The freeze file should record both numbers, so that a later reader can see that D4 passed on a crowd rather than on a population.
- Report the leg split. 34 from
proven15m, 0 from the +60%-in-60-min leg, and the reason for the zero is the tape worker, not the market. A D4 that passes on one leg with the other leg instrumentally broken is a weaker pass than the rule text implies, and the freeze should say so. - Do not let
--before nowwrite the freeze.Date.parse('now')isNaNand the scorer silently returns zero traders and zero scouts (section 3a). At 23:00, pass an explicit ISO boundary. ConfirmrowsBeforeBoundaryis non-zero in the output before writing the freeze file, and note thatscore-scouts.mjsrefuses to overwrite an existing freeze (exit 3), which is correct and should not be worked around. - Do not treat "D4 passes" as "start following scouts." Section 3a is unambiguous: 0 eligible traders at
--min 2. Whatever D4 says, the day-two ticket rule has no roster to hand it. - Projection, for what it is worth: 2.9 D4 events per hour over 11.7 hours. If the rate holds to the 23:00 close the raw count lands near 70. The rate is not the question; the token spread is.
Sources
All computations against the frozen snapshot at analysis-2026-09-06/data/experiment-a/snap/, taken 2026-09-06T07:30:19Z.
| what | source |
|---|---|
| pipeline counts, lag, holes, ids, seq | snap/fomo-events.jsonl, snap/fomo-events-materialized.jsonl, snap/collector-state.json; script analysis-2026-09-06/data/experiment-a/q1.py |
| marks, entry status, tape status and attempts | snap/marks.json, live research/call-sourcing/data/experiment-a/mark-state.json (read-only), ls research/call-sourcing/data/experiment-a/tapes/ |
| outcome distributions and cross-tabs | q2.py, q2b.py over snap/; merge in merge.py |
| D4 recount, leg split, token spread, 5-per-token cap | q3.py and the D4 recount in this pass |
| scorer runs | node research/call-sourcing/scripts/score-scouts.mjs snap/fomo-events-materialized.jsonl --before now and --before 2026-09-06T07:33:12Z --min {3,2,1} |
| leakage verdict | node research/call-sourcing/scripts/leakage-check.mjs snap/fomo-events-materialized.jsonl -> FAIL, 2 problems, both receivedAt before sourceTs |
| smartmoney re-rank, rug rates, follow-list membership | snap/smartmoney.json (updatedAt 07:28:02Z), research/smartmoney/FOLLOW-LIST.json; output at analysis-2026-09-06/data/experiment-a/q3b-out.txt; hit definition at watchtower/smartmoney.mjs:180 |
| behaviours B0 to B12 | q4.py |
| lead/lag against the proven feed, Gold verdicts on overlapping tokens | snap/feed.jsonl, q5.py, q5b.py |
| replayed books T0 to T10 | q6replay.py (this pass) |
| Gold v2 live config | watchtower/rules-v2.json set "Gold v2", executor/follower.json |
| shadow set vocabulary | watchtower/shadow.mjs evaluateMomentum (line 920) and fireMomentum (line 1193), fixes-2026-09-05/FIELDS.md |
| pre-registered D1 to D6 | research/call-sourcing/EXPERIMENT-A-ORDERS-2026-09-06.md |
| the 5.4 minute figure being conditional | analysis-2026-09-06/REPORT-capture.md lines 18, 29, 148, 171, 203 |
| Bolo error trends and quote misses | research/call-sourcing/progress-experiment-a.md, 07:59 to 10:24 Beirut |
Not answered from disk: whether the tape worker's child process fails on RPC, pool state or decode. The error string is truncated at Command failed and no stderr is captured. Reproducing it would mean running mark-experiment-a.mjs --tape-worker, which is Bolo's process and out of scope for a read-only lane.
REPORT-capture.md · updated 06/09/2026 07:42:40Digest for Thomas 09:00
Experiment A, day one, hour 8.4 of 24 (20:05Z Sat to 04:27Z Sun).
Rate: 648 events/h, 297 buys/h, 5637 rows, 2586 buys, 1735 traders, ingest lag median 8.7 s.
Coverage by token age at alert (buys): under 15m 136 · 15 to 60m 174 · 1 to 6h 426 · 6 to 24h 229 · over 24h 1292 · unknown 329.
Candidates (D3, under 6h and mcap under $3M at alert): 139. Upstream (no proven wallet before, one after): 16.
Wallet resolution: 813 of 2586 buys carry a wallet, 31%, up from 12% at hour one.
Holes: 0. Quote misses: 36 of 139 candidates, 26%.
D4 count now: 23 young first-buys, 22 traders. Thresholds are under 30 or under 10 traders at Sun 23:00.
D4 trend: NOT trending to kill on the count (23 at hour 8.4 projects to about 66), and already clear on traders.
Caveat that decides it: the +60% leg of D4 has fired 0 times because peak60mPct exists on 5 rows of 5637.
The whole D4 count is the proven-within-15-min leg, and 13 of 23 sit on one token, PEZ, which then rugged.
Read: the Fomo feed is real but shallow. It leads our proven wallets by a median of 5.4 minutes, not hours.
Bigger hole: 10 of the 12 tokens that ran +100% overnight with no proven-wallet buy are not in the Fomo feed either.