OpenClaw skills, heartbeat autonomy, and approval gates
Intermediate10 min readAutomations

OpenClaw skills, heartbeat autonomy, and approval gates

How OpenClaw skills load, how heartbeat periodic turns work, how to gate host shell execution, and how to keep browser automation behind restrictive policy and reviewed workflow confirmation.

What you should be able to do

Skills teach the agent how to work. Heartbeat gives it a pulse. Exec policy gates host shell access; browser policy, profile isolation, and workflow confirmation govern browser actions.

Saved only in this browser.
In this article

Once OpenClaw is installed and channel identity is locked down (setup, allowlists and pairing), the next layer is capability: skills, periodic heartbeat turns, host-shell approval policy, and whether browser automation is enabled inside a reviewed workflow.

Docs anchors: Skills, Heartbeat, Security.

Heartbeat plus unrestricted host exec, or browser automation with valuable signed-in state, creates unattended action using the credentials and access exposed to that surface. Enable periodic turns only after tool policy matches your threat model, especially if any channel other than you can trigger the agent.

Skills: what they are

Skills are markdown instruction packages (SKILL.md with YAML frontmatter + body) that teach the agent how and when to use tools. OpenClaw loads bundled skills plus local overrides, and filters them at load time based on environment, config, and whether required binaries exist.

Precedence (highest first), per current docs:

  1. Workspace skills
  2. Project agent skills
  3. Personal agent skills (~/.agents/skills in default state)
  4. Managed / local skills under the OpenClaw state dir
  5. Bundled skills
  6. Extra directories / plugin skills

When the same skill name appears in multiple places, the higher source wins. Treat skill folders as trusted code: anyone who can modify them can change agent behaviour.

Allowlists for which skills an agent sees

Location (precedence) and visibility (per-agent allowlist) are separate. Example shape from the docs:

{
  agents: {
    defaults: {
      skills: ['github', 'weather'],
    },
    list: [
      { id: 'writer' },
      { id: 'docs', skills: ['docs-search'] },
      { id: 'locked-down', skills: [] },
    ],
  },
}

Omit default skill lists only when you intentionally want a wide surface. For personal gateways, start narrow: skills you have read, that match binaries you install, for jobs you actually run.

Community skills and plugins are a supply chain. Installing them can run code and widen tools. Prefer official docs and skills you have reviewed; use security.installPolicy if you enforce operator-owned host-side allow/block decisions.

Node-hosted skills appear only while the paired node is connected. Their files, referenced paths, and binaries remain on that node, and execution uses exec host=node node=<node-id>. Initial node-role pairing approves skill publication; later skill changes require a node restart, not re-pairing. The agent’s exec policy and the node’s host-local approval policy still govern execution.

Heartbeat: a pulse, not a second brain

Heartbeat runs periodic agent turns in the main session so the model can surface anything that needs attention without spamming you. It is a scheduled main-session turn, not a background task record.

Defaults (verify on your version):

  • Interval often 30m (Anthropic OAuth/token setups may default higher when unset; docs describe 1h in that case)
  • Set agents.defaults.heartbeat.every (use 0m to disable)
  • Default prompt tells the agent to follow heartbeat monitor scratch, not invent recurring work from old chats, and reply HEARTBEAT_OK when nothing needs attention

Example:

{
  agents: {
    defaults: {
      heartbeat: {
        every: '30m',
        target: 'none',
        lightContext: true,
        isolatedSession: true,
        // activeHours: { start: "08:00", end: "22:00" },
      },
    },
  },
}

Practical guidance:

  • Keep target: "none" until you want deliveries; set target: "last" only when you accept pings to the last contact.
  • Use activeHours so night-time pulses stay quiet in your timezone.
  • Put recurring work in automations / cron jobs, not in heartbeat scratch folklore; heartbeat docs emphasise that split.
  • Scheduled heartbeats require automations enabled; if cron is disabled, scheduled heartbeats do not run.

Response contract: HEARTBEAT_OK (at start/end) is treated as an ack and suppressed when remaining content is short. Alerts should omit HEARTBEAT_OK and return only the alert text.

Heartbeat turns still use whatever tools the agent can access. A “harmless check-in” with exec allowed is still a scheduled opportunity for prompt-injected content in memory or fetched pages to request shell actions. Pair heartbeat with tool deny/ask policies.

Approval gates for shell and browser

OpenClaw’s security model treats exec approvals as guardrails for operator intent, not as hostile multi-tenant isolation. Still, for personal gateways they are the difference between “ask me” and “just run it.”

Exec

Relevant controls from the current exec approvals reference; confirm them in the schema shipped with your installed version:

  • tools.exec.mode is the canonical persisted host-exec policy: deny, allowlist, ask, auto, or full.
  • auto sends approval misses through OpenClaw’s native reviewer before a human fallback. It is a convenience path, not a proof that a command is safe.
  • Gateway and node execution also consult the local approvals document on the execution host. Effective policy is the stricter of config and that host-local document.
  • askFallback applies when a prompt is required but no UI is reachable or it times out. It defaults to deny; keep it there so loss of the approval route does not widen access.
  • Allowlists are per agent. Use narrow executable paths and argPattern where appropriate; strictInlineEval adds defense in depth when interpreters are allowlisted.
  • tools.exec.host: "auto" resolves to the sandbox when one is active and to the Gateway otherwise. Node execution requires a paired node and its own host-local approval state.

