⚙️ agent.yaml — the bot token and commands
O agent.yaml is the coach’s configuration file: it says which Telegram bot to use and which slash commands appear in the menu. The most important catch: the token no lives inside it. The file stores only the environment variable name that points to the token—the actual secret stays in ~/.env, outside git.
🟢 New here? Three terms before you continue
- agent.yaml — the coach’s "control panel" in text. You copy the
agent.yaml.exampleforagent.yamland edits it. - telegram_bot_token_env — instead of the raw token, it stores the variable NAME (e.g.:
HEALTH_BOT_TOKEN) that the agent reads from your~/.env. This way, the secret never ends up in the repository. - Slash command — a shortcut that starts with a “/” in Telegram (e.g.,
/checkin). Each one triggers a coach routine.
📋 Copy and adapt · goal: register the bot and declare the menu commands
# agent.yaml.example → copie para agent.yaml e edite
name: health-coach
# o bot NÃO guarda o token aqui — guarda o NOME da variável
# de ambiente que o agente lê do seu ~/.env (segredo fora do git)
telegram_bot_token_env: HEALTH_BOT_TOKEN
slash_commands:
- command: checkin
description: Revisão da manhã guiada pela recuperação
- command: today
description: O plano de hoje (treino, comida, café)
- command: sofar
description: O que você já registrou hoje
- command: newday
description: Fecha o dia e começa um novo
- command: supplements
description: Sua agenda de suplementos
- command: advice
description: Conselho com citações, reconciliado aos seus dados
Key concepts
The coach's control panel.
Keep the variable name, not the secret.
"/" shortcuts declared in the file.
Where the token actually lives.
📝 CLAUDE.md — the coach’s brain is your profile
O CLAUDE.md is the document the coach reads to learn who you are. That’s where “generic advice” becomes “your advice”: goals, blood tests, genetic variants, restrictions, supplement preferences and—importantly—the style with what you want to be held accountable for. The repository includes a template; you fill it in with your own reality.
📋 Copy and fill in · goal: give the coach your actual profile so it can ground each response
# CLAUDE.md — o cérebro do coach (preencha com o SEU perfil)
## Meta (goal)
<ex.: recomposição — perder ~4 kg de gordura mantendo massa até dez>
## Exames (bloods)
<só os SEUS valores: ApoB 95, HOMA-IR 1.4, Vitamina D 28, ...>
## Genética (SNPs)
<ex.: CYP1A2 metabolizador rápido de cafeína; APOE e3/e3>
## Restrições
<ex.: sem lactose; joelho direito sensível; tendência a dormir tarde>
## Suplementos (preferências)
<ex.: creatina 5g/dia; magnésio à noite; evita pré-treino com cafeína>
## Estilo do coach
Direto e cobrando — pode ser "savage on purpose":
me chama no flanco quando eu furo um check-in, sem rodeios.
⚠️ Never version the completed CLAUDE.md
- •The template is in the repository; the filled in contains real lab results and genetic data — this is sensitive health information.
- •Keep it out of git (in
.gitignore), along with your seed values, photos, and the~/.env. - •The public repo is the blueprint clean — not anyone’s records.
💡 Why “style” matters
A coach you ignore changes nothing. Describing the tone—gentle, technical, or "savage on purpose" demanding check-ins — makes the LLM speak the way you moves. It’s part of the profile just like ApoB.
Key concepts
The CLAUDE.md grounds each response in your situation.
Tone is also configurable.
Copy the template and fill in your own.
The filled-in file is never versioned.
⌨️ The slash commands, one by one
Each slash command is a shortcut that triggers a specific coach routine. You don’t needs about them—you can just chat normally—but they give you a quick button for the day's actions. The six in the menu come from the agent.yaml; there’s also the /healthdb, which provides a link button to the dashboard.
📊 How to read: typing "/" opens the menu (blue), which branches into the six declared commands (cyan). The /healthdb (amber, on the right) is an extra that sends a deep-link button to the dashboard.
| Command | What it does |
|---|---|
| /checkin | The morning review guided by recovery: it starts with last night’s recovery and ties your choices to the number. |
| /today | Today's plan—workout, food, and coffee—visibly tailored to your recovery (green = push, red = take it easy). |
| /sofar | Shows what you’ve already logged today (food, workout, weight, coffee) — the day’s total so far. |
| /newday | Closes out the day and starts a new one — useful when you turn the page before the automatic routine runs. |
| /supplements | Your supplement schedule: what to take and when, based on what's in the database. |
| /advice | Advice with citations (RAG from sources), reconciled with your own data before it’s delivered to you. |
| /healthdb | Extra — sends a deep link button to the dashboard, with the DASHBOARD_TOKEN stored in an HttpOnly cookie. |
Key concepts
The day’s anchor: recovery → plan.
Today's plan and what has already come in.
Advice cited and checked against your data.
Protected shortcut to the dashboard.
💬 Start the bot and say your first "hi"
With the token in the ~/.env e o agent.yaml ready, you start the agent and send a regular message — you don’t even need a command. The minimum test is exactly this: the bot boots and replies to a "hi." Behind that "hi" is the sequence you see in the diagram: the agent reads the snapshot, reasons through the LLM, and sends the response back to Telegram.
📊 How to read: from left to right is the path of your message; the dashed line is the answer coming back. The agent always goes through the state.py (snapshot) before reasoning—that’s what we’ll see running in the next topic.
Telegram conversation (illustrative)
✅ The test that confirms this step
From the validation checklist: "the agent boots up and responds to a regular message on Telegram" e "the slash commands appear in the '/' menu". If “hi” gets a reply and commands appear when you type “/”, the bot is up and running.
Key concepts
You don’t need a command to chat.
Starts by reading the token from ~/.env.
Every response starts with state.py.
The LLM replies right in Telegram.
📸 state.py — how the snapshot is assembled
O snapshot is the compact snapshot of “now” that the agent reads at the start of each turn: weight trend, what you ate today, blood pressure, last night’s recovery, your 7-day sleep pattern, and your goals. The script state.py builds this picture from the database — and you can run it in the terminal to see what the coach sees.
🟢 New here?
Session snapshot — it’s not magic or AI: it’s just a deterministic database query that combines the latest rows from each table into a summary. Running the state.py alone shows exactly the text that enters the LLM context before any reasoning.
📋 Run in the terminal · goal: print the snapshot (weight, intake, and goals) that the coach reads each turn
# na raiz do repositório, com o ~/.env preenchido
python3 agent/scripts/state.py
=== SNAPSHOT (2026-06-30) ===
weight: 82.4 kg (7d: -0.6 kg ↓)
today: 1 240 kcal · 96 g proteína · café 1×
last night: recovery 71% · HRV 64 ms · sono 7h20
7d sleep: média 6h54 (meta 7h30)
goals: recomposição — manter massa, -4 kg gordura
🔎 Why run this separately
If a coach response seems "out of context," the state.py is the first place to look: if the snapshot is empty or out of date, the problem is missing data in the database—not the LLM. It’s your debugging window.
Key concepts
Builds the snapshot from the database.
Read-only — no AI in the middle.
What needs to appear in the output.
See what the coach actually sees.
🧲 mem.py recall — semantic memory
The snapshot captures “now”; the semantic memory brings back the relevant past. Every message is stored with a embedding (a numerical signature of the meaning). When you ask something, the mem.py recall searches for past messages most similar to the question — even if they don’t use the same words — and returns them to the coach.
🟢 New here? Two terms
- Embedding — a vector of numbers that represents the meaning from a text. Similar phrases become nearby vectors, so search finds by meaning, not by exact word.
- Semantic recall — “remember by meaning”: given your question, the system measures the distance between embeddings and retrieves the closest memories (via
pgvector, in Supabase).
📋 Run in the terminal · goal: retrieve relevant past messages for a query
# busca por significado nas suas mensagens já guardadas
python3 agent/scripts/mem.py recall "<o que você quer lembrar>"
# ex.: como o álcool costuma afetar o meu sono
python3 agent/scripts/mem.py recall "vinho à noite e recuperação"
recall "vinho à noite e recuperação" → 3 hits
0.89 2026-06-12 "bebi 2 taças no jantar, dormi mal"
0.84 2026-05-28 "recovery caiu p/ 48% depois do churrasco c/ cerveja"
0.79 2026-05-09 "noites sem álcool: HRV mais alto na manhã"
🧠 Memory is the product
This is what sets the coach apart from a chatbot that forgets everything: it connects today’s question to your history and sees patterns ("every time you eat dinner late, your sleep suffers"). From the checklist: "semantic recall (mem.py recall) returns relevant past messages”.
Key concepts
Numerical signature of the meaning.
Searches by meaning, not by word.
The proximity search in Supabase.
Relevant history becomes insight.
🌳 The agent/ tree
Everything you configured lives in the folder agent/ — the sanitized, self-contained agent. It helps to keep the map in mind: at the root, the brain (CLAUDE.md) and the config (agent.yaml.example); nested inside are the scripts, database migrations, and dashboard.
📊 How to read: the outer border is the folder agent/. The files in the root are at the top; the three nested folders are below. The scripts you ran in this module (state.py, mem.py) live in scripts/.
scripts/db.py
The bank’s gate: select, inserts, and even create the photo bucket (mkbucket). Stdlib-only.
scripts/whoop-sync.py
Pulls recovery + sleep from the wearable into the table vitals. Runs on the morning cron (Track 2.4).
scripts/supplements.py
Builds the supplement schedule that the /supplements delivers.
scripts/advice.py
The RAG behind the /advice: advice with citations, reconciled with your data. The only one that needs requests.
✅ Self-check (optional): where does the Telegram bot token live?
Key concepts
CLAUDE.md + agent.yaml.example + AGENTS.md.
state, mem, db, whoop-sync, supplements, advice.
The 14-table schema + seed.
The web dashboard that reads from Supabase.
📋 Module summary
telegram_bot_token_env and declares the slash commands; the token stays in ~/.env.state.py prints the "now"; mem.py recall brings back the relevant past.Next module:
2.4 — Wearable and scheduling: connect WHOOP (OAuth), schedule the whoop-sync.py and trigger the morning review every day.