@delorenj/pjangler 1.2.21 → 1.2.25
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +1852 -368
- package/dist/mcp-server.js +1782 -296
- package/package.json +14 -3
- package/templates/commonproject/copier.yml +3 -0
- package/templates/commonproject/template/.mise/scripts/provision-bmad-skills.py +480 -0
- package/templates/commonproject/template/.mise/scripts/sync-skills.py +449 -0
- package/templates/commonproject/template/mise.toml.jinja +9 -2
- package/templates/commonproject/tests/test_provision_bmad_skills.py +203 -0
- package/templates/commonproject/tests/test_sync_skills_topology.py +120 -0
- package/templates/hermes-agent/README.md +70 -29
- package/templates/hermes-agent/copier.yml +9 -6
- package/templates/hermes-agent/docs/architecture.md +75 -51
- package/templates/hermes-agent/docs/fleet-control-plane/architecture.md +11 -6
- package/templates/hermes-agent/docs/fleet-control-plane/epics-and-stories.md +2 -2
- package/templates/hermes-agent/docs/fleet-control-plane/prd.md +2 -3
- package/templates/hermes-agent/docs/operations.md +179 -81
- package/templates/hermes-agent/docs/runbooks/runtime-checkpoint-repair.md +31 -171
- package/templates/hermes-agent/docs/sentinel/README.md +10 -10
- package/templates/hermes-agent/docs/sentinel/architecture.md +6 -8
- package/templates/hermes-agent/docs/sentinel/development.md +12 -15
- package/templates/hermes-agent/docs/sentinel.md +1 -1
- package/templates/hermes-agent/install-local.sh +41 -4
- package/templates/hermes-agent/runtime-scaffold/README.md +4 -2
- package/templates/hermes-agent/scripts/degit-runtime.sh +192 -0
- package/templates/hermes-agent/scripts/fleet-prune-debris.sh +128 -0
- package/templates/hermes-agent/scripts/fleet-sync.sh +164 -7
- package/templates/hermes-agent/scripts/hermes-runtime-templatize.py +321 -0
- package/templates/hermes-agent/scripts/migrate-profile-scoped-chat-secrets.py +136 -0
- package/templates/hermes-agent/scripts/momo-unify-agent.py +224 -0
- package/templates/hermes-agent/scripts/repair-runtime-checkpoint.sh +7 -119
- package/templates/hermes-agent/template/.gitignore.jinja +5 -2
- package/templates/hermes-agent/template/.runtime-scaffold/README.md +4 -2
- package/templates/hermes-agent/template/.scripts/00-banner.sh +1 -1
- package/templates/hermes-agent/template/.scripts/01-config.sh +3 -0
- package/templates/hermes-agent/template/.scripts/10-hermes-profile.sh +12 -1
- package/templates/hermes-agent/template/.scripts/20-runtime-repo.sh +55 -129
- package/templates/hermes-agent/template/.scripts/30-telegram.sh +276 -22
- package/templates/hermes-agent/template/.scripts/31-slack.sh +362 -0
- package/templates/hermes-agent/template/.scripts/60-bloodbank.sh +8 -66
- package/templates/hermes-agent/template/.scripts/70-systemd.sh +44 -30
- package/templates/hermes-agent/template/.scripts/80-registry.sh +93 -13
- package/templates/hermes-agent/template/.scripts/99-summary.sh +1 -4
- package/templates/hermes-agent/template/.scripts/_lib.sh +66 -1
- package/templates/hermes-agent/template/.scripts/checkpoint.sh +3 -2
- package/templates/hermes-agent/template/.scripts/config.example.toml +10 -10
- package/templates/hermes-agent/template/.scripts/heartbeat.sh +1 -1
- package/templates/hermes-agent/template/SOUL.md.jinja +2 -2
- package/templates/hermes-agent/template/hermes.jinja +6 -3
- package/templates/hermes-agent/template/role.yaml.jinja +24 -13
- package/templates/hermes-agent/tests/test_bloodbank_consumer_contract.py +429 -130
- package/templates/hermes-agent/tests/test_fleet_upgrade_contract.py +176 -0
- package/templates/hermes-agent/tests/test_launcher_chat_secret_isolation.py +85 -0
- package/templates/hermes-agent/tests/test_local_runtime_provisioning.py +130 -0
- package/templates/hermes-agent/tests/test_operator_docs_local_runtime_contract.py +132 -0
- package/templates/hermes-agent/tests/test_profile_env_detach_contract.py +14 -0
- package/templates/hermes-agent/tests/test_profile_scoped_chat_secrets.py +89 -0
- package/templates/hermes-agent/tests/test_repository_privacy_contract.py +32 -0
- package/templates/hermes-agent/tests/test_slack_provisioning.py +344 -0
- package/templates/hermes-agent/tests/test_telegram_provisioning.py +475 -0
- package/templates/hermes-agent/.codegraph/daemon.pid +0 -6
- package/templates/hermes-agent/.omo/run-continuation/ses_0e5b28303ffeXxL53hZjKggXDW.json +0 -10
- package/templates/hermes-agent/runtime-scaffold/bloodbank-consumer.py +0 -181
- package/templates/hermes-agent/template/.runtime-scaffold/bloodbank-consumer.py +0 -181
|
@@ -5,7 +5,6 @@ source "$(dirname "$0")/_lib.sh"
|
|
|
5
5
|
load_role_env
|
|
6
6
|
|
|
7
7
|
GW_UNIT="hermes-${AGENT_ID}-gateway.service"
|
|
8
|
-
CSM_UNIT="hermes-${AGENT_ID}-consumer.service"
|
|
9
8
|
HB_TIMER="hermes-${AGENT_ID}-heartbeat.timer"
|
|
10
9
|
|
|
11
10
|
cat >&2 <<EOF
|
|
@@ -15,18 +14,16 @@ cat >&2 <<EOF
|
|
|
15
14
|
│ Talk: @$BOT_HANDLE (Telegram DM)
|
|
16
15
|
│ Shell: $ROLE_DIR/hermes chat "status"
|
|
17
16
|
│ Board: $PLANE_BASE/$PLANE_WORKSPACE/projects/$(cat "$ROLE_DIR/.scripts/.plane-project-id" 2>/dev/null || echo "(skipped)")
|
|
18
|
-
│ Runtime:
|
|
17
|
+
│ Runtime: $ROLE_DIR/runtime (pure-local, ignored)
|
|
19
18
|
│ Hermes bin: $HERMES_BIN
|
|
20
19
|
│ Fleet env: $FLEET_ENV
|
|
21
20
|
│
|
|
22
21
|
│ Start fleet daemons:
|
|
23
22
|
│ systemctl --user start $GW_UNIT
|
|
24
|
-
│ systemctl --user start $CSM_UNIT
|
|
25
23
|
│ systemctl --user start $HB_TIMER
|
|
26
24
|
│
|
|
27
25
|
│ Tail logs:
|
|
28
26
|
│ journalctl --user -fu $GW_UNIT
|
|
29
|
-
│ journalctl --user -fu $CSM_UNIT
|
|
30
27
|
│
|
|
31
28
|
│ Fleet status:
|
|
32
29
|
│ python3 -c "import yaml,pathlib; print(yaml.safe_dump(yaml.safe_load(pathlib.Path('$REGISTRY_FILE').read_text())['agents']))"
|
|
@@ -145,10 +145,17 @@ if [[ -f "$FLEET_ENV" ]]; then
|
|
|
145
145
|
# shellcheck disable=SC1090
|
|
146
146
|
source "$FLEET_ENV"
|
|
147
147
|
fi
|
|
148
|
+
# Identity-bearing chat credentials are never fleet-scoped. Platform wiring
|
|
149
|
+
# steps capture explicit invocation values before sourcing this library and
|
|
150
|
+
# restore only those values afterward; all other provisioning steps stay clean.
|
|
151
|
+
unset TELEGRAM_BOT_TOKEN SLACK_BOT_TOKEN SLACK_APP_TOKEN
|
|
148
152
|
|
|
149
153
|
# Tools we expect on the host
|
|
150
154
|
HERMES_BIN="${HERMES_BIN:-${HERMES_FLEET_BIN:-$(config_get fleet.hermes_bin "$HOME/.hermes/hermes-agent/.venv/bin/hermes")}}"
|
|
151
155
|
HERMES_AGENT_REPO="${HERMES_AGENT_REPO:-${HERMES_FLEET_REPO:-$(config_get fleet.hermes_repo "$HOME/.hermes/hermes-agent")}}"
|
|
156
|
+
HERMES_RUNTIME_GIT_URL="${HERMES_RUNTIME_GIT_URL:-$(config_get fleet.hermes_git_url 'https://github.com/delorenj/hermes-agent.git')}"
|
|
157
|
+
HERMES_RUNTIME_GIT_REF="${HERMES_RUNTIME_GIT_REF:-$(config_get fleet.hermes_git_ref 'feature/PJAN-19-routing-publication')}"
|
|
158
|
+
HERMES_RUNTIME_GIT_SHA="${HERMES_RUNTIME_GIT_SHA:-$(config_get fleet.hermes_git_sha '113e1b182b6d72a7dd02a191f134a41668ceaf0e')}"
|
|
152
159
|
HERMES_OAUTH_FILE="${HERMES_OAUTH_FILE:-${HERMES_FLEET_OAUTH_FILE:-$(config_get fleet.oauth_file "$HOME/.hermes/auth.json")}}"
|
|
153
160
|
CODEX_HOME="${CODEX_HOME:-${HERMES_FLEET_CODEX_HOME:-$(config_get fleet.codex_home "$HOME/.codex")}}"
|
|
154
161
|
# Prefer a scaffold vendored into this agent directory; fall back to the configured template path.
|
|
@@ -158,6 +165,29 @@ if [[ ! -d "$RUNTIME_SCAFFOLD_DIR" ]]; then
|
|
|
158
165
|
fi
|
|
159
166
|
REGISTRY_FILE="${REGISTRY_FILE:-${HERMES_FLEET_REGISTRY_FILE:-$(config_get fleet.registry_file "$HOME/.hermes/agents-registry.yaml")}}"
|
|
160
167
|
|
|
168
|
+
# Cross-process serialization for fleet identity claims and registry updates.
|
|
169
|
+
# The lock file may remain on disk; flock ownership is kernel-scoped, so a
|
|
170
|
+
# crashed provisioner cannot leave a permanently stale lock.
|
|
171
|
+
FLEET_LOCK_FD=""
|
|
172
|
+
fleet_lock_acquire() {
|
|
173
|
+
command -v flock >/dev/null 2>&1 || die "flock is required for safe fleet registry updates"
|
|
174
|
+
local lock_file="${REGISTRY_FILE}.lock"
|
|
175
|
+
mkdir -p "$(dirname "$lock_file")"
|
|
176
|
+
[[ ! -L "$lock_file" ]] || die "refusing fleet lock symlink: $lock_file"
|
|
177
|
+
exec {FLEET_LOCK_FD}>"$lock_file"
|
|
178
|
+
chmod 600 "$lock_file"
|
|
179
|
+
flock -w "${FLEET_LOCK_TIMEOUT_SECONDS:-30}" "$FLEET_LOCK_FD" \
|
|
180
|
+
|| die "timed out waiting for fleet registry lock: $lock_file"
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
fleet_lock_release() {
|
|
184
|
+
if [[ "${FLEET_LOCK_FD:-}" =~ ^[0-9]+$ ]]; then
|
|
185
|
+
flock -u "$FLEET_LOCK_FD" 2>/dev/null || true
|
|
186
|
+
eval "exec ${FLEET_LOCK_FD}>&-"
|
|
187
|
+
fi
|
|
188
|
+
FLEET_LOCK_FD=""
|
|
189
|
+
}
|
|
190
|
+
|
|
161
191
|
# Bloodbank / NATS
|
|
162
192
|
BLOODBANK_NATS_HOST="${BLOODBANK_NATS_HOST:-$(config_get bloodbank.nats_host '127.0.0.1')}"
|
|
163
193
|
BLOODBANK_NATS_PORT="${BLOODBANK_NATS_PORT:-$(config_get bloodbank.nats_port '4222')}"
|
|
@@ -167,7 +197,8 @@ BLOODBANK_COMPOSE_DIR="${BLOODBANK_COMPOSE_DIR:-$(config_get bloodbank.compose_d
|
|
|
167
197
|
PLANE_BASE="${PLANE_BASE:-$(config_get plane.base 'https://plane.delo.sh')}"
|
|
168
198
|
PLANE_API_KEY="${PLANE_API_KEY:-${PLANE_33GOD_API_KEY:-}}"
|
|
169
199
|
|
|
170
|
-
export FLEET_ENV HERMES_BIN HERMES_AGENT_REPO
|
|
200
|
+
export FLEET_ENV HERMES_BIN HERMES_AGENT_REPO HERMES_RUNTIME_GIT_URL \
|
|
201
|
+
HERMES_RUNTIME_GIT_REF HERMES_RUNTIME_GIT_SHA HERMES_OAUTH_FILE CODEX_HOME \
|
|
171
202
|
RUNTIME_SCAFFOLD_DIR REGISTRY_FILE \
|
|
172
203
|
BLOODBANK_NATS_HOST BLOODBANK_NATS_PORT BLOODBANK_COMPOSE_DIR \
|
|
173
204
|
PLANE_BASE PLANE_API_KEY
|
|
@@ -180,6 +211,40 @@ systemd_user_available() {
|
|
|
180
211
|
[[ "$state" =~ ^(running|degraded|starting|maintenance)$ ]]
|
|
181
212
|
}
|
|
182
213
|
|
|
214
|
+
# Query one systemd user-unit state without conflating every non-zero exit with
|
|
215
|
+
# an inactive/disabled unit. Output is `ok|<state>` only for documented
|
|
216
|
+
# state/exit-code pairs; D-Bus, manager, and arbitrary query failures become
|
|
217
|
+
# `error|<safe summary>` so retirement callers can fail closed.
|
|
218
|
+
systemctl_user_unit_state() {
|
|
219
|
+
local query="$1" unit="$2" output rc first_line
|
|
220
|
+
command -v systemctl >/dev/null 2>&1 \
|
|
221
|
+
|| { printf 'error|systemctl unavailable'; return 0; }
|
|
222
|
+
set +e
|
|
223
|
+
output="$(LC_ALL=C systemctl --user "$query" "$unit" 2>&1)"
|
|
224
|
+
rc=$?
|
|
225
|
+
set -e
|
|
226
|
+
first_line="${output%%$'\n'*}"
|
|
227
|
+
first_line="${first_line//$'\t'/ }"
|
|
228
|
+
first_line="${first_line//|/}"
|
|
229
|
+
case "$query:$rc:$first_line" in
|
|
230
|
+
is-active:0:active|is-active:0:reloading|is-active:0:activating|is-active:0:deactivating)
|
|
231
|
+
printf 'ok|%s' "$first_line" ;;
|
|
232
|
+
is-active:3:inactive|is-active:3:failed)
|
|
233
|
+
printf 'ok|%s' "$first_line" ;;
|
|
234
|
+
is-active:4:inactive)
|
|
235
|
+
printf 'ok|not-found' ;;
|
|
236
|
+
is-enabled:0:enabled|is-enabled:0:enabled-runtime|is-enabled:0:linked|is-enabled:0:linked-runtime|is-enabled:0:alias|is-enabled:0:static|is-enabled:0:indirect|is-enabled:0:generated|is-enabled:0:transient)
|
|
237
|
+
printf 'ok|%s' "$first_line" ;;
|
|
238
|
+
is-enabled:1:disabled|is-enabled:1:masked|is-enabled:1:masked-runtime)
|
|
239
|
+
printf 'ok|%s' "$first_line" ;;
|
|
240
|
+
is-enabled:4:not-found)
|
|
241
|
+
printf 'ok|not-found' ;;
|
|
242
|
+
*)
|
|
243
|
+
[[ -n "$first_line" ]] || first_line="exit $rc with no state"
|
|
244
|
+
printf 'error|%s' "$first_line" ;;
|
|
245
|
+
esac
|
|
246
|
+
}
|
|
247
|
+
|
|
183
248
|
# Resolve project repo path (the repo that holds agents/hermes/<role>/).
|
|
184
249
|
# Walk up from $ROLE_DIR until we find a git root that isn't us.
|
|
185
250
|
project_repo_path() {
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
|
-
#
|
|
2
|
+
# Legacy checkpoint compatibility for installations whose runtime is still a
|
|
3
|
+
# nested Git repository. Pure-local runtimes intentionally skip this script.
|
|
3
4
|
# Idempotent — exits 0 with no commit if there are no changes.
|
|
4
5
|
#
|
|
5
6
|
# Secret-scan gate (PJAN): before committing, the staged diff is scanned for
|
|
@@ -11,7 +12,7 @@ set -euo pipefail
|
|
|
11
12
|
RUNTIME_DIR="$(cd "$(dirname "$0")/../runtime" && pwd)"
|
|
12
13
|
cd "$RUNTIME_DIR"
|
|
13
14
|
|
|
14
|
-
# Skip
|
|
15
|
+
# Skip when the pure-local runtime has no Git metadata.
|
|
15
16
|
[[ -d .git || -f .git ]] || exit 0
|
|
16
17
|
|
|
17
18
|
# Returns 0 when the staged diff looks clean, 1 when a likely secret is present.
|
|
@@ -13,8 +13,13 @@
|
|
|
13
13
|
[fleet]
|
|
14
14
|
# Absolute path to the shared Hermes executable every agent launcher execs.
|
|
15
15
|
hermes_bin = "~/.hermes/hermes-agent/.venv/bin/hermes"
|
|
16
|
-
# Checkout of the hermes-agent repo.
|
|
16
|
+
# Checkout of the shared hermes-agent repo.
|
|
17
17
|
hermes_repo = "~/.hermes/hermes-agent"
|
|
18
|
+
# Reviewed fleet runtime publication. Provisioning metadata and clean installs
|
|
19
|
+
# must agree on this fork/ref/SHA; do not substitute upstream main.
|
|
20
|
+
hermes_git_url = "https://github.com/delorenj/hermes-agent.git"
|
|
21
|
+
hermes_git_ref = "feature/PJAN-19-routing-publication"
|
|
22
|
+
hermes_git_sha = "113e1b182b6d72a7dd02a191f134a41668ceaf0e"
|
|
18
23
|
# Fallback runtime scaffold dir — used only when an agent's vendored
|
|
19
24
|
# ./.runtime-scaffold is missing.
|
|
20
25
|
runtime_scaffold_dir = "~/code/hermes-agent-template/runtime-scaffold"
|
|
@@ -45,17 +50,12 @@ symlinked_runtime_skills = [
|
|
|
45
50
|
]
|
|
46
51
|
|
|
47
52
|
[github]
|
|
48
|
-
#
|
|
49
|
-
|
|
53
|
+
# LEGACY INERT COMPATIBILITY METADATA ONLY. Older role manifests may still
|
|
54
|
+
# carry this owner field. Current provisioning does not create, attach,
|
|
55
|
+
# synchronize, restore, archive, or remove runtime storage from this value.
|
|
56
|
+
runtime_repo_owner = ""
|
|
50
57
|
|
|
51
58
|
[plane]
|
|
52
59
|
# Plane instance base URL and workspace slug (one project per agent).
|
|
53
60
|
base = "https://plane.delo.sh"
|
|
54
61
|
workspace = "33god"
|
|
55
|
-
|
|
56
|
-
[bloodbank]
|
|
57
|
-
# NATS endpoint the consumer connects to.
|
|
58
|
-
nats_host = "127.0.0.1"
|
|
59
|
-
nats_port = 4222
|
|
60
|
-
# Where the bloodbank docker compose lives (used only for a hint message). ~ ok.
|
|
61
|
-
compose_dir = "~/code/33GOD/bloodbank"
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
# full pass executes the role's sentinel.prompt.md, which reasons about tickets
|
|
9
9
|
# through the ticket-provider adapter (Linear | Plane | Trello) — never a
|
|
10
10
|
# hardcoded backend. After the sentinel decision (skip OR full), it
|
|
11
|
-
# opportunistically checkpoints
|
|
11
|
+
# opportunistically checkpoints only legacy nested-Git runtimes at most once
|
|
12
12
|
# per HEARTBEAT_CHECKPOINT_MIN_INTERVAL_SECONDS, so memory/session state stays
|
|
13
13
|
# durable without pushing every minute.
|
|
14
14
|
set -euo pipefail
|
|
@@ -44,8 +44,8 @@ question — not three vague ones.
|
|
|
44
44
|
You **MUST** emit a Bloodbank event for every consequential action you take.
|
|
45
45
|
Envelope shape: CloudEvents 1.0, type `bloodbank.v1.<domain>.<entity>.<action>`,
|
|
46
46
|
`actor.agent_id = {{ agent_id }}`, `producer = hermes-agent:{{ agent_id }}`,
|
|
47
|
-
`source = hermes://agent/{{ agent_id }}`.
|
|
48
|
-
|
|
47
|
+
`source = hermes://agent/{{ agent_id }}`. Inbound commands arrive through the
|
|
48
|
+
fleet-shared Hermes gateway and are routed by `data.target_agent_id`.
|
|
49
49
|
|
|
50
50
|
You **MUST NOT** invent new event `type` values. Bloodbank owns the naming
|
|
51
51
|
contract at `~/code/33GOD/bloodbank/docs/event-naming.md` —
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
|
-
# Launcher for {{ agent_id }}. Resolves HERMES_HOME to the runtime
|
|
2
|
+
# Launcher for {{ agent_id }}. Resolves HERMES_HOME to the local runtime
|
|
3
3
|
# and execs the shared fleet Hermes binary configured in ~/.hermes/fleet.env.
|
|
4
4
|
|
|
5
5
|
set -euo pipefail
|
|
@@ -12,6 +12,9 @@ if [[ -f "$FLEET_ENV" ]]; then
|
|
|
12
12
|
# shellcheck disable=SC1090
|
|
13
13
|
source "$FLEET_ENV"
|
|
14
14
|
fi
|
|
15
|
+
# Never pass an identity-bearing chat credential from shared fleet state into
|
|
16
|
+
# a profile process. Hermes loads the profile's own runtime/.env itself.
|
|
17
|
+
unset TELEGRAM_BOT_TOKEN SLACK_BOT_TOKEN SLACK_APP_TOKEN
|
|
15
18
|
|
|
16
19
|
CONFIG="${HERMES_TEMPLATE_CONFIG:-${XDG_CONFIG_HOME:-$HOME/.config}/hermes-agent-template/config.toml}"
|
|
17
20
|
config_get() {
|
|
@@ -49,8 +52,8 @@ HERMES_OAUTH_FILE="${HERMES_OAUTH_FILE:-${HERMES_FLEET_OAUTH_FILE:-$(config_get
|
|
|
49
52
|
CODEX_HOME="${CODEX_HOME:-${HERMES_FLEET_CODEX_HOME:-$(config_get fleet.codex_home "$HOME/.codex")}}"
|
|
50
53
|
|
|
51
54
|
if [[ ! -d "$HERMES_HOME" ]]; then
|
|
52
|
-
echo "hermes: runtime
|
|
53
|
-
echo " fix:
|
|
55
|
+
echo "hermes: local runtime not provisioned at $HERMES_HOME" >&2
|
|
56
|
+
echo " fix: run $ROLE_DIR/.scripts/20-runtime-repo.sh" >&2
|
|
54
57
|
exit 1
|
|
55
58
|
fi
|
|
56
59
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Hermes agent role manifest. Tracked in the PROJECT repository.
|
|
2
2
|
# The agent's actual state (memory, sessions, evolving SOUL) lives in the
|
|
3
|
-
# runtime
|
|
3
|
+
# ignored local runtime. This file is the immutable contract for this role.
|
|
4
4
|
|
|
5
5
|
repo: {{ target_repo }}
|
|
6
6
|
role: {{ role }}
|
|
@@ -14,12 +14,24 @@ model:
|
|
|
14
14
|
name: "{{ model_name }}"
|
|
15
15
|
|
|
16
16
|
# Hermes profile name. ~/.hermes/profiles/<name> symlinks to ./runtime/, so both
|
|
17
|
-
# HERMES_HOME and `hermes --profile <name>` resolve to the runtime
|
|
17
|
+
# HERMES_HOME and `hermes --profile <name>` resolve to the local runtime.
|
|
18
18
|
profile: {{ agent_id }}
|
|
19
19
|
|
|
20
20
|
# Telegram bot identity (one bot per agent — see docs/architecture.md).
|
|
21
21
|
telegram:
|
|
22
|
+
provisioning_status: "deferred"
|
|
22
23
|
bot_username: "{{ bot_handle }}"
|
|
24
|
+
bot_id: ""
|
|
25
|
+
|
|
26
|
+
# Slack is opt-in. Credentials live only in runtime/.env; this block records
|
|
27
|
+
# safe provisioning state and the verified auth.test identity.
|
|
28
|
+
slack:
|
|
29
|
+
provisioning_status: "deferred"
|
|
30
|
+
team_id: ""
|
|
31
|
+
team_name: ""
|
|
32
|
+
bot_user_id: ""
|
|
33
|
+
bot_id: ""
|
|
34
|
+
bot_username: ""
|
|
23
35
|
|
|
24
36
|
# Ticket-provider binding (linear | plane | trello).
|
|
25
37
|
# The heartbeat reconciliation pass talks ONLY to this via .scripts/lib/ticket-provider.sh;
|
|
@@ -54,25 +66,24 @@ plane:
|
|
|
54
66
|
# identifier is set by .scripts/42-ticket-provider.sh after creation (plane only)
|
|
55
67
|
identifier: ""
|
|
56
68
|
|
|
57
|
-
# Bloodbank
|
|
69
|
+
# Bloodbank ingress is owned by one fleet-shared Hermes gateway. The gateway
|
|
70
|
+
# reads the fleet registry and routes canonical commands by target_agent_id;
|
|
71
|
+
# this profile does not install its own NATS consumer or inbox bridge.
|
|
58
72
|
bloodbank:
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
- "bloodbank.cmd.v1.agent.>"
|
|
62
|
-
routing:
|
|
63
|
-
repo: "{{ target_repo }}"
|
|
64
|
-
target_agent_id: "{{ agent_id }}"
|
|
73
|
+
gateway_scope: fleet
|
|
74
|
+
target_agent_id: "{{ agent_id }}"
|
|
65
75
|
producer: "hermes-agent:{{ agent_id }}"
|
|
66
76
|
|
|
67
|
-
#
|
|
77
|
+
# Pure-local HERMES_HOME. The legacy GitHub identity remains metadata-only for
|
|
78
|
+
# locating old archives; provisioning never creates or attaches a submodule.
|
|
68
79
|
runtime:
|
|
69
80
|
# Empty owner -> resolved from config.toml [github].runtime_repo_owner.
|
|
70
81
|
github_owner: "{{ runtime_repo_owner }}"
|
|
71
82
|
github_repo: "{{ runtime_repo }}"
|
|
72
|
-
|
|
83
|
+
local_path: "./runtime"
|
|
73
84
|
checkpoint:
|
|
74
|
-
cadence: "
|
|
75
|
-
on_session_end:
|
|
85
|
+
cadence: "disabled"
|
|
86
|
+
on_session_end: false
|
|
76
87
|
|
|
77
88
|
# Provenance — managed by the template, do not hand-edit.
|
|
78
89
|
provisioned_at: "{{ '%Y-%m-%dT%H:%M:%SZ' | strftime }}"
|