Start with tools.exec.mode: "deny", or mode: "ask" plus an equally restrictive host-local approvals document when you need prompts, and keep elevated tools off. Gateway and node host execution otherwise defaults to full, while sandbox host execution defaults to deny. Tighten the host policy before channels, skills, or heartbeat widen the blast radius.

Node system.run on a paired Mac is remote code execution on that Mac. Pairing is not a per-command approval; the Gateway’s node command policy and the node’s own exec approvals form the execution boundary. To disable remote shell execution, set requested exec mode to deny and keep the node’s host-local approval policy restrictive, or remove the node role and pairing if you do not need it.

Browser

Browser control is an operator-grade surface (navigate, read pages, evaluate). Treat remote browser/CDP exposure like operator access: loopback or a deliberately protected private path, no public CDP/control endpoint. Use the dedicated openclaw browser profile, which is isolated from your daily browser profile, and keep the browser plugin/tool off until a reviewed task needs it. Exec approvals do not create a per-click browser approval boundary; require human confirmation in the workflow before consequential submits, purchases, publishing, or account changes.

Prompt injection via fetched pages is a first-class risk. Tool allow/deny policy, browser profile isolation, explicit workflow confirmation, and sandboxing reduce the blast radius; they do not remove the need for channel allowlists.

Elevated tools

tools.elevated escapes the sandbox. Keep allowFrom tight. Do not enable elevated mode for strangers or broad channel populations.

A sane autonomy ladder

StageSkillsHeartbeatExec / browser
0: chat onlynone / messaging profileoff (0m)mode: deny
1: assistedfew reviewed skillsoffmode: ask; browser off
2: light pulsesame30m to 1h, target: none, active hoursmode: ask; browser off
3: ops assistallowlisted skillsdelivers alerts to you onlymode: allowlist or ask; isolated browser only for reviewed tasks
4: wide autonomyonly with auditonly with sandbox + deny listsmode: full only for a single operator with no open DMs

Move up a stage only after openclaw security audit and enough retained runs to exercise normal work, denial paths, approval timeout, and recovery. A fixed number of days is not proof of safety.

Writing a small internal skill

A minimal useful skill is a folder with SKILL.md:

---
name: disk-check
description: Check disk usage on the gateway host when asked about disk or capacity.
---

When the user asks about disk space on this host:

1. Run only the allowlisted `df` invocation your exec policy permits.
2. Summarise filesystem use in three bullets.
3. Do not install packages or delete files.

Keep the description concrete so the agent knows when to use it. Pair the skill with a narrow exec mode, reviewed per-agent command and argument rules, strictInlineEval, and sandbox or OS isolation. These controls reduce the command surface; they do not prove that an allowed interpreter or helper cannot perform destructive work. Prefer workspace skills you control over grabbing every ClawHub package that looks convenient.

What to put in heartbeat scratch (and what not to)

Use the heartbeat monitor scratch (openclaw cron scratch <jobId> --set "...") as a short checklist, not a second task database:

Good: “If disk > 90% on gateway host, notify. If nothing, HEARTBEAT_OK.” Bad: “Remember to finish the Q3 roadmap, email Alice, refactor the agent, and scrape competitor pricing.”

Recurring work belongs in automations with their own schedules. Heartbeat that re-infers chores from old chats is how quiet installs become noisy and expensive.

Testing approvals before you trust them

  1. Set tools.exec.mode to deny for a fail-closed test, or to ask with a host-local approval document that is at least as restrictive when you want a prompt.
  2. From your allowlisted DM, ask the agent to run uname (or an equivalent harmless probe).
  3. Confirm you get a clean denial or an approval prompt, not a silent success.
  4. If testing prompts, let one request time out or make the UI unavailable and confirm askFallback: "deny" blocks it. When effective ask policy is always, confirm the next distinct command asks again.
  5. If a node is paired, repeat the test against that node’s separately stored approval policy.
  6. From a non-allowlisted identity, confirm no tool path exists.

If step 3 succeeds without the configured gate, inspect both the requested exec mode and the execution host’s local approvals document before enabling heartbeat.

Combine with n8n when the job is scheduled plumbing

Heartbeat is for agent-aware check-ins. Deterministic SaaS polls, retries, and human gates often belong in n8n (idempotency and human gates, Hermes API or webhook handoff). Use OpenClaw when the interface is chat; use n8n when the interface is systems.

Operator checklist

  • Skill allowlists reviewed; unused skills removed
  • No untrusted skill directories writable by others
  • Heartbeat interval and active hours set intentionally
  • Heartbeat target does not spam group channels
  • tools.exec.mode is deny or ask, and the execution host’s local approvals document is equally or more restrictive
  • Browser/search/fetch off unless required
  • Elevated tools off
  • Approval path tested with a harmless command
  • Audit re-run after each autonomy increase

Skills make the agent competent. Heartbeat makes it timely. Restrictive exec policy, browser policy, sandboxing, and channel identity controls reduce the chance that competence and timing become unattended host action. Turn the dials in that order, and only as far as your threat model justifies.

Read next

Continue through the same learning path with the next practical articles.