Files
AI-Profile-Router/platform/hermes/install-hermes.sh

87 lines
3.6 KiB
Bash
Executable File

#!/usr/bin/env bash
set -Eeuo pipefail
umask 077
STACK_DIR=${STACK_DIR:-/opt/mike-ai/stack}
SECRETS_DIR=${SECRETS_DIR:-/etc/mike-ai}
HERMES_DATA_DIR=${HERMES_DATA_DIR:-/data/hermes}
MUA_ENV=${MUA_ENV:-$SECRETS_DIR/mua-mcp.env}
die() { printf 'FEHLER: %s\n' "$*" >&2; exit 1; }
[[ $EUID -eq 0 ]] || die "Bitte als root ausführen."
[[ -s $SECRETS_DIR/router-api-key ]] || die "Router-API-Key fehlt."
[[ -s $STACK_DIR/platform/hermes/config.yaml ]] || die "Hermes-Konfiguration fehlt im Stack."
[[ -s $STACK_DIR/platform/hermes/SOUL.md ]] || die "Hermes-Systemanweisung fehlt im Stack."
install -d -m 0700 "$HERMES_DATA_DIR"
install -d -m 0750 "$HERMES_DATA_DIR/workspace"
[[ -s $SECRETS_DIR/hermes-api-key ]] || openssl rand -base64 48 >"$SECRETS_DIR/hermes-api-key"
[[ -s $SECRETS_DIR/hermes-dashboard-password ]] || openssl rand -base64 24 >"$SECRETS_DIR/hermes-dashboard-password"
[[ -s $SECRETS_DIR/hermes-dashboard-secret ]] || openssl rand -base64 48 >"$SECRETS_DIR/hermes-dashboard-secret"
for secret in \
"$SECRETS_DIR/hermes-api-key" \
"$SECRETS_DIR/hermes-dashboard-password" \
"$SECRETS_DIR/hermes-dashboard-secret"; do
# The Athena operator receives /etc/mike-ai read-only. A managed secret that
# is already mode 0600 needs no write at all, which keeps this installer
# safely idempotent both interactively and through the operator.
[[ $(stat -c '%a' "$secret") == 600 ]] || chmod 0600 "$secret"
done
router_key=$(<"$SECRETS_DIR/router-api-key")
mua_url=http://127.0.0.1:9/mcp
mua_token=not-configured
if [[ -s $MUA_ENV ]]; then
mua_url=$(sed -n 's/^MUA_MCP_URL=//p' "$MUA_ENV" | head -n 1)
mua_token=$(sed -n 's/^MUA_MCP_BEARER_TOKEN=//p' "$MUA_ENV" | head -n 1)
[[ -n $mua_url && -n $mua_token ]] || die "MUA URL oder Token fehlt."
fi
cat >"$HERMES_DATA_DIR/.env" <<EOF
ROUTER_API_KEY=$router_key
VOICE_TOOLS_OPENAI_KEY=$router_key
MUA_MCP_URL=$mua_url
MUA_MCP_BEARER_TOKEN=$mua_token
API_SERVER_ENABLED=true
API_SERVER_HOST=0.0.0.0
API_SERVER_PORT=8642
API_SERVER_KEY=$(<"$SECRETS_DIR/hermes-api-key")
API_SERVER_MODEL_NAME=MikeAI-Hermes
HERMES_DASHBOARD=1
HERMES_DASHBOARD_HOST=0.0.0.0
HERMES_DASHBOARD_PORT=9119
HERMES_DASHBOARD_BASIC_AUTH_USERNAME=michael
HERMES_DASHBOARD_BASIC_AUTH_PASSWORD=$(<"$SECRETS_DIR/hermes-dashboard-password")
HERMES_DASHBOARD_BASIC_AUTH_SECRET=$(<"$SECRETS_DIR/hermes-dashboard-secret")
EOF
chmod 0600 "$HERMES_DATA_DIR/.env"
if [[ -s $HERMES_DATA_DIR/config.yaml ]] && \
! cmp -s "$STACK_DIR/platform/hermes/config.yaml" "$HERMES_DATA_DIR/config.yaml"; then
cp -a "$HERMES_DATA_DIR/config.yaml" \
"$HERMES_DATA_DIR/config.yaml.before-managed-update-$(date +%Y%m%d-%H%M%S)"
fi
install -m 0600 "$STACK_DIR/platform/hermes/config.yaml" "$HERMES_DATA_DIR/config.yaml"
# Hermes expands environment variables in some runtime paths, but model.api_key
# is persisted and reloaded literally when a client changes the model. Render
# this one managed placeholder before the configuration becomes live.
ROUTER_API_KEY="$router_key" python3 - "$HERMES_DATA_DIR/config.yaml" <<'PY'
import os
import pathlib
import sys
path = pathlib.Path(sys.argv[1])
text = path.read_text()
placeholder = "${ROUTER_API_KEY}"
if placeholder not in text:
raise SystemExit("ROUTER_API_KEY placeholder missing from managed Hermes config")
path.write_text(text.replace(placeholder, os.environ["ROUTER_API_KEY"], 1))
PY
python3 "$STACK_DIR/platform/mcp/sync-clients.py" \
--registry "$STACK_DIR/config/mcp-registry.json" \
--hermes "$HERMES_DATA_DIR/config.yaml"
install -m 0600 "$STACK_DIR/platform/hermes/SOUL.md" "$HERMES_DATA_DIR/SOUL.md"
chown -R 10000:10000 "$HERMES_DATA_DIR"
"$STACK_DIR/platform/hermes/install-skills.sh"
printf 'HERMES_CONFIG_OK %s\n' "$HERMES_DATA_DIR"