diff --git a/workspace/skills/clawgo-node-child/SKILL.md b/workspace/skills/clawgo-node-child/SKILL.md new file mode 100644 index 0000000..8d8853a --- /dev/null +++ b/workspace/skills/clawgo-node-child/SKILL.md @@ -0,0 +1,34 @@ +--- +name: clawgo-node-child +description: Deploy and register a clawgo child node to a parent clawgo gateway without ad-hoc Python agents. Use when setting up sub-nodes, syncing provider settings from parent to child, enabling reverse tunnel fallback, and validating parent-dispatched nodes actions (describe/run/invoke/agent_task). +--- + +# Clawgo Node Child + +Use built-in clawgo services only. Do not create `node_agent.py`. + +## Execute + +1. Run `scripts/deploy_child.sh` on the operator host with env vars: + - `PARENT_HOST` `PARENT_PASS` + - `CHILD_HOST` `CHILD_PASS` + - Optional: `PARENT_GATEWAY_PORT` (default `18790`), `RELAY_PORT` (default `17789`), `CHILD_PORT` (default `7789`), `NODE_ID` (default `node-child`) +2. Script will: + - Copy `/usr/local/bin/clawgo` from parent to child + - Sync `providers` + `agents.defaults` into child `/root/.clawgo/provider-sync.json` + - Create child gateway config `/root/.clawgo/config.child.json` + - Install/start child service `clawgo-child-gateway.service` + - Install/start reverse tunnel service `clawgo-child-revtunnel.service` + - Register child node to parent `/nodes/register` + - Install child heartbeat cron (`/nodes/heartbeat` every minute) +3. Validate from parent: + - Health: `curl http://127.0.0.1:${RELAY_PORT}/health` + - Task dispatch: `clawgo agent` + `nodes action=agent_task node= mode=relay ...` + +## Notes + +- Prefer direct endpoint if reachable; keep reverse tunnel as fallback. +- If parent and CLI visibility differ, ensure node state persistence is enabled (`memory/nodes-state.json`). +- If child service fails, check: + - `journalctl -u clawgo-child-gateway.service -n 100 --no-pager` + - `journalctl -u clawgo-child-revtunnel.service -n 100 --no-pager` diff --git a/workspace/skills/clawgo-node-child/scripts/deploy_child.sh b/workspace/skills/clawgo-node-child/scripts/deploy_child.sh new file mode 100755 index 0000000..9e9097a --- /dev/null +++ b/workspace/skills/clawgo-node-child/scripts/deploy_child.sh @@ -0,0 +1,95 @@ +#!/usr/bin/env bash +set -euo pipefail + +: "${PARENT_HOST:?need PARENT_HOST}" +: "${PARENT_PASS:?need PARENT_PASS}" +: "${CHILD_HOST:?need CHILD_HOST}" +: "${CHILD_PASS:?need CHILD_PASS}" + +PARENT_GATEWAY_PORT="${PARENT_GATEWAY_PORT:-18790}" +RELAY_PORT="${RELAY_PORT:-17789}" +CHILD_PORT="${CHILD_PORT:-7789}" +NODE_ID="${NODE_ID:-node-child}" + +SSHP_PARENT=(sshpass -p "$PARENT_PASS" ssh -o StrictHostKeyChecking=no "root@${PARENT_HOST}") +SSHP_CHILD=(sshpass -p "$CHILD_PASS" ssh -o StrictHostKeyChecking=no "root@${CHILD_HOST}") + +# 1) Copy clawgo binary parent -> local -> child +sshpass -p "$PARENT_PASS" scp -o StrictHostKeyChecking=no "root@${PARENT_HOST}:/usr/local/bin/clawgo" /tmp/clawgo_child +sshpass -p "$CHILD_PASS" scp -o StrictHostKeyChecking=no /tmp/clawgo_child "root@${CHILD_HOST}:/usr/local/bin/clawgo" +"${SSHP_CHILD[@]}" "chmod +x /usr/local/bin/clawgo" + +# 2) Sync providers + agents.defaults from parent +"${SSHP_PARENT[@]}" "python3 - <<'PY' +import json +c=json.load(open('/root/.clawgo/config.json')) +p={'providers':c.get('providers',{}),'agents_defaults':c.get('agents',{}).get('defaults',{})} +print(json.dumps(p,ensure_ascii=False)) +PY" > /tmp/provider-sync.json +cat /tmp/provider-sync.json | "${SSHP_CHILD[@]}" "mkdir -p /root/.clawgo && cat > /root/.clawgo/provider-sync.json" + +# 3) Build child config (no ad-hoc python server) +"${SSHP_CHILD[@]}" "python3 - <<'PY' +import json +src='/root/.clawgo/provider-sync.json' +out='/root/.clawgo/config.child.json' +d=json.load(open(src)) +cfg={ + 'gateway': {'host':'0.0.0.0','port': ${CHILD_PORT}}, + 'providers': d.get('providers',{}), + 'agents': {'defaults': d.get('agents_defaults',{})}, + 'channels': {}, + 'tools': {'shell': {'enabled': True}}, + 'logging': {'level':'info'} +} +json.dump(cfg, open(out,'w'), ensure_ascii=False, indent=2) +print(out) +PY" + +# 4) Install child gateway service +"${SSHP_CHILD[@]}" "cat > /etc/systemd/system/clawgo-child-gateway.service < parent) +"${SSHP_CHILD[@]}" "yum install -y sshpass >/dev/null 2>&1 || true" +"${SSHP_CHILD[@]}" "cat > /etc/systemd/system/clawgo-child-revtunnel.service </dev/null; echo '*/1 * * * * curl -s -X POST http://${PARENT_HOST}:${PARENT_GATEWAY_PORT}/nodes/heartbeat -H \"Content-Type: application/json\" -d \"{\\\"id\\\":\\\"${NODE_ID}\\\"}\" >/dev/null 2>&1') | crontab -" + +echo "DONE: ${NODE_ID} deployed"