Files

115 lines
6.0 KiB
YAML

# plane-agentd live configuration on the LXC agentd-01 (/opt/plane-agentd, runs as root; docs/deploy-lxc.md).
# No secrets: token_key / ssh_key values are Vault key names; the values are injected by
# `agent-access.py exec --secret-env KEY=KEY` (cron/agentd-tick-lxc.sh). Rollback to oregon: config/agentd.oregon.yaml.
plane: {base_url: https://plane.kappiee.com, workspace: kappiee}
vault: {client: ~/.local/share/server-access-client/agent-access.py, config: https://nas.tail9531b.ts.net:8443/identity/agent.json}
agentd:
state_dir: /var/lib/plane-agentd # JSON state, heartbeat.json, lock
log_dir: /var/log/plane-agentd # agentd.log (cron output: cron.log, same dir)
helpers_dir: tools/win10 # win10-ps.sh / win10-put.sh (Windows terminals only); relative = repo
interval: 120
max_rounds_per_thread: 8
comment_max_chars: 6000
cli_terminal: oregon
# direct-ssh (PAD-12, docs/deploy-lxc.md "直连 SSH"): the dedicated key comes from Vault AGENTD_SSH_KEY via
# --secret-env; ControlMaster sockets and the known_hosts generated from the pinned host keys live in ssh_dir
ssh_key: AGENTD_SSH_KEY
ssh_dir: /run/plane-agentd/ssh
# Plane webhook receiver (`agentd webhook-serve`, systemd plane-agentd-webhook.service; docs/runbook.md "Webhook").
# One workspace-level Plane webhook (work items + comments) -> POST http://10.77.10.249:8790/plane -> one tick.
webhook:
bind: 10.77.10.249 # LAN only (Plane VM 506 10.77.10.69 is on the same /24)
port: 8790
path: /plane
secret_key: PLANE_WEBHOOK_SECRET # Vault key name; the value is injected by agent-access.py exec --secret-env
# the cron script holds `flock -n -E 75`; --scope moves the tick out of the receiver's cgroup, so restarting the
# receiver never kills a running tick
tick_command: [systemd-run, --scope, --quiet, --collect, /opt/plane-agentd/cron/agentd-tick-lxc.sh]
debounce_seconds: 3 # deliveries within this window -> one tick
retry_seconds: 15 # lock busy -> retry every 15 s ...
retry_window_seconds: 120 # ... for up to 2 min; then the cron tick covers it
notify: {kind: none} # notification hook, no-op (no ntfy service); core calls it on every state move
terminals:
win10:
# direct over Tailscale (PAD-12); Warpgate only when the direct path fails before a command ran.
# Rollback: transport: warpgate-ssh (ssh/fallback may stay, they are ignored then)
transport: direct-ssh
ssh: {host: 100.123.209.19, user: administrator, port: 22,
host_key: "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFzLX7QNHDFYwTgY4wNl0ihZryIyKgpp9HPpPDWbrTX3"}
fallback: warpgate-ssh
target: win10 # Warpgate target of the fallback
os: windows
launch: schtasks
repo: 'C:\Users\Administrator\Documents\GwentAssistantProject\gwent'
run_root: 'C:\Users\Administrator\Documents\GwentAssistantProject\gwent\runtime\agentd'
bins: {codex: 'C:\Users\Administrator\AppData\Local\Programs\OpenAI\Codex\bin\codex.exe'}
plane_user: window10
token_key: PLANE_WINDOW10_API_TOKEN
concurrency: 1
busy_processes: [codex] # do not start while a codex.exe agentd did not start is running
capabilities: [android, game]
executors: [codex]
oregon:
# the dispatcher (LXC, no agent CLIs) reaches oregon directly over Tailscale, Warpgate as fallback (design §9)
transport: direct-ssh
ssh: {host: 100.127.58.78, user: ubuntu, port: 22,
host_key: "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICUoI6W7npX+h/kHcXX3iy2XAWbNusrOjg28Xed75wWr"}
fallback: warpgate-ssh
target: oregon # agent-access.py target name (fallback)
os: linux
launch: nohup
repo: /home/ubuntu/Documents/wjj/project/gwent
run_root: /home/ubuntu/.gwent-board/agentd-runs # absolute: the remote shell does not expand ~ inside quotes
plane_user: oregon
token_key: PLANE_OREGON_API_TOKEN
concurrency: 1 # one shared worktree: no parallel edits
bins: {claude: /home/ubuntu/.local/bin/claude} # the SSH non-login shell has the system PATH only; no codex on oregon
executors: [claude-code]
executors:
codex:
adapter: codex
run: "codex exec --json -C '{repo}' -s workspace-write -m {model} -c 'model_reasoning_effort=\"{effort}\"' {tier} -o '{out}' -"
# `exec resume` takes no -C/-s: the runner already cd's into the repo, the sandbox goes in as a -c override
resume: "codex exec resume {thread} --json -m {model} -c 'model_reasoning_effort=\"{effort}\"' -c 'sandbox_mode=\"workspace-write\"' {tier} -o '{out}' -"
tier_arg: "-c 'service_tier=\"{tier}\"'"
tier_defaults: {gpt-6.1-sol: fast} # tier when no label sets one (`tier:<x>`, `tier:none` = no tier)
thread_from: events.jsonl:thread.started.thread_id
last_message: '{out}'
models: [gpt-6.1-sol, gpt-6-astra]
default_effort: medium
claude-code:
adapter: claude-code
run: "claude -p --model {model} --output-format json --permission-mode {perm}"
resume: "claude -p --resume {thread} --model {model} --output-format json --permission-mode {perm}"
permission_mode: acceptEdits
thread_from: json:session_id
last_message: json:result
models: [sonnet, opus, haiku]
projects:
GWENT:
id: 79cb5a60-aa4f-4138-9864-1dd70426e665
key_prefix: GW
states: {backlog: Backlog, todo: Todo, running: In Progress, waiting: Waiting, review: Review, done: Done}
reviewer: oregon
answerer: oregon
protocol_file: config/protocols/gwent-board-protocol.md # relative = repo; refresh from gwent/design/board-protocol.md
routing:
by_assignee: {window10: win10, oregon: oregon}
by_label:
'model:astra': {model: gpt-6-astra, effort: high}
'model:sol': {model: gpt-6.1-sol, tier: fast}
'effort:high': {effort: high}
'needs-game': {serialize_group: game}
default_executor: {win10: codex, oregon: claude-code}
retry:
transient_max: 3
backoff_minutes: [2, 5, 10]
timeout_hours: 4
max_rounds_per_thread: 8
max_progress_rounds: 12