Skip to main content
The system prompt defines how the bot behaves — its personality, what tools it knows about, and the rules it follows. It uses the 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.
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

The claude_code preset provides the base prompt — tool usage guidelines, safety instructions, and environment context. The appended ollim-bot instructions combine two sections in order:
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 either IDENTITY.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 the claude_code preset rather than a custom instruction in the appended prompt.
Rules: list before adding (avoid duplicates), mark complete rather than deleting.

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:
Format: [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 called report_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:
In the main session, pending updates are cleared after delivery. In interactive forks, they are read without clearing. See Context flow for the full read path and header variants.

Skills section

The system prompt’s skills section tells the bot how skills work — the directory structure, the skills: 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:

Update instruction variants

The preamble includes different instructions depending on the update-main-session mode:

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:
The preamble also includes a decision heuristic: “Would the user regret missing this?” Informational items should use 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: Foreground prompts contain only the tag followed by the routine/reminder body. Background prompts include the full preamble between the tag and the body.

Chain context

For reminders with max-chain > 0, additional context is appended:
On the final check, 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:
The explicit labeling of webhook data as “untrusted” is a security measure — it prevents external data from being misread as instructions for the bot.

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 in subagents/. These are separate from the main system prompt. Each file contains task-specific instructions, available commands, output format requirements, and triage rules. The gmail-reader and history-reviewer prompts share a common philosophy: missing a real item is worse than a false positive. The user-proxy prompt has the opposite bias: a wrong answer is worse than “unknown.”

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.