Agent profiles¶
An agent profile is the reusable definition of an agent: a name, a
description the master reads when deciding what to delegate, a system prompt the
agent runs under, and — most importantly — the maximum set of tools that agent may
use. Kerkov ships five built-in profiles, and you can add your own as AGENT.md
files.
For how agents run, see delegate and agent_wait and the
agent subsystem concept page.
Built-in profiles¶
| Profile | For | Tools |
|---|---|---|
recon |
Enumeration, OSINT, and scanning — no exploitation, no write. | read, http, exec, process, sbom_generate, vulnerability_scan, skill_lookup, recall, ledger |
analysis |
Read-only review of logs, code, or artifacts. | read, skill_lookup, recall, ledger |
exploit |
Exploitation and payload work on authorized targets. | read, write, http, exec, process, skill_lookup, recall, ledger, zap |
general |
Default ad-hoc delegation. | read, http, exec, process, skill_lookup, recall, ledger |
container-operator |
Low-token Docker Compose startup, readiness, status, and shutdown. | read, exec, container_lifecycle, skill_lookup, recall, ledger |
Two things every profile has that are not in the table: the report tool (how any
agent finishes — always present, never listed) and, below the depth cap,
delegate (so an agent can fan out further).
Notably absent from every built-in whitelist: sast_scan. A
whitelisted call bypasses interactive approval, and a wide OpenGrep scan is
expensive enough that the operator should see it first. A user-defined profile can
opt into it.
The AGENT.md schema¶
A user-defined profile is a Markdown file with YAML frontmatter, saved at
agents/<name>/AGENT.md in the project root. The frontmatter declares the profile;
the body is the system prompt.
---
name: example-recon
description: Example user-defined recon agent — narrow tools, OSINT-focused.
allowed_tools:
- read
- http
- skill_lookup
max_iterations: 20
---
You are a focused open-source reconnaissance agent.
Your job is to enumerate publicly-available information about the target the
master delegates to you. You have no execution or write capability — read, HTTP
fetch, and skill lookup only.
Stay on-task. When done (or when you cannot make progress), call the `report` tool
with status="completed", "partial", or "stuck". Do NOT emit further tool calls
after `report`.
Fields¶
| Field | Required | Default | Description |
|---|---|---|---|
name |
✓ | — | Unique profile name. The agent_type passed to delegate. |
description |
✓ | — | One line shown to the master LLM in its profile index. This is what the master reads to decide when to use the profile, so make it discriminating. |
allowed_tools |
✓ | — | A list of tool names. The maximum whitelist for any spawn of this profile — for that agent's own calls; see the scope of the ceiling. |
max_iterations |
— | 30 |
Per-agent loop cap. Also bounded by AGENT_MAX_ITERATIONS; the effective cap is the lower of the two. |
system_prompt |
— | the body | The agent's system prompt. If omitted, the Markdown body after the frontmatter is used — which is the normal way to write it. |
The system prompt comes from system_prompt if set, otherwise the body; a profile
with neither is skipped. report is always available and never listed in
allowed_tools.
allowed_tools is a ceiling¶
The whitelist is the maximum set a spawn may use. delegate can request a subset
via its own allowed_tools field, which narrows the profile's set — it can
never widen it. Requesting a tool outside the profile's whitelist rejects the
entire batch before any agent starts. For example, requesting ["read", "exec"]
for analysis fails because that profile does not allow exec.
report is accepted in the requested list as a special case, since every agent
has it. An explicit subset must still retain at least one of the profile's tools;
an empty list or ["report"] alone is rejected. Successful requests receive the
selected profile tools, plus report and the depth-dependent delegate described
above.
Tool names must match the registered names exactly — see the tools
reference. recall and ledger follow the same rule as any other
tool: every built-in profile whitelists them so agents can read what the engagement
already gathered, but a user-defined profile that omits them does not get them.
The ceiling is per agent, not per subtree¶
The whitelist bounds the tools this agent may call. It does not bound the agents it spawns.
delegate is appended by the runner after allowed_tools has been applied, so it is
outside the whitelist by construction — which is also why naming it in a delegate
request fails: validation checks the request against the profile's list, and
delegate is in no profile's list. (report is the one name excused there, since it
is the tool an agent must call to finish.) Any agent below
AGENT_MAX_DEPTH has it, and a nested delegation resolves
its own agent_type against the full profile index and draws from the same master
tool pool. Nothing requires the child's profile to be a subset of the parent's: an
analysis agent restricted to read can spawn an exploit child holding write,
exec, and zap. Because an agent auto-approves any call inside its own whitelist,
that child's exec never reaches an approval prompt — the operator approved the
master's delegate, one level up.
Treat allowed_tools as a capability list for one agent, then bound the tree
separately:
AGENT_MAX_DEPTH=1withholdsdelegatefrom every agent, which makes the approved whitelist the whole of what a delegation can reach./agents review <name>puts one agent's calls back through the operator's approval path, but only while you are attached to it.
Loading and precedence¶
Profiles are loaded at startup:
- The five built-ins are always present.
- Every
agents/<name>/AGENT.mdunder the project root is scanned and parsed.
A file is skipped with a logged warning, not fatally rejected, when it is missing a required field, has no valid frontmatter, has an empty system prompt, is larger than 256 KB, or fails validation. One bad profile never stops the others loading.
A user-defined profile may shadow a built-in of the same name — a warning is logged, and the user-defined one wins, because writing the file is opting into that. Two user-defined profiles with the same name: the last one loaded wins, also with a warning.
The master does not see full profiles — it sees a compact index of names,
descriptions, and tool sets, truncated past 8 KB so a large agents/ directory
cannot crowd out the master's own context.
Related¶
delegateandagent_wait— spawning agents against these profiles and collecting their reports.- Agents guide — watching, talking to, reviewing, and stopping a running agent.
- Agent subsystem — the internals.
- Tools reference — the tool names
allowed_toolsdraws from.