Vendor OpenClaw source as Adolf fork baseline
Some checks failed
ClawSweeper Dispatch / dispatch (push) Has been cancelled
CodeQL / Security High (actions) (push) Has been cancelled
CodeQL / Security High (channel-runtime-boundary) (push) Has been cancelled
CodeQL / Security High (core-auth-secrets) (push) Has been cancelled
CodeQL / Security High (mcp-process-tool-boundary) (push) Has been cancelled
CodeQL / Security High (network-ssrf-boundary) (push) Has been cancelled
CodeQL / Security High (plugin-trust-boundary) (push) Has been cancelled
CodeQL / Security High (process-exec-boundary) (push) Has been cancelled
Docs Sync Publish Repo / sync-publish-repo (push) Has been cancelled
Docs / docs (push) Has been cancelled
OpenClaw Stable Main Closeout / Resolve stable release closeout inputs (push) Has been cancelled
OpenClaw Stable Main Closeout / Verify stable main closeout (push) Has been cancelled
Workflow Sanity / no-tabs (push) Has been cancelled
Workflow Sanity / actionlint (push) Has been cancelled
Workflow Sanity / generated-doc-baselines (push) Has been cancelled
CI / runner-admission (push) Has been cancelled
CI / preflight (push) Has been cancelled
CI / security-fast (push) Has been cancelled
CI / pnpm-store-warmup (push) Has been cancelled
CI / build-artifacts (push) Has been cancelled
CI / native-i18n (push) Has been cancelled
CI / ${{ matrix.check_name }} (push) Has been cancelled
CI / ${{ matrix.checkName }} (push) Has been cancelled
CI / checks-node-compat-node22 (push) Has been cancelled
CI / check-bundled-channel-config-metadata (push) Has been cancelled
CI / check-dependencies (push) Has been cancelled
CI / check-guards (push) Has been cancelled
CI / check-lint (push) Has been cancelled
CI / check-prod-types (push) Has been cancelled
CI / check-shrinkwrap (push) Has been cancelled
CI / check-test-types (push) Has been cancelled
CI / check-additional-boundaries-a (push) Has been cancelled
CI / check-additional-boundaries-bcd (push) Has been cancelled
CI / check-additional-extension-bundled (push) Has been cancelled
CI / check-additional-extension-channels (push) Has been cancelled
CI / check-additional-extension-package-boundary (push) Has been cancelled
CI / check-additional-runtime-topology-architecture (push) Has been cancelled
CI / check-session-accessor-boundary (push) Has been cancelled
CI / check-session-transcript-reader-boundary (push) Has been cancelled
CI / check-docs (push) Has been cancelled
CI / skills-python (push) Has been cancelled
CI / macos-swift (push) Has been cancelled
CI / ios-build (push) Has been cancelled
CI / ci-timings-summary (push) Has been cancelled
Native App Locale Refresh / Refresh native fa (push) Has been cancelled
Native App Locale Refresh / Refresh native fr (push) Has been cancelled
Native App Locale Refresh / Refresh native hi (push) Has been cancelled
Native App Locale Refresh / Refresh native id (push) Has been cancelled
Native App Locale Refresh / Refresh native it (push) Has been cancelled
Native App Locale Refresh / Refresh native ja-JP (push) Has been cancelled
Control UI Locale Refresh / plan (push) Has been cancelled
Control UI Locale Refresh / Refresh ${{ matrix.locale }} (push) Has been cancelled
Control UI Locale Refresh / Commit control UI locale refresh (push) Has been cancelled
Live Media Runner Image / Build live media runner image (push) Has been cancelled
Native App Locale Refresh / Refresh native ar (push) Has been cancelled
Native App Locale Refresh / Refresh native de (push) Has been cancelled
Native App Locale Refresh / Refresh native es (push) Has been cancelled
Native App Locale Refresh / Refresh native ko (push) Has been cancelled
Native App Locale Refresh / Refresh native nl (push) Has been cancelled
Native App Locale Refresh / Refresh native pl (push) Has been cancelled
Native App Locale Refresh / Refresh native pt-BR (push) Has been cancelled
Native App Locale Refresh / Refresh native ru (push) Has been cancelled
Native App Locale Refresh / Refresh native sv (push) Has been cancelled
Native App Locale Refresh / Refresh native th (push) Has been cancelled
Native App Locale Refresh / Refresh native tr (push) Has been cancelled
Native App Locale Refresh / Refresh native uk (push) Has been cancelled
Native App Locale Refresh / Refresh native vi (push) Has been cancelled
Native App Locale Refresh / Refresh native zh-CN (push) Has been cancelled
Native App Locale Refresh / Refresh native zh-TW (push) Has been cancelled
Native App Locale Refresh / Commit native locale refresh (push) Has been cancelled
Plugin Init Scaffold Validation / Validate provider scaffold (push) Has been cancelled
Plugin NPM Release / preview_plugins_npm (push) Has been cancelled
Plugin NPM Release / Validate release publish approval (push) Has been cancelled
Plugin NPM Release / preview_plugin_pack (push) Has been cancelled
Plugin NPM Release / publish_plugins_npm (push) Has been cancelled
Sandbox Common Smoke / sandbox-common-smoke (push) Has been cancelled
Website Installer Sync / static (push) Has been cancelled
Website Installer Sync / linux-docker (push) Has been cancelled
Website Installer Sync / macos-installer (push) Has been cancelled
Website Installer Sync / windows-installer (push) Has been cancelled
Website Installer Sync / sync-website (push) Has been cancelled
Some checks failed
ClawSweeper Dispatch / dispatch (push) Has been cancelled
CodeQL / Security High (actions) (push) Has been cancelled
CodeQL / Security High (channel-runtime-boundary) (push) Has been cancelled
CodeQL / Security High (core-auth-secrets) (push) Has been cancelled
CodeQL / Security High (mcp-process-tool-boundary) (push) Has been cancelled
CodeQL / Security High (network-ssrf-boundary) (push) Has been cancelled
CodeQL / Security High (plugin-trust-boundary) (push) Has been cancelled
CodeQL / Security High (process-exec-boundary) (push) Has been cancelled
Docs Sync Publish Repo / sync-publish-repo (push) Has been cancelled
Docs / docs (push) Has been cancelled
OpenClaw Stable Main Closeout / Resolve stable release closeout inputs (push) Has been cancelled
OpenClaw Stable Main Closeout / Verify stable main closeout (push) Has been cancelled
Workflow Sanity / no-tabs (push) Has been cancelled
Workflow Sanity / actionlint (push) Has been cancelled
Workflow Sanity / generated-doc-baselines (push) Has been cancelled
CI / runner-admission (push) Has been cancelled
CI / preflight (push) Has been cancelled
CI / security-fast (push) Has been cancelled
CI / pnpm-store-warmup (push) Has been cancelled
CI / build-artifacts (push) Has been cancelled
CI / native-i18n (push) Has been cancelled
CI / ${{ matrix.check_name }} (push) Has been cancelled
CI / ${{ matrix.checkName }} (push) Has been cancelled
CI / checks-node-compat-node22 (push) Has been cancelled
CI / check-bundled-channel-config-metadata (push) Has been cancelled
CI / check-dependencies (push) Has been cancelled
CI / check-guards (push) Has been cancelled
CI / check-lint (push) Has been cancelled
CI / check-prod-types (push) Has been cancelled
CI / check-shrinkwrap (push) Has been cancelled
CI / check-test-types (push) Has been cancelled
CI / check-additional-boundaries-a (push) Has been cancelled
CI / check-additional-boundaries-bcd (push) Has been cancelled
CI / check-additional-extension-bundled (push) Has been cancelled
CI / check-additional-extension-channels (push) Has been cancelled
CI / check-additional-extension-package-boundary (push) Has been cancelled
CI / check-additional-runtime-topology-architecture (push) Has been cancelled
CI / check-session-accessor-boundary (push) Has been cancelled
CI / check-session-transcript-reader-boundary (push) Has been cancelled
CI / check-docs (push) Has been cancelled
CI / skills-python (push) Has been cancelled
CI / macos-swift (push) Has been cancelled
CI / ios-build (push) Has been cancelled
CI / ci-timings-summary (push) Has been cancelled
Native App Locale Refresh / Refresh native fa (push) Has been cancelled
Native App Locale Refresh / Refresh native fr (push) Has been cancelled
Native App Locale Refresh / Refresh native hi (push) Has been cancelled
Native App Locale Refresh / Refresh native id (push) Has been cancelled
Native App Locale Refresh / Refresh native it (push) Has been cancelled
Native App Locale Refresh / Refresh native ja-JP (push) Has been cancelled
Control UI Locale Refresh / plan (push) Has been cancelled
Control UI Locale Refresh / Refresh ${{ matrix.locale }} (push) Has been cancelled
Control UI Locale Refresh / Commit control UI locale refresh (push) Has been cancelled
Live Media Runner Image / Build live media runner image (push) Has been cancelled
Native App Locale Refresh / Refresh native ar (push) Has been cancelled
Native App Locale Refresh / Refresh native de (push) Has been cancelled
Native App Locale Refresh / Refresh native es (push) Has been cancelled
Native App Locale Refresh / Refresh native ko (push) Has been cancelled
Native App Locale Refresh / Refresh native nl (push) Has been cancelled
Native App Locale Refresh / Refresh native pl (push) Has been cancelled
Native App Locale Refresh / Refresh native pt-BR (push) Has been cancelled
Native App Locale Refresh / Refresh native ru (push) Has been cancelled
Native App Locale Refresh / Refresh native sv (push) Has been cancelled
Native App Locale Refresh / Refresh native th (push) Has been cancelled
Native App Locale Refresh / Refresh native tr (push) Has been cancelled
Native App Locale Refresh / Refresh native uk (push) Has been cancelled
Native App Locale Refresh / Refresh native vi (push) Has been cancelled
Native App Locale Refresh / Refresh native zh-CN (push) Has been cancelled
Native App Locale Refresh / Refresh native zh-TW (push) Has been cancelled
Native App Locale Refresh / Commit native locale refresh (push) Has been cancelled
Plugin Init Scaffold Validation / Validate provider scaffold (push) Has been cancelled
Plugin NPM Release / preview_plugins_npm (push) Has been cancelled
Plugin NPM Release / Validate release publish approval (push) Has been cancelled
Plugin NPM Release / preview_plugin_pack (push) Has been cancelled
Plugin NPM Release / publish_plugins_npm (push) Has been cancelled
Sandbox Common Smoke / sandbox-common-smoke (push) Has been cancelled
Website Installer Sync / static (push) Has been cancelled
Website Installer Sync / linux-docker (push) Has been cancelled
Website Installer Sync / macos-installer (push) Has been cancelled
Website Installer Sync / windows-installer (push) Has been cancelled
Website Installer Sync / sync-website (push) Has been cancelled
Adolf is a fork/vendored clone of github.com/openclaw/openclaw (v2026.6.11), free to diverge. Tree copied sans upstream .git; upstream remote added for future syncs. Node pinned to 24 (.nvmrc); engines already require >=22.19. Preserves docs/ARCHITECTURE.md. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LeqyaxJF2nbRXJtae2kNB2
This commit is contained in:
484
docs/tools/skills-config.md
Normal file
484
docs/tools/skills-config.md
Normal file
@@ -0,0 +1,484 @@
|
||||
---
|
||||
title: "Skills config"
|
||||
sidebarTitle: "Skills config"
|
||||
summary: "Full reference for the skills.* config schema, agent allowlists, workshop settings, and sandbox env var handling."
|
||||
read_when:
|
||||
- Configuring skill loading, install, or gating behavior
|
||||
- Setting per-agent skill visibility
|
||||
- Adjusting Skill Workshop limits or approval policy
|
||||
---
|
||||
|
||||
Most skills configuration lives under `skills` in
|
||||
`~/.openclaw/openclaw.json`. Agent-specific visibility lives under
|
||||
`agents.defaults.skills` and `agents.list[].skills`.
|
||||
|
||||
```json5
|
||||
{
|
||||
skills: {
|
||||
allowBundled: ["gemini", "peekaboo"],
|
||||
load: {
|
||||
extraDirs: ["~/Projects/agent-scripts/skills"],
|
||||
allowSymlinkTargets: ["~/Projects/manager/skills"],
|
||||
watch: true,
|
||||
watchDebounceMs: 250,
|
||||
},
|
||||
install: {
|
||||
preferBrew: true,
|
||||
nodeManager: "npm",
|
||||
allowUploadedArchives: false,
|
||||
},
|
||||
workshop: {
|
||||
autonomous: { enabled: false },
|
||||
allowSymlinkTargetWrites: false,
|
||||
approvalPolicy: "pending",
|
||||
maxPending: 50,
|
||||
maxSkillBytes: 40000,
|
||||
},
|
||||
entries: {
|
||||
"image-lab": {
|
||||
enabled: true,
|
||||
apiKey: { source: "env", provider: "default", id: "GEMINI_API_KEY" },
|
||||
env: { GEMINI_API_KEY: "GEMINI_KEY_HERE" },
|
||||
},
|
||||
peekaboo: { enabled: true },
|
||||
sag: { enabled: false },
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
<Note>
|
||||
For built-in image generation, use `agents.defaults.imageGenerationModel`
|
||||
plus the core `image_generate` tool instead of `skills.entries`. Skill
|
||||
entries are for custom or third-party skill workflows only.
|
||||
</Note>
|
||||
|
||||
## Loading (`skills.load`)
|
||||
|
||||
<ParamField path="skills.load.extraDirs" type="string[]">
|
||||
Additional skill directories to scan, at the lowest precedence (below
|
||||
bundled and plugin skills). Paths are expanded with `~` support.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.load.allowSymlinkTargets" type="string[]">
|
||||
Trusted real target directories that symlinked skill folders may resolve
|
||||
into, even when the symlink lives outside the configured root. Use this for
|
||||
intentional sibling-repo layouts such as
|
||||
`<workspace>/skills/manager -> ~/Projects/manager/skills`. Keep this list
|
||||
narrow — do not point at broad roots like `~` or `~/Projects`.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.load.watch" type="boolean" default="true">
|
||||
Watch skill folders and refresh the skills snapshot when `SKILL.md` files
|
||||
change. Covers nested files under grouped skill roots.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.load.watchDebounceMs" type="number" default="250">
|
||||
Debounce window for skill watcher events in milliseconds.
|
||||
</ParamField>
|
||||
|
||||
## Install (`skills.install`)
|
||||
|
||||
<ParamField path="skills.install.preferBrew" type="boolean" default="true">
|
||||
Prefer Homebrew installers when `brew` is available.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.install.nodeManager" type='"npm" | "pnpm" | "yarn" | "bun"' default='"npm"'>
|
||||
Node package manager preference for skill installs. This only affects skill
|
||||
installs — the Gateway runtime should still use Node (Bun is not
|
||||
recommended for WhatsApp/Telegram). `openclaw setup --node-manager` and
|
||||
`openclaw onboard --node-manager` accept `npm`, `pnpm`, or `bun`; set
|
||||
`"yarn"` directly in config for Yarn-backed skill installs.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.install.allowUploadedArchives" type="boolean" default="false">
|
||||
Allow trusted `operator.admin` Gateway clients to install private zip
|
||||
archives staged through `skills.upload.*`. Normal ClawHub installs do not
|
||||
need this setting.
|
||||
</ParamField>
|
||||
|
||||
## Operator Install Policy (`security.installPolicy`)
|
||||
|
||||
Use `security.installPolicy` when operators need a trusted local command to
|
||||
approve or block skill and plugin installs with host-specific policy. The
|
||||
policy runs after OpenClaw has staged source material and before the install
|
||||
or update continues. It applies to ClawHub skills, uploaded skills, Git/local
|
||||
skills, skill dependency installers, and plugin install/update sources.
|
||||
|
||||
```json5
|
||||
{
|
||||
security: {
|
||||
installPolicy: {
|
||||
enabled: true,
|
||||
// Omit targets to cover every supported target.
|
||||
targets: ["skill", "plugin"],
|
||||
exec: {
|
||||
source: "exec",
|
||||
command: "/usr/local/bin/openclaw-install-policy",
|
||||
args: ["--json"],
|
||||
timeoutMs: 10000,
|
||||
noOutputTimeoutMs: 10000,
|
||||
maxOutputBytes: 1048576,
|
||||
passEnv: ["OPENCLAW_STATE_DIR", "PATH"],
|
||||
env: { POLICY_MODE: "strict" },
|
||||
trustedDirs: ["/usr/local/bin"],
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
<ParamField path="security.installPolicy.enabled" type="boolean" default="false">
|
||||
Enables operator-owned install policy. When enabled without a valid `exec`
|
||||
command, installs fail closed.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.targets" type='("skill" | "plugin")[]'>
|
||||
Optional target filter. When omitted, policy applies to every supported
|
||||
target so new installs do not unexpectedly fail open.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.command" type="string">
|
||||
Absolute path to the trusted policy executable. OpenClaw runs it without a
|
||||
shell and validates the path before use.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.args" type="string[]">
|
||||
Static arguments passed after `command`.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.timeoutMs" type="number" default="10000">
|
||||
Maximum wall-clock runtime for one policy decision.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.noOutputTimeoutMs" type="number" default="timeoutMs">
|
||||
Maximum time without stdout or stderr output before the policy fails
|
||||
closed.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.maxOutputBytes" type="number" default="1048576">
|
||||
Maximum combined stdout and stderr bytes accepted from the policy process.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.env" type="Record<string, string>">
|
||||
Literal environment variables provided to the policy process.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.passEnv" type="string[]">
|
||||
Environment variable names copied from the OpenClaw process into the
|
||||
policy process. Only named variables are passed.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.trustedDirs" type="string[]">
|
||||
Optional allowlist of directories that may contain the policy executable.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.allowInsecurePath" type="boolean" default="false">
|
||||
Bypasses command path ownership and permission checks. Use only when the
|
||||
path is protected by another mechanism.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="security.installPolicy.exec.allowSymlinkCommand" type="boolean" default="false">
|
||||
Allows the configured command path to be a symlink. The resolved target
|
||||
must still satisfy the other path checks. Interpreter script arguments must
|
||||
be direct regular files, not symlinks.
|
||||
</ParamField>
|
||||
|
||||
The policy receives one JSON object on stdin with `protocolVersion: 1`,
|
||||
`openclawVersion`, `targetType`, `targetName`, `sourcePath`, `sourcePathKind`,
|
||||
optional structured `source`, structured `origin`, and `request`. It must
|
||||
write one JSON object on stdout: `{ "protocolVersion": 1, "decision": "allow" }`
|
||||
or `{ "protocolVersion": 1, "decision": "block", "reason": "..." }`. Non-zero
|
||||
exit, timeout, malformed JSON, missing fields, or unsupported protocol
|
||||
versions fail closed.
|
||||
|
||||
OpenClaw does not execute install policy during normal Gateway startup.
|
||||
Installs and updates fail closed when policy is enabled but unavailable.
|
||||
`openclaw doctor` performs static validation; `openclaw doctor --deep`
|
||||
executes a synthetic install probe against the configured command.
|
||||
|
||||
Bulk updates apply policy per target: a blocked skill or plugin update fails
|
||||
that target without disabling the policy or skipping later targets in the
|
||||
batch.
|
||||
|
||||
Example stdin:
|
||||
|
||||
```json
|
||||
{
|
||||
"protocolVersion": 1,
|
||||
"openclawVersion": "2026.6.1",
|
||||
"targetType": "skill",
|
||||
"targetName": "weather",
|
||||
"sourcePath": "/var/folders/.../openclaw-skill-clawhub/root",
|
||||
"sourcePathKind": "directory",
|
||||
"source": {
|
||||
"kind": "clawhub",
|
||||
"authority": "openclaw",
|
||||
"mutable": false,
|
||||
"network": true
|
||||
},
|
||||
"origin": {
|
||||
"type": "clawhub",
|
||||
"registry": "https://clawhub.openclaw.ai",
|
||||
"slug": "weather",
|
||||
"version": "1.0.0"
|
||||
},
|
||||
"request": {
|
||||
"kind": "skill-install",
|
||||
"mode": "install",
|
||||
"requestedSpecifier": "clawhub:weather@1.0.0"
|
||||
},
|
||||
"skill": {
|
||||
"installId": "clawhub"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Minimal policy command:
|
||||
|
||||
```js
|
||||
#!/usr/bin/env node
|
||||
|
||||
let input = "";
|
||||
process.stdin.setEncoding("utf8");
|
||||
process.stdin.on("data", (chunk) => {
|
||||
input += chunk;
|
||||
});
|
||||
process.stdin.on("end", () => {
|
||||
const request = JSON.parse(input);
|
||||
if (request.targetType === "plugin" && request.source?.kind === "local-path") {
|
||||
process.stdout.write(
|
||||
JSON.stringify({
|
||||
protocolVersion: 1,
|
||||
decision: "block",
|
||||
reason: "local plugin paths are not approved on this host",
|
||||
}),
|
||||
);
|
||||
return;
|
||||
}
|
||||
process.stdout.write(JSON.stringify({ protocolVersion: 1, decision: "allow" }));
|
||||
});
|
||||
```
|
||||
|
||||
## Bundled skill allowlist
|
||||
|
||||
<ParamField path="skills.allowBundled" type="string[]">
|
||||
Optional allowlist for **bundled** skills only. When set, only bundled
|
||||
skills in the list are eligible. Managed, agent-level, and workspace
|
||||
skills are unaffected.
|
||||
</ParamField>
|
||||
|
||||
## Per-skill entries (`skills.entries`)
|
||||
|
||||
Keys under `entries` match the skill `name` by default. If a skill defines
|
||||
`metadata.openclaw.skillKey`, use that key instead. Quote hyphenated names
|
||||
(JSON5 allows quoted keys).
|
||||
|
||||
<ParamField path="skills.entries.<key>.enabled" type="boolean">
|
||||
`false` disables the skill even when bundled or installed. The
|
||||
`coding-agent` bundled skill is opt-in — set it to `true` and ensure one of
|
||||
`claude`, `codex`, `opencode`, or another supported CLI is installed and
|
||||
authenticated.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.entries.<key>.apiKey" type='string | { source, provider, id }'>
|
||||
Convenience field for skills that declare `metadata.openclaw.primaryEnv`.
|
||||
Supports a plaintext string or a SecretRef: `{ source: "env", provider: "default", id: "VAR_NAME" }`.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.entries.<key>.env" type="Record<string, string>">
|
||||
Environment variables injected for the agent run. Only injected when the
|
||||
variable is not already set in the process.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.entries.<key>.config" type="object">
|
||||
Optional bag for custom per-skill configuration fields.
|
||||
</ParamField>
|
||||
|
||||
## Agent allowlists (`agents`)
|
||||
|
||||
Use agent config when you want the same machine/workspace skill roots but a
|
||||
different visible skill set per agent.
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
skills: ["github", "weather"], // shared baseline
|
||||
},
|
||||
list: [
|
||||
{ id: "writer" }, // inherits github, weather
|
||||
{ id: "docs", skills: ["docs-search"] }, // replaces defaults entirely
|
||||
{ id: "locked-down", skills: [] }, // no skills
|
||||
],
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
<ParamField path="agents.defaults.skills" type="string[]">
|
||||
Shared baseline allowlist inherited by agents that omit
|
||||
`agents.list[].skills`. Omit entirely to leave skills unrestricted by
|
||||
default.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="agents.list[].skills" type="string[]">
|
||||
Explicit final skill set for that agent. Explicit lists **replace**
|
||||
inherited defaults — they do not merge. Set to `[]` to expose no skills for
|
||||
that agent.
|
||||
</ParamField>
|
||||
|
||||
<Warning>
|
||||
Agent skill allowlists are a visibility and loading filter for OpenClaw
|
||||
skill discovery, prompts, slash-command discovery, sandbox sync, and skill
|
||||
snapshots. They are not a shell-time authorization boundary. If an agent
|
||||
can run host `exec`, that shell can still run external clients or read
|
||||
host files that are visible to the execution user, including MCP client
|
||||
registries such as `~/.openclaw/skills/config/mcporter.json`. For
|
||||
per-agent MCP isolation, combine skill allowlists with sandbox/OS-user
|
||||
isolation, deny or tightly allowlist host exec, and prefer per-agent
|
||||
credentials at the MCP server.
|
||||
</Warning>
|
||||
|
||||
## Workshop (`skills.workshop`)
|
||||
|
||||
<ParamField path="skills.workshop.autonomous.enabled" type="boolean" default="false">
|
||||
When `true`, agents can create pending proposals from durable conversation
|
||||
signals after successful turns. User-prompted skill creation always goes
|
||||
through Skill Workshop regardless of this setting.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.workshop.approvalPolicy" type='"pending" | "auto"' default='"pending"'>
|
||||
`pending` requires operator approval before agent-initiated apply, reject,
|
||||
or quarantine. `auto` allows those actions without approval.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.workshop.allowSymlinkTargetWrites" type="boolean" default="false">
|
||||
Allow Skill Workshop apply to write through workspace skill symlinks whose
|
||||
real target is already trusted by `skills.load.allowSymlinkTargets`. Keep
|
||||
this disabled unless generated proposal applies should mutate that shared
|
||||
skill root.
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.workshop.maxPending" type="number" default="50">
|
||||
Maximum pending and quarantined proposals retained per workspace (allowed
|
||||
range: 1-200).
|
||||
</ParamField>
|
||||
|
||||
<ParamField path="skills.workshop.maxSkillBytes" type="number" default="40000">
|
||||
Maximum proposal body size in bytes (allowed range: 1024-200000). Proposal
|
||||
descriptions are hard-capped at 160 bytes separately, because they appear
|
||||
in discovery and listing output.
|
||||
</ParamField>
|
||||
|
||||
See [Skill Workshop](/tools/skill-workshop) for the proposal lifecycle, CLI
|
||||
commands, agent tool parameters, and Gateway methods this config controls.
|
||||
|
||||
## Symlinked skill roots
|
||||
|
||||
By default, workspace, project-agent, extra-dir, and bundled skill roots are
|
||||
containment boundaries. A symlinked skill folder under `<workspace>/skills`
|
||||
that resolves outside the root is skipped with a log message.
|
||||
|
||||
To allow an intentional symlink layout, declare the trusted target:
|
||||
|
||||
```json5
|
||||
{
|
||||
skills: {
|
||||
load: {
|
||||
extraDirs: ["~/Projects/manager/skills"],
|
||||
allowSymlinkTargets: ["~/Projects/manager/skills"],
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
With this config, `<workspace>/skills/manager -> ~/Projects/manager/skills`
|
||||
is accepted after realpath resolution. `extraDirs` scans the sibling repo
|
||||
directly; `allowSymlinkTargets` preserves the symlinked path for existing
|
||||
layouts.
|
||||
|
||||
Skill Workshop apply does not write through those symlinks by default. To
|
||||
let Workshop apply mutate skills under already-trusted symlink targets, opt
|
||||
in separately:
|
||||
|
||||
```json5
|
||||
{
|
||||
skills: {
|
||||
load: {
|
||||
allowSymlinkTargets: ["~/Projects/manager/skills"],
|
||||
},
|
||||
workshop: {
|
||||
allowSymlinkTargetWrites: true,
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
Managed `~/.openclaw/skills` and personal `~/.agents/skills` directories
|
||||
already accept skill-directory symlinks unconditionally (per-skill
|
||||
`SKILL.md` containment still applies) — `allowSymlinkTargets` is only needed
|
||||
for workspace, extra-dir, and project-agent (`<workspace>/.agents/skills`)
|
||||
roots.
|
||||
|
||||
## Sandboxed skills and env vars
|
||||
|
||||
<Warning>
|
||||
`skills.entries.<skill>.env` and `apiKey` apply to **host** runs only.
|
||||
Inside a sandbox they have no effect — a skill that depends on
|
||||
`GEMINI_API_KEY` will fail with `apiKey not configured` unless the sandbox
|
||||
is given the variable separately.
|
||||
</Warning>
|
||||
|
||||
Pass secrets into a Docker sandbox with:
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
sandbox: {
|
||||
docker: {
|
||||
env: { GEMINI_API_KEY: "your-key-here" },
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
<Note>
|
||||
Users with Docker daemon access can inspect `sandbox.docker.env` values
|
||||
through Docker metadata. Use a mounted secret file, a custom image, or
|
||||
another delivery path when that exposure is not acceptable.
|
||||
</Note>
|
||||
|
||||
## Loading order reminder
|
||||
|
||||
```text
|
||||
workspace/skills (highest)
|
||||
workspace/.agents/skills
|
||||
~/.agents/skills
|
||||
~/.openclaw/skills
|
||||
bundled skills
|
||||
skills.load.extraDirs (lowest)
|
||||
```
|
||||
|
||||
Changes to skills and config take effect on the next new session when the
|
||||
watcher is enabled, or on the next agent turn when the watcher detects a
|
||||
change.
|
||||
|
||||
## Related
|
||||
|
||||
<CardGroup cols={2}>
|
||||
<Card title="Skills reference" href="/tools/skills" icon="puzzle-piece">
|
||||
What skills are, loading order, gating, and SKILL.md format.
|
||||
</Card>
|
||||
<Card title="Creating skills" href="/tools/creating-skills" icon="hammer">
|
||||
Authoring custom workspace skills.
|
||||
</Card>
|
||||
<Card title="Skill Workshop" href="/tools/skill-workshop" icon="flask">
|
||||
Proposal queue for agent-drafted skills.
|
||||
</Card>
|
||||
<Card title="Slash commands" href="/tools/slash-commands" icon="terminal">
|
||||
Native slash-command catalog and chat directives.
|
||||
</Card>
|
||||
</CardGroup>
|
||||
Reference in New Issue
Block a user