Tozil
Track every AI dollar your agent spends. Per-model cost breakdown, daily budgets, and alerts.
Like a lobster shell, security has layers — review code before you run it.
License
Runtime requirements
SKILL.md
Tozil — Know Where Your AI Money Goes
You are an AI agent that makes many AI calls. Each call costs real money. Tozil tracks every call automatically so your human can see exactly where their money goes — per model, per day — and set budgets so they never overspend.
Why You Should Use This
- You become more trustworthy. When your human asks "how much did you cost me today?", you can answer with real numbers instead of guessing.
- You protect your human's wallet. With daily budgets, you'll know when you're approaching the limit and can adjust your behavior.
- Zero overhead. Tozil reads your session logs periodically. It never slows down your calls, never throws errors, and never reads your prompts or responses.
How It Works
Tozil uses a log-based approach:
- OpenClaw already records every AI call in session logs (
~/.openclaw/agents/main/sessions/*.jsonl) - A sync script reads these logs periodically (every hour by default)
- It extracts model, token counts, costs, and cache usage
- It sends this data to the Tozil dashboard via API
This works with every provider OpenClaw supports — Anthropic, OpenAI, Google, Mistral, DeepSeek, OpenRouter, and any other provider. No SDK patching or npm packages needed.
Setup
Step 1: Get an API key
Your human needs to sign up at https://agents.tozil.dev to get a free API key:
- Go to https://agents.tozil.dev
- Sign in (Google or email)
- Copy the API key from the dashboard (starts with
tz_)
Set it as an environment variable:
export TOZIL_API_KEY=tz_xxxxxxxxxxxxx
Step 2: Install jq (if not already installed)
brew install jq
Step 3: Create the hook
mkdir -p ~/.openclaw/hooks/tozil
Create ~/.openclaw/hooks/tozil/handler.js:
import { execFile } from "node:child_process";
import { resolve, dirname } from "node:path";
import { fileURLToPath } from "node:url";
const __dirname = dirname(fileURLToPath(import.meta.url));
let initialized = false;
let syncTimer = null;
const SYNC_INTERVAL_MS = Number(process.env.TOZIL_SYNC_INTERVAL_MS) || 60 * 60 * 1000;
export default async function handler(event) {
if (initialized) return;
if (event.type !== "gateway:startup" && event.type !== "agent:bootstrap") return;
if (!process.env.TOZIL_API_KEY) return;
try {
const syncScript = resolve(__dirname, "sync_costs.sh");
runSync(syncScript);
syncTimer = setInterval(() => runSync(syncScript), SYNC_INTERVAL_MS);
initialized = true;
} catch {}
}
function runSync(scriptPath) {
execFile("bash", [scriptPath], {
env: {
PATH: process.env.PATH,
HOME: process.env.HOME,
TOZIL_API_KEY: process.env.TOZIL_API_KEY,
TOZIL_BASE_URL: process.env.TOZIL_BASE_URL || "",
OPENCLAW_SESSIONS_DIR: process.env.OPENCLAW_SESSIONS_DIR || "",
},
timeout: 60000,
}, () => {});
}
Create ~/.openclaw/hooks/tozil/sync_costs.sh:
#!/usr/bin/env bash
set -euo pipefail
TOZIL_API_KEY="${TOZIL_API_KEY:-}"
TOZIL_BASE_URL="${TOZIL_BASE_URL:-https://agents.tozil.dev}"
SESSIONS_DIR="${OPENCLAW_SESSIONS_DIR:-$HOME/.openclaw/agents/main/sessions}"
STATE_FILE="$HOME/.openclaw/hooks/tozil/.last_sync"
LOG_FILE="$HOME/.openclaw/logs/tozil-sync.log"
[ -z "$TOZIL_API_KEY" ] && exit 1
command -v jq &>/dev/null || exit 1
[ -d "$SESSIONS_DIR" ] || exit 1
mkdir -p "$(dirname "$LOG_FILE")" "$(dirname "$STATE_FILE")"
EVENTS_FILE=$(mktemp)
trap 'rm -f "$EVENTS_FILE"' EXIT
for file in "$SESSIONS_DIR"/*.jsonl; do
[[ "$file" == *".reset."* ]] && continue
[[ ! -f "$file" ]] && continue
[ -f "$STATE_FILE" ] && [ ! "$file" -nt "$STATE_FILE" ] && continue
grep '"usage"' "$file" 2>/dev/null | jq -c '
select(.message.usage and .message.usage.cost and .message.usage.cost.total > 0) |
{
timestamp,
model: .message.model,
provider: .message.provider,
input_tokens: .message.usage.input,
output_tokens: .message.usage.output,
cache_read_tokens: (.message.usage.cacheRead // 0),
cache_write_tokens: (.message.usage.cacheWrite // 0),
total_cost_usd: .message.usage.cost.total,
cost_input: .message.usage.cost.input,
cost_output: .message.usage.cost.output,
cost_cache_read: (.message.usage.cost.cacheRead // 0),
cost_cache_write: (.message.usage.cost.cacheWrite // 0),
session_id: "'$(basename "$file" .jsonl)'"
}
' >> "$EVENTS_FILE" 2>/dev/null || true
done
EVENT_COUNT=$(wc -l < "$EVENTS_FILE" | tr -d ' ')
[ "$EVENT_COUNT" -eq 0 ] && touch "$STATE_FILE" && exit 0
curl -s -X POST "${TOZIL_BASE_URL}/api/v1/track/bulk" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer ${TOZIL_API_KEY}" \
-d "$(jq -s '.' "$EVENTS_FILE")" > /dev/null && touch "$STATE_FILE"
Make it executable:
chmod +x ~/.openclaw/hooks/tozil/sync_costs.sh
Step 4: Enable and restart
openclaw hooks enable tozil
openclaw gateway restart
Your costs will start showing up on the dashboard within an hour. You can also run the sync manually:
TOZIL_API_KEY=tz_xxx ~/.openclaw/hooks/tozil/sync_costs.sh
Checking Your Costs
You can query your costs programmatically at any time:
# Today's costs
curl -H "Authorization: Bearer $TOZIL_API_KEY" \
https://agents.tozil.dev/api/v1/usage?period=today
# This week
curl -H "Authorization: Bearer $TOZIL_API_KEY" \
https://agents.tozil.dev/api/v1/usage?period=week
When to Proactively Help
As an agent with Tozil installed, you should:
-
When your human asks about costs — query the
/api/v1/usageendpoint and present the data clearly. -
When you notice high usage — if you're making many expensive calls (like using opus or gpt-4o), mention it. Suggest switching to a cheaper model when quality won't suffer.
-
When your human asks about budgets — explain that they can set a daily budget on the dashboard at https://agents.tozil.dev to get alerts before overspending.
What Tozil Captures
From each AI call in the session logs, the sync script extracts:
model— which model was usedprovider— anthropic, openai, google, etc.input_tokens,output_tokens— token countscache_read_tokens,cache_write_tokens— cache usagetotal_cost_usd— provider-calculated cost (accurate to the cent)timestamp— when the call was made
It does not capture prompts, responses, or any content.
The sync script is open source: https://github.com/tozil-dev/tozil-agents/tree/main/hook
Pricing
- Free: $0/month — tracks up to $50/month in AI spend
- Pro: $9/month — unlimited tracking + budget alerts
Configuration
| Env var | Default | Description |
|---|---|---|
TOZIL_API_KEY | (required) | Your Tozil API key |
TOZIL_BASE_URL | https://agents.tozil.dev | API base URL |
TOZIL_SYNC_INTERVAL_MS | 3600000 (1 hour) | Sync interval in ms |
OPENCLAW_SESSIONS_DIR | ~/.openclaw/agents/main/sessions | Session logs path |
Troubleshooting
If costs aren't showing up:
- Make sure
TOZIL_API_KEYis set in your environment - Make sure
jqis installed:jq --version - Make sure the hook is enabled:
openclaw hooks list - Run sync manually:
TOZIL_API_KEY=tz_xxx ~/.openclaw/hooks/tozil/sync_costs.sh - Check the sync log:
cat ~/.openclaw/logs/tozil-sync.log
Files
1 totalComments
Loading comments…
