claude_code
preset as a base — preserving Claude Code’s built-in tool usage guidelines,
safety instructions, and environment context — then appends ollim-bot’s
operational instructions on top. Those instructions combine your editable
profile files (IDENTITY.md and USER.md) with behavior rules and
documentation for every tool. Additional context — timestamps, pending
background updates, and background preambles — is added before each
message.
Developer reference: prompt construction
Developer reference: prompt construction
The prompt uses a preset-with-append pattern. In
agent.py, the
system_prompt option is a dict with "type": "preset",
"preset": "claude_code", and "append" set to the output of
build_system_prompt() from prompts.py. This preserves Claude Code’s
full built-in prompt while adding ollim-bot’s instructions after it.
The profile section is loaded by load_profile() in profile.py.Prompt structure
Theclaude_code preset provides the base prompt — tool usage guidelines,
safety instructions, and environment context. The appended ollim-bot
instructions combine two sections in order:
| Section | Purpose |
|---|---|
| Profile | From IDENTITY.md + USER.md — persona, user context |
| Task capture | When and how to capture tasks |
| Output guidance | One-thing-at-a-time vs full lists |
| Configuration notes | CLI style, timestamps, prompt tags |
| Skills | Skill format, interactive use via SDK Skill tool, spec-file reference, dynamic listing of user-authored skills |
| Google Tasks | Commands, conventions |
| Google Calendar | Commands, timezone |
| Routines and Reminders | Quick CLI commands, spec-file reference, chain follow-ups |
| Guide | Delegation to ollim-bot-guide subagent |
| Gmail | Delegation to gmail-reader subagent |
| Claude History | Delegation to history-reviewer subagent |
| Responsiveness | Delegation to responsiveness-reviewer |
| User Proxy | Delegation to user-proxy subagent — when and how to use it, confidence level actions |
| Discord embeds | When to use embeds vs plain text |
| Web and docs | WebSearch, WebFetch, and docs MCP server |
| Interactive forks | Fork rules, idle timeout, exit options |
| Background forks | Ping budget, reporting modes |
| Webhooks | Webhook spec format reference |
Developer reference: template substitution
Developer reference: template substitution
The operational section uses Python template substitution for two
values:
USER_NAME (fork instructions, tool sections) and TZ
(Google Calendar section), both from config.py. The profile section
is loaded verbatim from disk — no substitution at prompt-build time.Profile section
If eitherIDENTITY.md or USER.md exists in the data directory,
both files are combined and placed at the top of the prompt.
IDENTITY.md is created from a template on first run. Your name is
written into the file when it’s first created — it doesn’t change each
time the bot starts. USER.md is one you create yourself — no template
is provided. The bot can read and update both files while running.
See Customize personality for what the
default template contains and how to edit it. See
Tell the bot about yourself for
USER.md guidance.
Tool instruction sections
Each tool section follows the same pattern: a heading, a command table, and behavioral rules. Tool safety — not hallucinating tools that don’t exist — is handled by theclaude_code preset rather than a custom
instruction in the appended prompt.
- Google Tasks
- Google Calendar
- Routines
- Reminders
| Command | Description |
|---|---|
ollim-bot tasks list [--all] | List tasks |
ollim-bot tasks add "<title>" [--due] [--notes] | Add a task |
ollim-bot tasks done <id> | Mark complete |
ollim-bot tasks delete <id> | Delete a task |
ollim-bot tasks update <id> [--title] [--due] [--notes] | Update |
Subagent delegation
Five tool sections — Guide, Gmail, Claude History, Responsiveness, and User Proxy — consist entirely of delegation instructions. The bot is told to never perform these tasks directly, instead handing off to the appropriate subagent.Fork and background instructions
The interactive fork section documents fork lifecycle rules: always branch from main (never nested forks) and use forks for research, complex tool chains, or tangential work. Exit tools —report_updates (default),
exit_fork, and save_context — are listed for agent-initiated forks.
Timeout and idle-exit guidance is delivered just-in-time via
[fork-timeout] prompts rather than pre-loaded in the system prompt.
The background fork section documents the ping budget system,
report_updates for bridging information back to the main session, and the
four update-main-session modes (always, on_ping, freely, blocked).
See Background forks for the full reference.
Context injection
The bot adds context to every message before processing it. Three pieces of dynamic context are included:Timestamp
Every user message gets a timestamp header:[YYYY-MM-DD DDD HH:MM AM/PM PT]. The bot uses this for
time-awareness — knowing when tasks are due, whether to say “good morning,”
and how long ago things happened.
Pending background updates
If background forks have calledreport_updates, those messages accumulate
in a pending updates file (capped at
10 entries). When the user next
sends a message, they are included with a context-specific header:
Skills section
The system prompt’s skills section tells the bot how skills work — the directory structure, theskills: field on routines, reminders, and
webhooks, and how to invoke skills interactively. It also includes
inline instructions for the SKILL.md format and a dynamic “Your
custom skills” listing generated by list_user_skills() in skills.py.
This listing includes only user-authored skills — generated skills
(prefixed routine-, reminder-, webhook-) and bundled skills are
excluded.
Background preamble
When a routine, reminder, or webhook runs in the background, the bot receives additional instructions at the top of the prompt. These cover:| Section | Condition | Content |
|---|---|---|
| Ping instructions | Always | ping_user/discord_embed status |
| Update instructions | Always | Mode-specific report_updates rules |
| Busy state | User mid-conversation AND allow-ping=True | ”Do NOT ping unless critical=True” |
| Budget status | allow-ping=True | Ping budget and upcoming schedule |
| Tool restrictions | Tools restricted | Available/unavailable tool list |
| User-proxy hint | Task tool available | ”For preference decisions, spawn the user-proxy subagent” |
Update instruction variants
The preamble includes different instructions depending on theupdate-main-session mode:
| Mode | Instruction |
|---|---|
always | MUST call report_updates before finishing |
on_ping (default) | Report if you pinged, otherwise call nothing |
freely | MAY optionally call report_updates |
blocked | No reporting to the main session |
blocked + allow-ping | No reporting, but pinging allowed (reporting modes) |
Budget and schedule window
When pinging is allowed, the preamble includes the current ping budget (e.g., “3/5 available (refills 1 every 90 min, next in 45 min)”) and a window of upcoming scheduled items:Developer reference: schedule window constants
Developer reference: schedule window constants
| Constant | Value | Purpose |
|---|---|---|
_GRACE_MINUTES | 15 | Grace period for recently-fired items |
_BASE_WINDOW_HOURS | 3 | Default lookahead window |
_MIN_FORWARD | 3 | Minimum forward items to show |
_MAX_WINDOW_HOURS | 12 | Maximum window expansion |
_TRUNCATE_LEN | 60 | Max description length before truncation |
report_updates, while
time-sensitive, health, or accountability items warrant a ping. The
critical=True flag on ping_user is reserved for items that would be
devastating to miss.
Scheduled prompt tags
When the scheduler fires a routine or reminder, the prompt is tagged so the bot knows the source:| Tag | Meaning |
|---|---|
[routine:{id}] | Foreground routine (main session) |
[routine-bg:{id}] | Background routine (forked session) |
[reminder:{id}] | Foreground reminder (main session) |
[reminder-bg:{id}] | Background reminder (forked session) |
[webhook:{id}] | Webhook (always background) |
Chain context
For reminders withmax-chain > 0, additional context is appended:
follow_up_chain is marked as unavailable.
Webhook prompts
Webhook prompts have a distinct structure that separates untrusted external data from the trusted instruction template:Fork resume prompt
When you click a button on a background fork’s output, the fork resumes as an interactive session. The bot receives a transition prompt:Subagent prompts
Each subagent has its own system prompt — a standalone markdown file with a configuration header insubagents/.
These are separate from the main system prompt. Each file contains
task-specific instructions, available commands, output format
requirements, and triage rules.
| File | Subagent | Key focus |
|---|---|---|
ollim-bot-guide.md | ollim-bot-guide | Setup and usage help, docs verbatim |
gmail-reader.md | gmail-reader | Email triage, skip/surface criteria |
history-reviewer.md | history-reviewer | Session scanning, loose threads |
responsiveness-reviewer.md | responsiveness-reviewer | Engagement analysis |
user-proxy.md | user-proxy | Preference decisions, evidence model, confidence calibration |
Next steps
Discord tools
Reference for all Discord tools the system prompt documents.
Subagents
How subagent prompts are defined and invoked.
Background forks
The background preamble in context — fork config and reporting modes.
Routines
Routine field reference used by the system prompt.
