Core Concept
The central idea is prompt composition:- Agents define “who” the AI is (personality, specialization, tone).
- Skills define “what” it must know/obey (rules, knowledge, compliance).
Benefits
Reuse
Versioning
.md files can be versioned in Git.Collaboration
Consistency
Specialization
Dispatch as Worker
agent_call by the LLM orchestrator.Skill Auto-activation
triggers: or paths: in their frontmatter are automatically injected into the system prompt when detected in the user’s message.Per-Agent Model & Effort
model: and effort: — the dispatcher routes correctly without changing the user’s active choice.Directory Structure
Files live under~/.chatcli/:
Agent File Format
Agents are Markdown files with YAML frontmatter:tools Field — Multi-Agent Integration
The tools field in the YAML frontmatter is the key to integration with the multi-agent orchestration system. It defines which commands the agent can use when dispatched as a worker by the LLM orchestrator.
Example without tools
read, search, tree).Advanced Agent Frontmatter
Recent releases bring full parity between agents and skills for LLM preference fields. Both are optional and backwards compatible — agents without these fields keep working exactly as before.How the Dispatcher Applies Model/Effort
When the orchestrator LLM dispatches an agent via<agent_call>, the dispatcher:
Reads `agent.Model()` and `agent.Effort()`
BuiltinAgentMeta (defaults + env var override).If `Model()` is non-empty, runs the Model Router
claude-*, gpt-*, gemini-*, etc.) → optimistic fallback on the user’s provider. If the target provider is not configured (no API key), it gracefully falls back to the user’s client and logs a clear warning.If `Effort()` is non-empty, attaches to the worker `ctx`
client.EffortFromContext(ctx) inside SendPrompt and inject thinking.budget_tokens (Anthropic) or reasoning.effort / reasoning_effort (OpenAI) into the request body — only on models that support it.`cli.Client`, `cli.Provider` and `cli.Model` are **not** mutated
Example: Custom Agent with Ideal Model
Skill File Format
Skills contain pure knowledge or compliance rules:Skills V2 — Packages with Subskills and Scripts
Beyond V1 skills (single.md file), ChatCLI supports V2 Skills: directories with multiple documents and executable scripts.
V2 Skill Structure
Subskills
.md files inside the skill directory (except SKILL.md) are registered as subskills. When the agent is dispatched as a worker, subskill paths appear in the worker’s system prompt, which can read them as needed.
Scripts
Files inscripts/ are registered as executable skills on the worker. The system automatically infers the run command from the extension:
@coder exec command and their results return to the worker.
Advanced Skill Frontmatter
Beyond the basic fields (name, description, allowed-tools), skills support advanced frontmatter for fine-grained behavior control. All advanced fields are optional and backwards compatible — existing skills keep working unchanged.
Automatic Activation: triggers
Keywords that activate the skill automatically when detected in the user message. Case-insensitive, with two tiers:
- Contiguous substring (fast path) — the whole trigger appears as-is:
servicenow loginfires on “do the ServiceNow login”. - All words, any order — multi-word triggers also fire when every word appears as a whole token in the text, regardless of order:
servicenow loginalso fires on “preciso fazer o login no servicenow”. Whole tokens only — short words never match inside other words (message medoes not fire on “user message”), and punctuation tokenizes on both sides (unit-tests≈unit tests).
pkg/persona/manager.go#FindTriggeredSkills. Detection runs on every chat turn and, in agent/coder mode, at the start of the run and again on every turn of the ReAct loop (see Mid-task re-activation).
Automatic Activation: paths
File globs that activate the skill when matching files are being discussed. Supports *, ** (recursive doublestar), and ?.
@file path/..., @path/to/file.go, or bare tokens like pkg/foo/bar_test.go and main.go) and matches each against the paths: patterns of every installed skill.
Examples that trigger *_test.go:
"run the tests in pkg/foo/bar_test.go""@file pkg/foo/bar_test.go""@pkg/foo/bar_test.go"
pkg/persona/types.go#MatchesPath (with a custom doublestar matcher, zero external deps) and pkg/persona/manager.go#FindPathMatchedSkills. Path extraction from input is in cli/skill_activation.go#extractFilePaths.
Mid-task re-activation (agent/coder)
In agent/coder mode, activation is not limited to the initial query. On every turn of the ReAct loop, ChatCLI re-scans for skills that haven’t fired yet, matching against:- the model’s own reasoning and the file paths inside its
tool_callargs — if the agent decides mid-task to “write a Helm chart for this”, or starts touching files matching a skill’spaths:globs, the skill activates in time to shape the very next action; - follow-up instructions you type mid-session (the type-ahead queue or the coder continuation prompt).
[SKILL AUTO-ACTIVATION — MID-TASK] message at the next turn boundary, so the cached system-prompt prefix is never invalidated mid-run. Each skill fires at most once per run (deduplicated against startup injection), and the dedup set survives @park/resume. Mid-task model:/effort: hints are honored only when no startup skill already claimed them.
Disable with CHATCLI_AGENT_SKILL_RESCAN=false (on by default; listed in /config under skills).
model and effort Propagation
When a skill auto-activates (via triggers or paths), is pinned (/skill pin), or is manually invoked, its model: and effort: are propagated to the current turn:
model:— the dispatcher/resolver swaps the LLM client for this turn. Works within the same provider (e.g.,sonnet→opuson Claude) or cross-provider (e.g., user on Claude, skill wantsgpt-5on OpenAI). If the target provider is not configured, it falls back to the user’s client with a visible notice.effort:— mapped tothinking.budget_tokens(Anthropic, Opus 4.x / Sonnet 4.x / 3.7 models) orreasoning_effort/reasoning.effort(OpenAI, o1/o3/o4/gpt-5 models). Unsupported models silently ignore.
model: in this order wins; subsequent conflicts are logged as warnings but don’t force additional swaps.
Manual Invocation via /<skill-name>
Skills with user-invocable: true are available as direct slash commands:
/<skill-name> ahead of the default router, validates that the skill exists with user-invocable: true, loads its content, displays the argument-hint (when args are empty), and fires the turn with the skill injected as a ”# Manually Invoked Skill” block in the system prompt — taking precedence over auto-activated skills.
The protected command list (/agent, /coder, /run, /switch, /help, /skill, etc.) can never be shadowed by a skill — even a skill named agent won’t shadow the built-in command.
Slash command autocomplete also includes all user-invocable: true skills, showing description and argument-hint side by side.
Invocation Control
disable-model-invocation: true together with user-invocable: true = the skill only runs when the user types /skill-name, never through automatic detection. Useful for destructive or highly specific skills.Pin a Skill for the Session (/skill pin)
When you need a skill to apply to every turn of the session — not only those that match triggers:/paths: — pin it:
# Pinned Skills block in the system prompt, cacheable via cache_control: ephemeral. On hint conflicts, pinned beats auto-activation but loses to a manual /<skill-name> invocation.
Skills with disable-model-invocation: true cannot be pinned — the flag exists precisely to forbid automatic injection. Use manual /<skill-name> for those.
Full details, examples, and the precedence table: Pin Skills in Skill Registry.
/agent Without Context
Before: typing /agent alone entered agent mode immediately and sent an empty message to the LLM.
Now: typing /agent (or /run) without an inline task prints the persona handler help plus a usage hint and does not start the ReAct loop. Same applies to /coder. This avoids token burn on empty messages and makes the UX more predictable.
Skills from Remote Registries
Besides creating skills manually, you can search and install skills from remote registries via the/skill command:
~/.chatcli/skills/<name>/SKILL.md as V2 packages and are immediately available for agents. ChatCLI supports multiple registries simultaneously (ChatCLI.dev, ClawHub, corporate registries) with fan-out parallel search. See Skill Registry for full details.Dispatch as Worker (Multi-Agent)
When starting/coder or /agent, all custom agents are automatically registered in the multi-agent orchestration system. The LLM orchestrator can then dispatch them via <agent_call>:
What the worker gets
When dispatched, CustomAgent runs with:Personalized system prompt
Mini ReAct loop
Permitted commands
tools field of the frontmatter.Per-turn resolved client
model:, the dispatcher calls ResolveModelRouting to obtain the correct client before each mini-ReAct turn.Effort applied to ctx
effort:, the worker’s ctx receives WithEffortHint, read by the provider inside SendPrompt.Parallel reads
File locks
Error recovery
tool_call to diagnose and fix failures.End-to-End Example
Management Commands
All management commands are integrated under/agent:
Prompt Assembly Order
When an agent is loaded, the system prompt is assembled in this order:[ROLE]
[PERSONALITY]
[SKILLS]
[AUTO-LOADED SKILLS]
triggers: or paths: on the current message[MANUAL SKILL]
/<skill-name>[PLUGINS]
[REMINDER]
Full Practical Example
1. Create an agent
Create the file~/.chatcli/agents/python-data.md:
2. Use the agent
Agent and Skill Precedence (Project > Global)
Both agents and skills support per-project directories with precedence over the globals. ChatCLI auto-detects the project root by looking for a.agent/ or .git/ directory upward from the current directory.
Search Order
Project Structure
Integration with /coder
When an agent is loaded:
/agent <task>— Uses the agent’s persona./coder <task>— Combines the agent’s persona with the coder prompt.
@coder tools to edit files, run tests, etc. The agent’s model: and effort: preferences are honored in both modes.
Tips
Start Simple
Version on Git
Share with the Team
Use Clear Descriptions
Test the Prompt
/agent show to inspect the assembled prompt.Assign `effort` Carefully
effort: high costs more tokens. Reserve it for agents that truly need deep reasoning (reviewers, planners, diagnostics).Useful Skill Examples
- clean-code — Clean code principles
- error-handling — Error handling patterns
- testing-patterns — Automated testing patterns
- docker-master — Dockerfile best practices
- clean-scripts — Safe Bash scripting patterns
- aws-security — AWS security rules
- team-conventions — Team-specific conventions
Remote Agents and Skills
When connected to a ChatCLI server viachatcli connect, the client automatically discovers agents and skills available on the server. They are transferred to the client and composed locally, allowing merge with local resources.
Since the recent update, the gRPC wire (pb.AgentInfo) carries all the advanced fields — model, effort, category, version, author, tags — so remote agents behave exactly like local ones for routing purposes.
Provisioning via Kubernetes
- Helm
- Operator
/home/chatcli/.chatcli/agents/ and /home/chatcli/.chatcli/skills/, and are available for remote discovery automatically. Advanced frontmatter fields (model, effort, category, etc.) are read by the chatcli binary inside the pod — the CRD and operator do not need changes to support them.Next steps
Multi-Agent Orchestration
<agent_call>.