🤖 codex: WIP agent-first templates (n/a)
What: - add agent-first templates and human/agent steps - embed full onboarding in README as single source of truth - remove indirection docs and template step files Why: - make onboarding executable for zero-context agents Tests: - not run (docs/templates only)
This commit is contained in:
parent
13c0bfd00c
commit
80c87822c7
81
README.md
81
README.md
@ -7,12 +7,83 @@ Declarative Clawdis for macOS via Nix, designed to be **agent‑first**.
|
||||
- This repo is a **public, generic** Nix package + Home Manager module for Clawdis.
|
||||
- It does **not** include or depend on any personal `nixos-config` or private machine setup.
|
||||
|
||||
## Start here
|
||||
## Agent‑first onboarding (the only supported path)
|
||||
|
||||
- Agent‑First Guide: `docs/agent-first.md`
|
||||
- Operator Reference: `docs/operator-reference.md`
|
||||
- RFC: `docs/rfc/2026-01-02-declarative-clawdis-nix.md`
|
||||
This README is the **single source of truth**. Do not look for other docs.
|
||||
|
||||
### Human‑in‑the‑loop (you must do these)
|
||||
|
||||
1) Create a Telegram bot token and save it to a file on disk.
|
||||
- Recommended path: `/run/agenix/telegram-bot-token`
|
||||
- If you do not use agenix, any readable file path works.
|
||||
2) Send a Telegram message to your bot from the chat(s) you want to allow.
|
||||
- This is required so chat IDs appear in Telegram’s updates feed.
|
||||
3) Provide these inputs to the agent (no guesswork):
|
||||
- macOS version
|
||||
- CPU architecture: `arm64` or `x86_64`
|
||||
- Home Manager configuration name (e.g. `myuser`)
|
||||
- Telegram bot token file path
|
||||
- Telegram allowFrom chat IDs (list of ints)
|
||||
|
||||
Do not proceed unless all inputs above are provided.
|
||||
|
||||
### Agent‑only steps (no human intervention)
|
||||
|
||||
1) Check if Determinate Nix is installed. If not, install it.
|
||||
- If `nix --version` fails, run:
|
||||
`curl -fsSL https://install.determinate.systems/nix | sh -s -- install`
|
||||
2) Enable flakes in `~/.config/nix/nix.conf`.
|
||||
- Ensure the directory exists: `mkdir -p ~/.config/nix`
|
||||
- Ensure this line exists: `experimental-features = nix-command flakes`
|
||||
3) Create a fresh local flake at `~/code/clawdis-local`.
|
||||
4) Copy the template file from this repo:
|
||||
- Source: `templates/agent-first/flake.nix`
|
||||
- Target: `~/code/clawdis-local/flake.nix`
|
||||
- Command: `cp templates/agent-first/flake.nix ~/code/clawdis-local/flake.nix`
|
||||
5) Replace placeholders in `~/code/clawdis-local/flake.nix`:
|
||||
- `<system>` = `aarch64-darwin` for arm64, `x86_64-darwin` for Intel
|
||||
- `<user>` = Home Manager configuration name
|
||||
- `<tokenPath>` = Telegram bot token file path
|
||||
- `<allowFrom>` = space‑separated list of ints
|
||||
- Do not leave any placeholders in the file.
|
||||
- After editing, re-open the file and verify there are no `<...>` strings left.
|
||||
6) Validate the token file exists and is non‑empty before proceeding.
|
||||
- If the file does not exist or is empty, stop and ask the human to fix it.
|
||||
7) If the human did not supply chat IDs, run the helper:
|
||||
- File: `templates/agent-first/get-telegram-chat-ids.py`
|
||||
- Command: `python3 templates/agent-first/get-telegram-chat-ids.py <tokenPath>`
|
||||
- Ask the human to pick which chat IDs to allow.
|
||||
- If the helper returns no chat IDs, stop and ask the human to send a message, then re‑run the helper.
|
||||
- If `python3` is missing, ask the human to install Xcode Command Line Tools.
|
||||
8) Run Home Manager:
|
||||
- If not installed: `nix run home-manager/release-24.11 -- init`
|
||||
- If this command fails, stop and ask the human for approval to proceed.
|
||||
- Then: `home-manager switch --flake .#<user>`
|
||||
9) Verify:
|
||||
- `launchctl print gui/$UID/com.nix-clawdis.gateway | grep state`
|
||||
- `tail -n 50 ~/.clawdis/logs/clawdis-gateway.log`
|
||||
10) Ask the human to send a test message and confirm a reply.
|
||||
|
||||
### Expected success signals
|
||||
|
||||
- `launchctl print` shows `state = running`.
|
||||
- Log file contains no fatal errors on startup.
|
||||
- Bot replies to a message in an allowlisted chat.
|
||||
|
||||
### Deterministic checklist (agent self‑test)
|
||||
|
||||
The agent’s work is correct **only if** all checks pass:
|
||||
|
||||
- A new local flake exists at `~/code/clawdis-local`.
|
||||
- That flake references `github:joshp123/nix-clawdis` as an input.
|
||||
- Home Manager config enables `programs.clawdis` with Telegram enabled.
|
||||
- Token is referenced by a file path (no inline secrets).
|
||||
- `launchctl print gui/$UID/com.nix-clawdis.gateway | grep state` shows `state = running`.
|
||||
- `~/.clawdis/logs/clawdis-gateway.log` shows startup without fatal errors.
|
||||
- A real Telegram message in an allowlisted chat receives a bot response.
|
||||
|
||||
If any item fails, the setup is incomplete.
|
||||
|
||||
## Status
|
||||
|
||||
This repo is being rebuilt to be fully declarative and agent‑first. The RFC is the source of truth.
|
||||
The RFC lives at `docs/rfc/2026-01-02-declarative-clawdis-nix.md` and defines success criteria.
|
||||
|
||||
@ -1,57 +1,5 @@
|
||||
# Agent‑First Guide (single prompt + deterministic checklist)
|
||||
# Agent‑First Guide
|
||||
|
||||
This repo is designed to be executed by a coding agent with **zero context**. Use the prompt below exactly as‑is.
|
||||
Single source of instructions: `templates/agent-first/steps.md`.
|
||||
|
||||
## Copy‑paste prompt (the only supported onboarding path)
|
||||
|
||||
```text
|
||||
You are setting up Clawdis on macOS using the public nix-clawdis repo.
|
||||
|
||||
Requirements:
|
||||
- Everything must be declarative and reproducible.
|
||||
- Do NOT touch any personal nixos-config or private repo.
|
||||
- Use a fresh, local flake directory (e.g. ~/code/clawdis-local).
|
||||
- Use Home Manager for user-level config.
|
||||
|
||||
Inputs (ask me to fill these in if missing):
|
||||
- macOS version:
|
||||
- Home Manager configuration name (e.g. "myuser"):
|
||||
- Telegram bot token file path:
|
||||
- Telegram allowFrom chat IDs (list of ints):
|
||||
|
||||
Steps you must perform:
|
||||
1) Check if Determinate Nix is installed; install it if missing.
|
||||
2) Enable flakes in ~/.config/nix/nix.conf.
|
||||
3) Create a local flake at ~/code/clawdis-local (do not use any personal config repo).
|
||||
4) Add nix-clawdis as a flake input and enable the Home Manager module.
|
||||
5) Wire the Telegram token file path and allowFrom list declaratively.
|
||||
6) Run home-manager switch for the configured user.
|
||||
7) Verify launchd status and logs:
|
||||
- launchctl print gui/$UID/com.nix-clawdis.gateway | grep state
|
||||
- tail -n 50 ~/.clawdis/logs/clawdis-gateway.log
|
||||
8) Smoke test: send a Telegram message in an allowlisted chat and confirm the bot replies.
|
||||
|
||||
Constraints:
|
||||
- Telegram-first only.
|
||||
- No ad-hoc JSON edits; config must be derived from Nix options.
|
||||
- Secrets must be passed as a file path (agenix-style).
|
||||
|
||||
Deliverables:
|
||||
- A working Clawdis gateway running via launchd.
|
||||
- A single, reproducible local flake that can be rebuilt on another machine.
|
||||
- A short summary of what was changed and how to verify it again.
|
||||
```
|
||||
|
||||
## Deterministic checklist (agent self‑test)
|
||||
|
||||
The agent’s work is correct **only if** all checks pass:
|
||||
|
||||
- A new local flake exists at `~/code/clawdis-local`.
|
||||
- That flake references `github:joshp123/nix-clawdis` as an input.
|
||||
- Home Manager config enables `programs.clawdis` with Telegram enabled.
|
||||
- Token is referenced by a file path (no inline secrets).
|
||||
- `launchctl print gui/$UID/com.nix-clawdis.gateway | grep state` shows `state = running`.
|
||||
- `~/.clawdis/logs/clawdis-gateway.log` shows startup without fatal errors.
|
||||
- A real Telegram message in an allowlisted chat receives a bot response.
|
||||
|
||||
If any item fails, the setup is incomplete.
|
||||
This guide intentionally contains **no code blocks**. All code lives in files under `templates/agent-first/`.
|
||||
|
||||
34
templates/agent-first/flake.nix
Normal file
34
templates/agent-first/flake.nix
Normal file
@ -0,0 +1,34 @@
|
||||
{
|
||||
description = "Clawdis local";
|
||||
|
||||
inputs = {
|
||||
nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
|
||||
home-manager.url = "github:nix-community/home-manager";
|
||||
home-manager.inputs.nixpkgs.follows = "nixpkgs";
|
||||
nix-clawdis.url = "github:joshp123/nix-clawdis";
|
||||
};
|
||||
|
||||
outputs = { self, nixpkgs, home-manager, nix-clawdis }:
|
||||
let
|
||||
system = "<system>";
|
||||
pkgs = import nixpkgs { inherit system; };
|
||||
in {
|
||||
homeManagerConfigurations.<user> = home-manager.lib.homeManagerConfiguration {
|
||||
inherit pkgs;
|
||||
modules = [
|
||||
nix-clawdis.homeManagerModules.clawdis
|
||||
{
|
||||
programs.clawdis = {
|
||||
enable = true;
|
||||
providers.telegram = {
|
||||
enable = true;
|
||||
botTokenFile = "<tokenPath>";
|
||||
allowFrom = [ <allowFrom> ];
|
||||
};
|
||||
routing.queue.mode = "interrupt";
|
||||
};
|
||||
}
|
||||
];
|
||||
};
|
||||
};
|
||||
}
|
||||
42
templates/agent-first/get-telegram-chat-ids.py
Normal file
42
templates/agent-first/get-telegram-chat-ids.py
Normal file
@ -0,0 +1,42 @@
|
||||
import json
|
||||
import sys
|
||||
import urllib.request
|
||||
|
||||
def die(msg):
|
||||
print(msg, file=sys.stderr)
|
||||
sys.exit(1)
|
||||
|
||||
if len(sys.argv) != 2:
|
||||
die("Usage: python3 get-telegram-chat-ids.py <tokenPath>")
|
||||
|
||||
token_path = sys.argv[1]
|
||||
try:
|
||||
with open(token_path, "r", encoding="utf-8") as f:
|
||||
token = f.read().strip()
|
||||
except FileNotFoundError:
|
||||
die(f"Token file not found: {token_path}")
|
||||
|
||||
if not token:
|
||||
die("Token file is empty")
|
||||
|
||||
url = f"https://api.telegram.org/bot{token}/getUpdates"
|
||||
try:
|
||||
with urllib.request.urlopen(url) as resp:
|
||||
data = json.loads(resp.read().decode("utf-8"))
|
||||
except Exception as exc:
|
||||
die(f"Failed to call Telegram API: {exc}")
|
||||
|
||||
results = data.get("result", [])
|
||||
chat_ids = []
|
||||
for entry in results:
|
||||
msg = entry.get("message") or entry.get("edited_message")
|
||||
if not msg:
|
||||
continue
|
||||
chat = msg.get("chat") or {}
|
||||
cid = chat.get("id")
|
||||
if cid is not None and cid not in chat_ids:
|
||||
chat_ids.append(cid)
|
||||
|
||||
print("Chat IDs:")
|
||||
for cid in chat_ids:
|
||||
print(cid)
|
||||
Loading…
Reference in New Issue
Block a user