feat(security): add client-side skill security enforcement

Add a capability-based security model for community skills, inspired by
how mobile and Apple ecosystem apps declare capabilities upfront. This is
not a silver bullet for prompt injection, but it's a significant step up
from the status quo and encourages responsible developer practices by
making capability requirements explicit and visible.

Runtime enforcement for community skills installed from ClawHub:

- Capability declarations (shell, filesystem, network, browser, sessions)
  parsed from SKILL.md frontmatter and enforced at tool-call time
- Static SKILL.md scanner detecting prompt injection patterns, suspicious
  constructs, and capability mismatches
- Global skill security context tracking loaded community skills and
  their aggregate capabilities
- Before-tool-call enforcement gate blocking undeclared tool usage
- Command-dispatch capability check preventing shell/filesystem access
  without explicit declaration
- Trust tier classification (builtin/community/local) — only community
  skills are subject to enforcement
- System prompt trust context warning for skills with scan warnings or
  missing capability declarations
- CLI: `skills list -v`, `skills info`, `skills check` now surface
  capabilities, scan results, and security status
- TUI security log panel for skill enforcement events
- Docs updated across 7 files covering the full security model

Companion PR: openclaw/clawhub (capability visibility + UI badges)
This commit is contained in:
theonejvo
2026-02-17 02:26:41 +11:00
parent 602a1ebd55
commit 2c61fb69c1
29 changed files with 1571 additions and 120 deletions

View File

@@ -35,3 +35,64 @@ export const DANGEROUS_ACP_TOOL_NAMES = [
] as const;
export const DANGEROUS_ACP_TOOLS = new Set<string>(DANGEROUS_ACP_TOOL_NAMES);
// ---------------------------------------------------------------------------
// Skill capability → tool group mapping.
// Maps human-readable capability names (declared in SKILL.md frontmatter) to
// the existing TOOL_GROUPS in tool-policy.ts.
//
// CLAWHUB ALIGNMENT: Keep in sync with clawhub/convex/lib/skillCapabilities.ts.
// Both OpenClaw and ClawHub validate against the same capability names.
// ---------------------------------------------------------------------------
export const CAPABILITY_TOOL_GROUP_MAP: Record<string, string> = {
shell: "group:runtime", // exec, process
filesystem: "group:fs", // read, write, edit, apply_patch
network: "group:web", // web_search, web_fetch
browser: "group:ui", // browser, canvas
sessions: "group:sessions", // sessions_spawn, sessions_send, subagents, etc.
messaging: "group:messaging", // message
scheduling: "group:scheduling", // cron
};
/**
* Tools always denied when community skills are loaded, regardless of
* capability declarations. These are control-plane / infrastructure tools
* that no community skill should ever touch.
*/
export const COMMUNITY_SKILL_ALWAYS_DENY = [
"gateway", // control-plane reconfiguration
"nodes", // device/node control
] as const;
export const COMMUNITY_SKILL_ALWAYS_DENY_SET = new Set<string>(COMMUNITY_SKILL_ALWAYS_DENY);
/**
* Tools that require an explicit capability declaration from community skills.
* If a community skill doesn't declare the matching capability, these tools
* are blocked at runtime by the before-tool-call hook.
*/
export const DANGEROUS_COMMUNITY_SKILL_TOOLS = [
// shell capability
"exec",
"process",
"lobster",
// filesystem capability (mutations only — read is safe and always allowed)
"write",
"edit",
"apply_patch",
// network capability
"web_fetch",
"web_search",
// browser capability
"browser",
// sessions capability
"sessions_spawn",
"sessions_send",
"subagents",
// messaging capability
"message",
// scheduling capability
"cron",
] as const;
export const DANGEROUS_COMMUNITY_SKILL_TOOL_SET = new Set<string>(DANGEROUS_COMMUNITY_SKILL_TOOLS);