Files
ContractorAgent/docs/claude/CLI.md

7.6 KiB

Contractor Agents CLI Design

Purpose

Define the plugin-owned CLI surface for managing contractor-backed OpenClaw agents.

Phase 1 supports Claude only. Gemini remains reserved in the command shape but is not implemented yet.

Command root

openclaw contractor-agents

This should be implemented as a plugin-owned CLI root, not as a patch to openclaw agents add.

Why a separate command root

Current OpenClaw plugin docs show support for plugin CLI registration, but do not document support for extending existing core commands with new flags.

Relevant doc statements:

"Common registration methods: ... registerCommand / registerCli | CLI commands"

"For plugin-owned root CLI commands, prefer api.registerCli(..., { descriptors: [...] }) ..."

This suggests the supported extension seam is plugin-owned CLI trees.

Sources:

Phase 1 command

openclaw contractor-agents add --agent-id <agent-id> --workspace <workspace> --contractor <claude|gemini>

Phase 1 restrictions:

  • --contractor must currently be claude
  • gemini is accepted only as a reserved future value if desired, but should currently fail with a clear not-yet-implemented message unless you intentionally decide to reject it at parsing time

Arguments

Required

  • --agent-id <agent-id>
  • --workspace <workspace>
  • --contractor <claude|gemini>

Optional, possible later

Not required for first implementation, but likely useful later:

  • --bridge-model <model-id>
  • --backend <acp-backend>
  • --mode <persistent|oneshot>
  • --json
  • --non-interactive

For now, phase 1 can hardcode the bridge model and runtime defaults.

Behavior of add

For:

openclaw contractor-agents add --agent-id my-agent --workspace /path/to/ws --contractor claude

The CLI should do the following.

Step 1, validate inputs

  • ensure agent-id is provided
  • ensure workspace exists or is creatable, based on your desired policy
  • ensure contractor kind is supported
  • ensure target agent does not already exist unless overwrite behavior is explicitly added later

Step 2, create the base OpenClaw agent

Run the equivalent of:

openclaw agents add <agent-id> --workspace <workspace> --model contractor-claude-bridge --non-interactive

Important note:

Earlier review of openclaw agents add docs showed these supported options:

--workspace <dir> --model <id> --agent-dir <dir> --bind <channel[:accountId]> --non-interactive --json

Source:

This means the contractor CLI can compose the existing agent creation flow rather than replacing it.

Step 3, mark the agent as a contractor-backed agent

After agent creation, write contractor metadata so runtime selection and session bridging can identify this agent as contractor-managed.

Proposed config direction:

{
  agents: {
    list: [
      {
        id: "my-agent",
        model: "contractor-claude-bridge",
        runtime: {
          type: "contractor",
          contractor: {
            kind: "claude",
            backend: "acp",
            mode: "persistent"
          }
        }
      }
    ]
  }
}

Exact schema is still TBD, but the CLI should be the mechanism that writes this state.

Step 4, initialize contractor runtime state

Prepare runtime state for the agent, including a place to store session mappings.

Suggested path:

<workspace>/.openclaw/contractor-agent/

Suggested initial files:

session-map.json
runtime.json

Session mapping responsibility

The CLI does not create Claude sessions immediately unless you explicitly want eager setup.

Recommended phase 1 behavior:

  • create agent metadata
  • create runtime state directory
  • initialize empty mapping file
  • defer real Claude session creation to first actual agent turn

This keeps add lightweight and avoids unused contractor sessions.

Suggested future commands

These are not required immediately, but the command tree should reserve room for them.

Status

openclaw contractor-agents status --agent-id <agent-id>

Show:

  • contractor kind
  • bridge model id
  • runtime backend
  • session mapping count
  • recent activity

List sessions

openclaw contractor-agents sessions --agent-id <agent-id>

Show session mappings for the given contractor-backed agent.

Reset mapping

openclaw contractor-agents reset-session --agent-id <agent-id> --openclaw-session <session-key>

Drop a specific OpenClaw-to-Claude mapping so the next message recreates the Claude session.

Disable

openclaw contractor-agents disable --agent-id <agent-id>

Either:

  • remove contractor metadata but keep agent
  • or mark the contractor runtime disabled

Semantics TBD.

JSON output

I recommend all subcommands eventually support --json so this can be scripted.

Example success response shape:

{
  "ok": true,
  "agentId": "my-agent",
  "workspace": "/path/to/ws",
  "contractor": "claude",
  "model": "contractor-claude-bridge",
  "runtimeStateDir": "/path/to/ws/.openclaw/contractor-agent"
}

Failure cases

The CLI should fail clearly for:

  • unsupported contractor kind
  • agent already exists
  • workspace invalid or inaccessible
  • bridge model plugin not available
  • failure in underlying openclaw agents add
  • failure writing contractor metadata

If the agent is created successfully but metadata writing fails, the CLI should either:

  • roll back the created agent if safe and simple
  • or return a partial-failure error with explicit cleanup instructions

Phase 1 recommendation: prefer explicit rollback if implementation is reliable.

Interaction with the bridge model

The CLI should not directly run Claude Code or create a Claude contractor session by default.

Its main job is to provision an agent whose primary model is the contractor bridge model:

  • contractor-claude-bridge

That model then handles runtime dispatch during actual conversation turns.

Implementation notes

The plugin should register a root command owned by the plugin.

Relevant doc statements:

"For plugin-owned root CLI commands, prefer api.registerCli(..., { descriptors: [...] }) when you want the command to stay lazy-loaded without disappearing from the root CLI parse tree."

Source:

So the intended shape is:

  • plugin registers contractor-agents
  • plugin owns parsing and handling of its subcommands
  • plugin composes openclaw agents add behavior internally or via shared config/runtime helpers

Open questions

  1. Should the CLI shell out to openclaw agents add or use a lower-level config/runtime helper directly?
  2. Where should contractor metadata live, agents.list[].runtime, plugin config, or both?
  3. Should gemini be rejected now or accepted with a not implemented error?
  4. Should add create the workspace if it does not exist?
  5. Should agent creation be rolled back if contractor metadata writing fails?

References

Plugin CLI support

"Common registration methods: ... registerCommand / registerCli | CLI commands"

Source:

Plugin-owned CLI descriptors

"For plugin-owned root CLI commands, prefer api.registerCli(..., { descriptors: [...] }) ..."

Source:

Existing agent creation command

agents add [name]

--workspace <dir> --model <id> --agent-dir <dir> --bind <channel[:accountId]> --non-interactive --json

Source: