You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
99 lines
3.5 KiB
99 lines
3.5 KiB
#!/usr/bin/env python3 |
|
"""Parse agents.yaml and output agent info in shell-friendly format. |
|
|
|
Usage: |
|
python3 parse_agents.py list # list agent IDs |
|
python3 parse_agents.py info <id> # get agent info as KEY=VALUE |
|
python3 parse_agents.py services # list all agents with service details |
|
python3 parse_agents.py ids # space-separated agent IDs (for bash loops) |
|
""" |
|
|
|
import sys |
|
import yaml |
|
from pathlib import Path |
|
|
|
AGENTS_YAML = Path(__file__).resolve().parent.parent / 'agents.yaml' |
|
|
|
|
|
def load(): |
|
with open(AGENTS_YAML, 'r', encoding='utf-8') as f: |
|
return yaml.safe_load(f) or {} |
|
|
|
|
|
def cmd_list(data): |
|
for aid, agent in data.get('agents', {}).items(): |
|
print(f"{aid}\t{agent.get('type', 'unknown')}\t{agent.get('name', '')}") |
|
|
|
|
|
def cmd_ids(data): |
|
print(' '.join(data.get('agents', {}).keys())) |
|
|
|
|
|
def _shell_quote(val): |
|
"""Escape a value for safe bash eval: wrap in single quotes, escape inner quotes.""" |
|
s = str(val) |
|
return "'" + s.replace("'", "'\\''") + "'" |
|
|
|
|
|
def cmd_info(data, agent_id): |
|
agents = data.get('agents', {}) |
|
if agent_id not in agents: |
|
print(f"AGENT_FOUND=false", file=sys.stderr) |
|
sys.exit(1) |
|
a = agents[agent_id] |
|
svc = a.get('service', {}) |
|
defaults = data.get('defaults', {}) |
|
print(f"AGENT_ID={_shell_quote(agent_id)}") |
|
print(f"AGENT_NAME={_shell_quote(a.get('name', ''))}") |
|
print(f"AGENT_TYPE={_shell_quote(a.get('type', 'local-systemd'))}") |
|
print(f"PROFILE_DIR={_shell_quote(a.get('profile_dir', ''))}") |
|
print(f"WORKSPACE={_shell_quote(a.get('workspace', ''))}") |
|
print(f"ENV_FILE={_shell_quote(a.get('env_file', ''))}") |
|
print(f"IS_HUB={_shell_quote(str(a.get('is_hub', False)).lower())}") |
|
print(f"QDRANT_HOST={_shell_quote(a.get('qdrant_host', defaults.get('qdrant_host', 'localhost')))}") |
|
if a.get('type') == 'local-cli': |
|
print(f"CHECK_CMD={_shell_quote(svc.get('check_cmd', ''))}") |
|
print(f"START_CMD={_shell_quote(svc.get('start_cmd', ''))}") |
|
print(f"CHECK_PATTERN={_shell_quote(svc.get('check_pattern', ''))}") |
|
elif a.get('type') == 'local-systemd': |
|
unit = svc.get('unit', f"openclaw-gateway-{agent_id}.service") |
|
print(f"SYSTEMD_UNIT={_shell_quote(unit)}") |
|
elif a.get('type') == 'remote-http': |
|
print(f"HEALTH_URL={_shell_quote(svc.get('health_url', ''))}") |
|
print(f"TIMEOUT={_shell_quote(svc.get('timeout', 5000))}") |
|
|
|
|
|
def cmd_services(data): |
|
"""Output all agents in tab-separated format suitable for bash/JS parsing.""" |
|
agents = data.get('agents', {}) |
|
for aid, a in agents.items(): |
|
svc = a.get('service', {}) |
|
t = a.get('type', 'local-systemd') |
|
if t == 'local-cli': |
|
print(f"{aid}\t{t}\t{svc.get('check_cmd', '')}\t{svc.get('start_cmd', '')}\t{svc.get('check_pattern', '')}") |
|
elif t == 'local-systemd': |
|
unit = svc.get('unit', f"openclaw-gateway-{aid}.service") |
|
print(f"{aid}\t{t}\t{unit}") |
|
elif t == 'remote-http': |
|
print(f"{aid}\t{t}\t{svc.get('health_url', '')}\t{svc.get('timeout', 5000)}") |
|
|
|
|
|
if __name__ == '__main__': |
|
if len(sys.argv) < 2: |
|
print(__doc__) |
|
sys.exit(1) |
|
|
|
data = load() |
|
cmd = sys.argv[1] |
|
|
|
if cmd == 'list': |
|
cmd_list(data) |
|
elif cmd == 'ids': |
|
cmd_ids(data) |
|
elif cmd == 'info' and len(sys.argv) > 2: |
|
cmd_info(data, sys.argv[2]) |
|
elif cmd == 'services': |
|
cmd_services(data) |
|
else: |
|
print(__doc__) |
|
sys.exit(1)
|
|
|