Day 3: The $17 Wake-Up Call and First Demand Signals
2026-03-09 · MoneyMachine
Date: 2026-03-09 Author: Jeff (written with AI assistance) Phase: v3 Phase 1 — First Revenue
The Cost Explosion
We woke up to a $17.90 OpenRouter bill. For one day.
That’s $537/month projected. On a system that has generated exactly zero dollars in revenue. For context, our entire monthly budget is $1,000, and OpenRouter was supposed to be a rounding error — maybe $5-15/month for the lightweight agents.
The culprit: heartbeats. Every agent in OpenClaw gets periodic heartbeat messages — “hey, anything to report?” The default was every 15 minutes, and it was firing for all six agents. Revenue Ops and Domain Analyst, both running on DeepSeek v3.2 via OpenRouter, had absolutely nothing to do. No tasks queued, no data to process. But every 15 minutes, each one would wake up, read its full context window, think for a moment, and respond with some variation of “nothing to report.” Repeat that 96 times per day, per agent, with per-token billing, and you get a very expensive way to hear “nothing.”
The fix was straightforward: disable heartbeats for every agent except Adrian. Adrian runs on Codex 5.3 via ChatGPT Pro, which is a flat $200/month regardless of usage — zero marginal cost per heartbeat. He gets a 30-minute pulse. Everyone else (Scout, Builder, Marketer, Revenue Ops, Domain Analyst) gets triggered on-demand only, which is exactly how v3 was designed to work. We just hadn’t enforced it in the cron config.
Projected daily OpenRouter cost going forward: under $2. Lesson learned the expensive way.
EISDIR: Five Code Paths to Kill One Bug
This one has been haunting us since Day 1. Agents crash when they call read() on a directory path instead of a file. OpenClaw’s internals don’t handle the EISDIR error — the Node process just dies.
We thought we’d fixed it on Day 2 with patches to the minified dist bundles. We had not. There were five separate code paths where this could happen, spread across eight files. Every time we patched one and restarted, an agent would find another within minutes. Four iterations to find them all.
The final fix: catch EISDIR at every layer and return a directory listing instead of crashing. We wrapped it all into a reusable script at scripts/patch-openclaw-read.sh that re-applies the patches after OpenClaw updates — because npm update will wipe every one of them. This is the kind of infrastructure work that’s invisible when it works and catastrophic when it doesn’t.
Scout’s Data Pipeline: Decoupling Fetch from Analysis
Scout’s job is to find demand signals — people on Hacker News, Reddit, and forums saying “I wish X existed” or “I’d pay for Y.” The v3 plan had Scout doing this end-to-end as an agent: fetch data, parse it, score it.
Reality check: Scout runs on qwen3.5:35b via Ollama on the ThinkPad, accessed over Tailscale from the VPS. That’s 319ms of network latency per API call, plus model inference time, plus tool-call overhead. Multi-step agent workflows — fetch a page, parse JSON, fetch another page, score results — were timing out every single time.
The solution was to stop asking an LLM to do what a bash script does better. We split the pipeline:
- fetch-hn-signals.sh — a cron job (every 2h) that hits 14 HN Algolia API queries and dumps raw JSON to disk. No LLM involved. Fast, reliable, free.
- extract-hn-signals.py — a Python script that scores posts using keyword matching and heuristics. Again, no LLM. Runs in seconds.
- Scout (agent) — reserved for deeper analysis of pre-scored signals, where the LLM actually adds value.
First run pulled 52 demand signals from the last 7 days of HN alone. People asking for tools, complaining about existing solutions, describing workflows they’d pay to automate. That’s 52 opportunities sitting in a queue, waiting to be scored and prioritized by Adrian.
No LLM tokens were burned to find them.
Reddit: Blocked at the Gate
We tried to add Reddit scanning to the pipeline. Reddit’s public .json endpoints return 403 from our Contabo VPS — datacenter IPs are blocked for unauthenticated access. Submitted a Reddit API application for proper OAuth credentials. Also submitted a LemonSqueezy application for payment processing. Both pending.
Accounts and Tools
Progress on the operational side:
- Stripe: Done. Ready for SaaS payments when we have a product.
- Beehiiv: Done. “The Tool Drop” newsletter created, API key configured, publication ID saved. Email list infrastructure is ready.
- LemonSqueezy: Application submitted, pending approval. Needed for info product sales.
- Reddit API: Application submitted, pending approval. Needed for demand scanning.
- Tools config: Scout was missing
execandweb_fetchpermissions — only had read/write/edit. Addedexec,web_fetch,web_searchto the global tools.allow list. Agents can now actually run shell commands and fetch URLs.
Dashboard: Clean Slate for V3
Added a V3_PIVOT_TIME filter to the health scoring system. Everything before the v3 pivot (March 8) is excluded from health metrics. No more v2 error noise polluting the dashboard. Clean baseline for measuring whether the demand-driven approach actually works.
Day 3 by the Numbers
| Metric | Value |
|---|---|
| Revenue | $0 |
| OpenRouter spend (24h) | $17.90 (mistake — now fixed) |
| Projected daily cost (post-fix) | < $2 |
| EISDIR code paths patched | 5 across 8 files |
| HN demand signals captured | 52 |
| Accounts ready | 2 of 4 (Stripe, Beehiiv) |
| Accounts pending | 2 of 4 (LemonSqueezy, Reddit) |
What’s Next: Day 4+
- Adrian scores the 52 HN demand signals using the v3 scoring rubric
- First Go/No-Go decision on an info product
- Reddit API approval (hopefully) unlocks a much larger signal pool
- LemonSqueezy approval lets us actually sell things
- Builder starts on the first product once Adrian greenlights an opportunity
Three days in, we’ve spent $17.90 on nothing and found 52 potential somethings. The system is shifting from “agents doing busywork” to “agents waiting for real work.” That’s progress, even if the bank account doesn’t show it yet.