$ whoami — 八咫烏, the three-legged crow. gathers, guides, reports.
Every log, every project.
One live console.
Yatagarasu is a self-hosted, multi-tenant log aggregator. A fire-and-forget SDK ships your logs to TimescaleDB — search them, tail them live, chart them, get alerted, and let your AI agent debug them over MCP.
demo mode, fake data, zero signup — or self-host it in 4 commands.
1 core
entire stack runs on a 1 vCPU / 1.9 GB VPS
0 ELK
TimescaleDB tuned to ~350 MB, no Elasticsearch tax
6 tools
remote MCP server, read-only, fail-closed auth
1 req / 50 logs
buffered SDK — batch POST, never per-line
## the problem
You run five side projects on three boxes. When something breaks, the ritual begins: ssh into each one, grep through rotated files, correlate timestamps by hand, and hope the log you need wasn't already rotated away. Hosted log platforms fix this — for a monthly bill bigger than the VPS running your entire portfolio.
Yatagarasu is the third option: one hub you own, every project's logs in a single searchable, streamable, alertable console.
## features
info
Batch ingestion
The SDK buffers in memory and ships batched POSTs — flush by time or size, never one INSERT per log line. Built for a 1-core box.
info
Live tail, no WebSocket
SSE + Postgres LISTEN/NOTIFY stream every insert straight to the browser. tail -f for your whole portfolio, in a tab.
debug
Time-series native
TimescaleDB hypertables with continuous aggregates for charts, compression after 3 days, retention drop after 14. ~350 MB tuned.
warn
Alert rules
A worker evaluates rules on an interval — error spikes, silence, thresholds — and emails you through Resend before users notice.
debug
Multi-tenant by key
Per-project API keys with rate limiting. One hub, every side project, isolated streams.
error
AI-debuggable (MCP)
A remote MCP server with 6 read-only tools. Point Claude at production logs and ask "why did checkout fail at 3am?".
## how it works
- 01
Install the SDK
One dependency, published on npm. Works in any Node app.
- 02
Log like you always did
log.info / log.error with structured meta. Never throws, never blocks — buffer, retry, backoff, flush on shutdown.
- 03
Watch it flow
Open the console: grep, filter by level, tail live, chart volume, set alert rules. Done.
import { createLogger } from '@satakedev/yatagarasu'
const log = createLogger({
apiKey: process.env.YATAGARASU_KEY!,
project: 'my-app',
})
log.info('user logged in', { userId: 42 })
log.error('payment failed', { orderId, err })## mcp — your ai agent reads production
Paste one block into your Claude config and your agent can list projects, query logs, follow traces and summarize errors — read-only, owner-token auth, fail-closed when no token is set. "Why did checkout fail at 3am?" becomes a prompt, not an investigation.
- list_projectsenumerate tenants and their streams
- query_logssearch with filters, levels, time ranges
- get_metricsvolume and error-rate rollups
- get_traceevery line sharing a trace id
- get_log_contextthe lines around a suspect log
- summarize_errorsgrouped error digest for a window
{
"mcpServers": {
"yatagarasu": {
"type": "http",
"url": "https://yatagarasu.satake.dev/api/mcp",
"headers": { "Authorization": "Bearer <MCP_TOKEN>" }
}
}
}## architecture — built from scratch, on purpose
client apps (A, B, C) │ @satakedev/yatagarasu — buffered, fire-and-forget │ POST /api/ingest (Bearer <key>) ▼ Next.js API ── validate key → batch INSERT ▼ TimescaleDB (logs hypertable) ├─ continuous aggregates → charts ├─ compression >3d · retention >14d ├─ LISTEN/NOTIFY → SSE → live tail └─ worker → alert rules → email ▼ console: search · grep · tail -f · metrics · MCP
No ELK (Elasticsearch alone would eat the whole box). No ClickHouse (its merges would fight a single core). TimescaleDB gives hypertables, continuous aggregates, compression and retention — inside Postgres, in ~350 MB.
The classic pipeline — collect, store, index, analyze — implemented by hand: Next.js, Drizzle + raw SQL, SSE, Better Auth, Resend. Every trade-off documented in the repo.
$ tail -f your-entire-portfolio