fix(harnesses): migrate to ESO secrets_required form, mirror agent-runtimes
The CRS-served harnesses still carried `secrets_files: [{encrypted: true}]`
which now hard-fails on H-SECRET-1 ("SOPS-encrypted secrets_files entries
are no longer permitted") in the dispatcher's harness validator. Sync the
8 provider harnesses with the agent-runtimes copies: same `secrets_required`
shape, same `init.sh` (ESO-mounted file paths), same `bin/` wrappers.
Use bare `account_ref: "<provider>"` (not `<provider>.cp:cp` — that
scope-kind isn't valid per SR-DISP-1-FIELD).
Provider key names follow the per-provider schema as emitted by the CP
provisioner: minimax/airouter/z-ai → api_key; gitea-https/gitea-admin →
{token,base_url,username}; gitea-ssh* → {host,private_key}.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
10
harnesses/contexts/airouter/v1/bin/anthropic-compat-wrapper.sh
Executable file
10
harnesses/contexts/airouter/v1/bin/anthropic-compat-wrapper.sh
Executable file
@@ -0,0 +1,10 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# Anthropic-compat wrapper for airouter harness (Phase 9 ESO-managed secrets)
|
||||||
|
# Reads airouter credentials from /run/agent/secrets/airouter/ and passes them
|
||||||
|
# as env vars to the underlying Claude runner.
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
exec env \
|
||||||
|
ANTHROPIC_AUTH_TOKEN="$(cat /run/agent/secrets/airouter/auth_token)" \
|
||||||
|
ANTHROPIC_BASE_URL="$(cat /run/agent/secrets/airouter/base_url)" \
|
||||||
|
claude "$@"
|
||||||
@@ -8,7 +8,11 @@ provides: [agentic-runner]
|
|||||||
env:
|
env:
|
||||||
OPENAI_BASE_URL: "https://api.airouter.ch/v1"
|
OPENAI_BASE_URL: "https://api.airouter.ch/v1"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./provider.sops.env
|
- name: airouter
|
||||||
target: /opt/harness/secrets/airouter/provider.sops.env
|
account_ref: "airouter"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/airouter
|
||||||
|
mode: "0400"
|
||||||
|
|
||||||
|
scripts:
|
||||||
|
init: ./init.sh
|
||||||
|
|||||||
29
harnesses/contexts/airouter/v1/init.sh
Executable file
29
harnesses/contexts/airouter/v1/init.sh
Executable file
@@ -0,0 +1,29 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# airouter init — Phase 9 ESO-managed secret mount.
|
||||||
|
#
|
||||||
|
# Verifies the ESO-mounted secret files exist; the wrapper
|
||||||
|
# (`bin/anthropic-compat-wrapper.sh`) reads them at exec time.
|
||||||
|
#
|
||||||
|
# Per H-SECRET-4: NO `export` of credentials here. The earlier draft of this
|
||||||
|
# file exported ANTHROPIC_AUTH_TOKEN and ANTHROPIC_BASE_URL from this script,
|
||||||
|
# which runs as root under uid-wrapper.sh — even though the export was
|
||||||
|
# subshell-scoped, the secret was briefly resident in /proc/<pid>/environ of
|
||||||
|
# a root process. The wrapper's `exec env VAR=...` pattern is the only
|
||||||
|
# acceptable credential delivery point.
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
SECRETS_DIR="/run/agent/secrets/airouter"
|
||||||
|
|
||||||
|
if [ ! -d "$SECRETS_DIR" ]; then
|
||||||
|
echo "ERROR: Secret directory $SECRETS_DIR not found. ESO mount may have failed." >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
for f in auth_token base_url; do
|
||||||
|
if [ ! -r "$SECRETS_DIR/$f" ]; then
|
||||||
|
echo "ERROR: $SECRETS_DIR/$f not readable. Check ESO ExternalSecret for airouter." >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
echo "airouter secrets verified at $SECRETS_DIR"
|
||||||
45
harnesses/contexts/gitea-admin/v1/bin/gitea-admin-wrapper.sh
Executable file
45
harnesses/contexts/gitea-admin/v1/bin/gitea-admin-wrapper.sh
Executable file
@@ -0,0 +1,45 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# gitea-admin-wrapper.sh — reads the ESO-mounted gitea-admin token at exec time
|
||||||
|
# and prefixes it as a transient env var to the underlying tool.
|
||||||
|
#
|
||||||
|
# M22 Phase 9: token mounted at /run/agent/secrets/gitea-admin/token (read-only,
|
||||||
|
# tmpfs, mode 0400). The token NEVER enters the wrapper's parent shell — only
|
||||||
|
# the exec'd tool's environment via `exec env VAR=value cmd`. The brief
|
||||||
|
# presence in /proc/<tool_pid>/environ of the tool process is the accepted
|
||||||
|
# floor (per spec/secrets-runtime.md SR-DISP-7 / H-SECRET-4).
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
TOKEN_FILE="/run/agent/secrets/gitea-admin/token"
|
||||||
|
|
||||||
|
# git-credential-helper subcommand: read token and emit git credential format.
|
||||||
|
# Git invokes us as `gitea-admin-wrapper.sh git-credential-helper get` and
|
||||||
|
# expects key=value lines on stdout terminated by a blank line.
|
||||||
|
git_credential_helper() {
|
||||||
|
if [[ ! -r "$TOKEN_FILE" ]]; then
|
||||||
|
echo "gitea-admin-wrapper: token file not readable at $TOKEN_FILE" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
local base_url="${GITEA_BASE_URL:-https://gitea.oreillyit.nz}"
|
||||||
|
local host
|
||||||
|
host=$(echo "$base_url" | sed 's|https\?://||')
|
||||||
|
# Trailing blank line per git credential-helper protocol.
|
||||||
|
printf 'protocol=https\nhost=%s\nusername=git\npassword=%s\n\n' "$host" "$(cat "$TOKEN_FILE")"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
|
||||||
|
case "${1:-}" in
|
||||||
|
git-credential-helper)
|
||||||
|
git_credential_helper
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
if [[ ! -r "$TOKEN_FILE" ]]; then
|
||||||
|
echo "gitea-admin-wrapper: token file not readable at $TOKEN_FILE" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
# `exec env VAR=...` keeps the secret out of the wrapper's parent shell
|
||||||
|
# — it lands only in the exec'd tool's /proc/<pid>/environ. NEVER use
|
||||||
|
# `export VAR=` here, which would leak the secret to the wrapper's
|
||||||
|
# ancestors (H-SECRET-4 violation).
|
||||||
|
exec env GITEA_ADMIN_TOKEN="$(cat "$TOKEN_FILE")" "$@"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
@@ -17,11 +17,18 @@ ssh_hosts:
|
|||||||
identity_secret: SSH_KEY_AI_ENABLEMENT
|
identity_secret: SSH_KEY_AI_ENABLEMENT
|
||||||
|
|
||||||
secrets_required:
|
secrets_required:
|
||||||
|
# ESO-managed gitea-admin token (M22 Phase 9)
|
||||||
|
- name: gitea-admin
|
||||||
|
account_ref: "gitea-admin"
|
||||||
|
mount_path: /run/agent/secrets/gitea-admin
|
||||||
|
mode: "0400"
|
||||||
|
# Legacy SSH key (file-based, already delivered as mount)
|
||||||
- name: SSH_KEY_AI_ENABLEMENT
|
- name: SSH_KEY_AI_ENABLEMENT
|
||||||
mount: /home/agent/.ssh/id_ed25519
|
mount: /home/agent/.ssh/id_ed25519
|
||||||
mode: "0600"
|
mode: "0600"
|
||||||
|
|
||||||
secrets_files:
|
env:
|
||||||
- source: ./provider.sops.env
|
GITEA_BASE_URL: "https://gitea.oreillyit.nz"
|
||||||
target: /opt/harness/secrets/gitea-admin/provider.sops.env
|
|
||||||
encrypted: true
|
scripts:
|
||||||
|
init: ./init.sh
|
||||||
19
harnesses/contexts/gitea-admin/v1/init.sh
Executable file
19
harnesses/contexts/gitea-admin/v1/init.sh
Executable file
@@ -0,0 +1,19 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# init.sh for gitea-admin harness (M22 Phase 9)
|
||||||
|
# Sets up non-secret env vars and configures git credential helper.
|
||||||
|
# Credential token is NOT exported here — only read at exec time by the wrapper.
|
||||||
|
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
# Non-secret configuration
|
||||||
|
export GITEA_BASE_URL="${GITEA_BASE_URL:-https://gitea.oreillyit.nz}"
|
||||||
|
|
||||||
|
# Ensure SSH directory exists with correct permissions
|
||||||
|
mkdir -p /home/agent/.ssh
|
||||||
|
chmod 700 /home/agent/.ssh
|
||||||
|
|
||||||
|
# Configure git to use the gitea-admin credential helper wrapper
|
||||||
|
# The wrapper reads the ESO-mounted token at exec time
|
||||||
|
git config --global credential.helper "!/opt/harness/contexts/gitea-admin/v1/bin/gitea-admin-wrapper.sh git-credential-helper"
|
||||||
|
|
||||||
|
echo "[gitea-admin] init complete"
|
||||||
@@ -12,7 +12,8 @@ git_identity:
|
|||||||
scripts:
|
scripts:
|
||||||
init: "./init.sh"
|
init: "./init.sh"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./provider.sops.env
|
- name: gitea-https
|
||||||
target: /opt/harness/secrets/gitea-https/provider.sops.env
|
account_ref: "gitea-https"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/gitea-https
|
||||||
|
mode: "0400"
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
# Configure git to use GITEA_TOKEN for HTTPS cloning/pushing to gitea.oreillyit.nz
|
# Configure git to use git credential helper for gitea.oreillyit.nz via HTTPS.
|
||||||
#
|
#
|
||||||
# Uses a credential helper script that reads the token from the environment.
|
# The token is read from /run/agent/secrets/gitea-https/token at every git
|
||||||
# This avoids embedding the token in clone URLs (which would appear in logs).
|
# invocation (not at init time). This avoids the token appearing in logs.
|
||||||
|
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
@@ -11,14 +11,16 @@ CRED_HELPER="/opt/harness/contexts/gitea-https/v1/git-credential-gitea.sh"
|
|||||||
# Create the credential helper script
|
# Create the credential helper script
|
||||||
cat > "$CRED_HELPER" << 'HELPER_EOF'
|
cat > "$CRED_HELPER" << 'HELPER_EOF'
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
# Git credential helper that provides GITEA_TOKEN for gitea.oreillyit.nz
|
# Git credential helper that provides the token from a mounted file
|
||||||
if [ -z "${GITEA_TOKEN:-}" ]; then
|
# for gitea.oreillyit.nz.
|
||||||
exit 1
|
# This reads the file at EVERY git invocation, not at init time.
|
||||||
fi
|
set -euo pipefail
|
||||||
|
SECRET_FILE=/run/agent/secrets/gitea-https/token
|
||||||
|
[ -r "$SECRET_FILE" ] || exit 1
|
||||||
echo "protocol=https"
|
echo "protocol=https"
|
||||||
echo "host=gitea.oreillyit.nz"
|
echo "host=gitea.oreillyit.nz"
|
||||||
echo "username=token"
|
echo "username=token"
|
||||||
echo "password=${GITEA_TOKEN}"
|
echo "password=$(cat $SECRET_FILE)"
|
||||||
HELPER_EOF
|
HELPER_EOF
|
||||||
|
|
||||||
chmod +x "$CRED_HELPER"
|
chmod +x "$CRED_HELPER"
|
||||||
@@ -26,4 +28,4 @@ chmod +x "$CRED_HELPER"
|
|||||||
# Configure git to use this credential helper for gitea.oreillyit.nz
|
# Configure git to use this credential helper for gitea.oreillyit.nz
|
||||||
git config --global credential.https://gitea.oreillyit.nz.helper "$CRED_HELPER"
|
git config --global credential.https://gitea.oreillyit.nz.helper "$CRED_HELPER"
|
||||||
|
|
||||||
echo "Git HTTPS credential helper configured for gitea.oreillyit.nz"
|
echo "Git HTTPS credential helper configured for gitea.oreillyit.nz"
|
||||||
@@ -18,7 +18,8 @@ ssh_hosts:
|
|||||||
scripts:
|
scripts:
|
||||||
init: "./init.sh"
|
init: "./init.sh"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./ssh-key.sops.env
|
- name: gitea-ssh-accelerators
|
||||||
target: /opt/harness/secrets/gitea-ssh-accelerators/ssh-key.sops.env
|
account_ref: "gitea-ssh-accelerators"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/gitea-ssh-accelerators
|
||||||
|
mode: "0400"
|
||||||
|
|||||||
@@ -1,29 +1,21 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
|
# gitea-ssh-accelerators init: copy the ESO-mounted SSH key to the path the
|
||||||
|
# harness-init `~/.ssh/config` expects (`IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-accelerators`).
|
||||||
|
#
|
||||||
|
# Per H-SECRET-4: NO `export` of credentials. (The earlier draft set
|
||||||
|
# `GIT_SSH_COMMAND` here — a path, not a credential — but that export dies
|
||||||
|
# with the subshell and the harness-init's SSH config is the load-bearing
|
||||||
|
# path anyway.)
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
# Extract SSH private key from decrypted env file for the accelerators identity.
|
SSH_KEY_SRC="/run/agent/secrets/gitea-ssh-accelerators/id_ed25519"
|
||||||
# The meta-init script generates ~/.ssh/config with
|
SSH_KEY_DST="/home/agent/.ssh/gitea-oreillyit-nz-accelerators"
|
||||||
# IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-accelerators
|
|
||||||
# matching the ssh_hosts alias in harness.yaml.
|
|
||||||
|
|
||||||
SSH_KEY_FILE="/home/agent/.ssh/gitea-oreillyit-nz-accelerators"
|
if [ ! -r "$SSH_KEY_SRC" ]; then
|
||||||
|
echo "ERROR: SSH key not found at $SSH_KEY_SRC — ESO ExternalSecret not Ready?" >&2
|
||||||
for env_file in /opt/harness/secrets/gitea-ssh-accelerators/*.decrypted.env /opt/harness/secrets/gitea-ssh-accelerators/*.env; do
|
exit 1
|
||||||
[ -f "$env_file" ] || continue
|
|
||||||
while IFS='=' read -r key value; do
|
|
||||||
[[ "$key" =~ ^[[:space:]]*# ]] && continue
|
|
||||||
[[ -z "$key" ]] && continue
|
|
||||||
if [ "$key" = "GITEA_SSH_KEY" ]; then
|
|
||||||
mkdir -p /home/agent/.ssh
|
|
||||||
echo "$value" | base64 -d > "$SSH_KEY_FILE"
|
|
||||||
chmod 600 "$SSH_KEY_FILE"
|
|
||||||
chown agent:agent "$SSH_KEY_FILE"
|
|
||||||
echo "SSH key written to $SSH_KEY_FILE"
|
|
||||||
break 2
|
|
||||||
fi
|
|
||||||
done < "$env_file"
|
|
||||||
done
|
|
||||||
|
|
||||||
if [ ! -f "$SSH_KEY_FILE" ]; then
|
|
||||||
echo "WARNING: GITEA_SSH_KEY not found in any env file under /opt/harness/secrets/gitea-ssh-accelerators/"
|
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
mkdir -p /home/agent/.ssh
|
||||||
|
install -m 0600 -o agent -g agent "$SSH_KEY_SRC" "$SSH_KEY_DST"
|
||||||
|
echo "gitea-ssh-accelerators: SSH key staged at $SSH_KEY_DST (0600 agent:agent)"
|
||||||
|
|||||||
@@ -18,7 +18,8 @@ ssh_hosts:
|
|||||||
scripts:
|
scripts:
|
||||||
init: "./init.sh"
|
init: "./init.sh"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./ssh-key.sops.env
|
- name: gitea-ssh-homelab
|
||||||
target: /opt/harness/secrets/gitea-ssh-homelab/ssh-key.sops.env
|
account_ref: "gitea-ssh-homelab"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/gitea-ssh-homelab
|
||||||
|
mode: "0400"
|
||||||
@@ -1,29 +1,30 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
|
# gitea-ssh-homelab init: copy the ESO-mounted SSH key to the path the
|
||||||
|
# harness-init `~/.ssh/config` expects.
|
||||||
|
#
|
||||||
|
# The harness-init dispatcher (`entrypoint/harness_init.py`) writes
|
||||||
|
# `~/.ssh/config` from the harness's `ssh_hosts:` block; for this provider
|
||||||
|
# the entry is `Host gitea.oreillyit.nz-homelab` with
|
||||||
|
# `IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-homelab`.
|
||||||
|
#
|
||||||
|
# We only need to materialise the key file at that path. We MUST NOT append
|
||||||
|
# our own SSH config block — doing so would (a) duplicate harness-init's
|
||||||
|
# config (SSH first-match-wins, so the appended block becomes dead) and
|
||||||
|
# (b) any unaliased `Host gitea.oreillyit.nz` block would collide with
|
||||||
|
# other gitea harnesses (gitea-https, gitea-admin) when composed.
|
||||||
|
#
|
||||||
|
# Per H-SECRET-4: NO `export` of credentials here. The path to the key is
|
||||||
|
# not a secret; the key content is, and it stays in the file.
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
# Extract SSH private key from decrypted env file for the homelab identity.
|
SSH_KEY_SRC="/run/agent/secrets/gitea-ssh-homelab/id_ed25519"
|
||||||
# The meta-init script generates ~/.ssh/config with
|
SSH_KEY_DST="/home/agent/.ssh/gitea-oreillyit-nz-homelab"
|
||||||
# IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-homelab
|
|
||||||
# matching the ssh_hosts alias in harness.yaml.
|
|
||||||
|
|
||||||
SSH_KEY_FILE="/home/agent/.ssh/gitea-oreillyit-nz-homelab"
|
if [ ! -r "$SSH_KEY_SRC" ]; then
|
||||||
|
echo "ERROR: SSH key not found at $SSH_KEY_SRC — ESO ExternalSecret not Ready?" >&2
|
||||||
for env_file in /opt/harness/secrets/gitea-ssh-homelab/*.decrypted.env /opt/harness/secrets/gitea-ssh-homelab/*.env; do
|
exit 1
|
||||||
[ -f "$env_file" ] || continue
|
|
||||||
while IFS='=' read -r key value; do
|
|
||||||
[[ "$key" =~ ^[[:space:]]*# ]] && continue
|
|
||||||
[[ -z "$key" ]] && continue
|
|
||||||
if [ "$key" = "GITEA_SSH_KEY" ]; then
|
|
||||||
mkdir -p /home/agent/.ssh
|
|
||||||
echo "$value" | base64 -d > "$SSH_KEY_FILE"
|
|
||||||
chmod 600 "$SSH_KEY_FILE"
|
|
||||||
chown agent:agent "$SSH_KEY_FILE"
|
|
||||||
echo "SSH key written to $SSH_KEY_FILE"
|
|
||||||
break 2
|
|
||||||
fi
|
|
||||||
done < "$env_file"
|
|
||||||
done
|
|
||||||
|
|
||||||
if [ ! -f "$SSH_KEY_FILE" ]; then
|
|
||||||
echo "WARNING: GITEA_SSH_KEY not found in any env file under /opt/harness/secrets/gitea-ssh-homelab/"
|
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
mkdir -p /home/agent/.ssh
|
||||||
|
install -m 0600 -o agent -g agent "$SSH_KEY_SRC" "$SSH_KEY_DST"
|
||||||
|
echo "gitea-ssh-homelab: SSH key staged at $SSH_KEY_DST (0600 agent:agent)"
|
||||||
|
|||||||
@@ -18,7 +18,8 @@ ssh_hosts:
|
|||||||
scripts:
|
scripts:
|
||||||
init: "./init.sh"
|
init: "./init.sh"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./ssh-key.sops.env
|
- name: gitea-ssh
|
||||||
target: /opt/harness/secrets/gitea-ssh/ssh-key.sops.env
|
account_ref: "gitea-ssh"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/gitea-ssh
|
||||||
|
mode: "0400"
|
||||||
|
|||||||
@@ -1,32 +1,27 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
|
# gitea-ssh init: copy the ESO-mounted SSH key to the path the harness-init
|
||||||
|
# `~/.ssh/config` expects.
|
||||||
|
#
|
||||||
|
# The harness-init dispatcher writes `~/.ssh/config` with
|
||||||
|
# IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-ai-enablement
|
||||||
|
# so the key must end up at that path with mode 0600 owned by agent.
|
||||||
|
#
|
||||||
|
# The ESO mount at /run/agent/secrets/gitea-ssh/private_key is read-only
|
||||||
|
# (V1VolumeMount(read_only=True)), so chmod against it would fail with EROFS.
|
||||||
|
# install(1) handles permissions/ownership atomically against the destination.
|
||||||
|
#
|
||||||
|
# Per M22 Phase 9 file-only delivery (H-SECRET-4): no credential value enters
|
||||||
|
# an env var.
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
# Extract SSH private key from decrypted env file and write to the per-host
|
SSH_KEY_SRC="/run/agent/secrets/gitea-ssh/private_key"
|
||||||
# identity file path. The meta-init script generates ~/.ssh/config with
|
SSH_KEY_DST="/home/agent/.ssh/gitea-oreillyit-nz-ai-enablement"
|
||||||
# IdentityFile /home/agent/.ssh/gitea-oreillyit-nz-ai-enablement
|
|
||||||
# matching the ssh_hosts alias in harness.yaml.
|
|
||||||
|
|
||||||
SSH_KEY_FILE="/home/agent/.ssh/gitea-oreillyit-nz-ai-enablement"
|
if [ ! -r "$SSH_KEY_SRC" ]; then
|
||||||
|
echo "ERROR: SSH key not found at $SSH_KEY_SRC — ESO ExternalSecret not Ready?" >&2
|
||||||
# Find the decrypted env file (dispatcher decrypts SOPS at dispatch time for K8s,
|
exit 1
|
||||||
# or the meta-init script decrypts for Docker)
|
|
||||||
for env_file in /opt/harness/secrets/gitea-ssh/*.decrypted.env /opt/harness/secrets/gitea-ssh/*.env; do
|
|
||||||
[ -f "$env_file" ] || continue
|
|
||||||
while IFS='=' read -r key value; do
|
|
||||||
# Skip comments and blank lines
|
|
||||||
[[ "$key" =~ ^[[:space:]]*# ]] && continue
|
|
||||||
[[ -z "$key" ]] && continue
|
|
||||||
if [ "$key" = "GITEA_SSH_KEY" ]; then
|
|
||||||
mkdir -p /home/agent/.ssh
|
|
||||||
echo "$value" | base64 -d > "$SSH_KEY_FILE"
|
|
||||||
chmod 600 "$SSH_KEY_FILE"
|
|
||||||
chown agent:agent "$SSH_KEY_FILE"
|
|
||||||
echo "SSH key written to $SSH_KEY_FILE"
|
|
||||||
break 2
|
|
||||||
fi
|
|
||||||
done < "$env_file"
|
|
||||||
done
|
|
||||||
|
|
||||||
if [ ! -f "$SSH_KEY_FILE" ]; then
|
|
||||||
echo "WARNING: GITEA_SSH_KEY not found in any env file under /opt/harness/secrets/gitea-ssh/"
|
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
mkdir -p /home/agent/.ssh
|
||||||
|
install -m 0600 -o agent -g agent "$SSH_KEY_SRC" "$SSH_KEY_DST"
|
||||||
|
echo "gitea-ssh: SSH key staged at $SSH_KEY_DST (0600 agent:agent)"
|
||||||
|
|||||||
9
harnesses/contexts/minimax/v1/bin/anthropic-compat-wrapper.sh
Executable file
9
harnesses/contexts/minimax/v1/bin/anthropic-compat-wrapper.sh
Executable file
@@ -0,0 +1,9 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# Anthropic-compat wrapper for MiniMax (Phase 9 ESO-managed secrets).
|
||||||
|
# Reads the api_key file and passes it as ANTHROPIC_AUTH_TOKEN to claude.
|
||||||
|
# ANTHROPIC_BASE_URL is set in harness.yaml `env:` and flows through.
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
exec env \
|
||||||
|
ANTHROPIC_AUTH_TOKEN="$(cat /run/agent/secrets/minimax/api_key)" \
|
||||||
|
claude "$@"
|
||||||
@@ -11,9 +11,13 @@ env:
|
|||||||
CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC: "1"
|
CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC: "1"
|
||||||
DISABLE_PROMPT_CACHING: "1"
|
DISABLE_PROMPT_CACHING: "1"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./provider.sops.env
|
- name: minimax
|
||||||
target: /opt/harness/secrets/minimax/provider.sops.env
|
account_ref: "minimax"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/minimax
|
||||||
|
mode: "0400"
|
||||||
|
|
||||||
# TODO: Add network_hosts for api.minimax.io when context harnesses support it
|
scripts:
|
||||||
|
init: ./init.sh
|
||||||
|
|
||||||
|
# TODO: Add network_hosts for api.minimax.io when context harnesses support it
|
||||||
|
|||||||
18
harnesses/contexts/minimax/v1/init.sh
Executable file
18
harnesses/contexts/minimax/v1/init.sh
Executable file
@@ -0,0 +1,18 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
# Verify the ESO-managed MiniMax api_key file is mounted. The wrapper
|
||||||
|
# (`bin/anthropic-compat-wrapper.sh`) reads it at exec time and exports
|
||||||
|
# ANTHROPIC_AUTH_TOKEN to the claude subprocess.
|
||||||
|
#
|
||||||
|
# ANTHROPIC_BASE_URL is set in harness.yaml `env:` (not in the K8s Secret),
|
||||||
|
# so no file check is required for it.
|
||||||
|
|
||||||
|
API_KEY_FILE="/run/agent/secrets/minimax/api_key"
|
||||||
|
|
||||||
|
if [ ! -r "$API_KEY_FILE" ]; then
|
||||||
|
echo "ERROR: $API_KEY_FILE not readable. Check ESO ExternalSecret acct-<minimax-id>." >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "minimax api_key verified at $API_KEY_FILE"
|
||||||
12
harnesses/contexts/z-ai/v1/bin/anthropic-compat-wrapper.sh
Executable file
12
harnesses/contexts/z-ai/v1/bin/anthropic-compat-wrapper.sh
Executable file
@@ -0,0 +1,12 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# z-ai Anthropic-compatible wrapper — injects ESO-mounted credentials
|
||||||
|
# M22 Phase 9 Wave 4
|
||||||
|
# Files at /run/agent/secrets/z-ai/ are mounted by the dispatcher via ESO K8s Secret
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
SECRETS_DIR="/run/agent/secrets/z-ai"
|
||||||
|
|
||||||
|
exec env \
|
||||||
|
ANTHROPIC_AUTH_TOKEN="$(cat "$SECRETS_DIR/auth_token")" \
|
||||||
|
ANTHROPIC_BASE_URL="$(cat "$SECRETS_DIR/base_url")" \
|
||||||
|
claude "$@"
|
||||||
@@ -11,9 +11,13 @@ env:
|
|||||||
CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC: "1"
|
CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC: "1"
|
||||||
DISABLE_PROMPT_CACHING: "1"
|
DISABLE_PROMPT_CACHING: "1"
|
||||||
|
|
||||||
secrets_files:
|
secrets_required:
|
||||||
- source: ./provider.sops.env
|
- name: z-ai
|
||||||
target: /opt/harness/secrets/z-ai/provider.sops.env
|
account_ref: "z-ai"
|
||||||
encrypted: true
|
mount_path: /run/agent/secrets/z-ai
|
||||||
|
mode: "0400"
|
||||||
|
|
||||||
|
scripts:
|
||||||
|
init: "./init.sh"
|
||||||
|
|
||||||
# TODO: Add network_hosts for api.z.ai when context harnesses support it
|
# TODO: Add network_hosts for api.z.ai when context harnesses support it
|
||||||
16
harnesses/contexts/z-ai/v1/init.sh
Executable file
16
harnesses/contexts/z-ai/v1/init.sh
Executable file
@@ -0,0 +1,16 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
# z-ai harness init — verifies ESO secret mount exists
|
||||||
|
# M22 Phase 9 Wave 4
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
echo "=== z-ai/v1 init ==="
|
||||||
|
|
||||||
|
SECRETS_DIR="/run/agent/secrets/z-ai"
|
||||||
|
if [ ! -d "$SECRETS_DIR" ]; then
|
||||||
|
echo "ERROR: ESO secret mount not found at $SECRETS_DIR" >&2
|
||||||
|
echo "Has the dispatcher been configured with ESO-managed secrets?" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "z-ai ESO secret mount verified at $SECRETS_DIR"
|
||||||
|
echo "=== z-ai/v1 init complete ==="
|
||||||
Reference in New Issue
Block a user