181 lines
7.6 KiB
Bash
Executable File
181 lines
7.6 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# ════════════════════════════════════════════════════════════════
|
|
# 根据探测档位动态生成资源调优 · tune-from-env.sh
|
|
# Sovereign: TCS-0002∞ · 国作登字-2026-A-00037559
|
|
# 守护: 铸渊 · ICE-GL-ZY001
|
|
# ════════════════════════════════════════════════════════════════
|
|
#
|
|
# 读 detect-env.sh 写出的 server-env.json, 依据 size_tier 生成:
|
|
# 1. $DATA_ROOT/lighthouse/.env.tune — 决策快照
|
|
# 含 SIZE_TIER / PG_SHARED_BUFFERS / PG_WORK_MEM / PG_MAX_CONN
|
|
# / GITEA_CACHE_POOL / GITEA_QUEUE_LENGTH / RUNNER_DEFAULT_ENABLED
|
|
# 2. 决策回执 -> $DEPLOY_ROOT/_logs/tune-decision-*.json
|
|
#
|
|
# ⚠️ 当前 .env.tune 的真实作用域 (2026-05-08 修正, 别再被注释误导):
|
|
# .env.tune 不是 docker-compose 的 env_file. compose 启动时不会
|
|
# 自动读它 (docker-compose.yml 没有 env_file: .env.tune 声明).
|
|
#
|
|
# bootstrap.sh 会在调 docker compose up 之前 `source .env.tune`,
|
|
# **当前真正影响行为的只有 RUNNER_DEFAULT_ENABLED** — 它决定 update
|
|
# 阶段是否带 `--profile runner` 起 runner 容器.
|
|
#
|
|
# PG_SHARED_BUFFERS / PG_WORK_MEM / PG_MAX_CONN / GITEA_CACHE_POOL /
|
|
# GITEA_QUEUE_LENGTH 这些字段目前**只是档位决策的存档**, 写到 .env.tune
|
|
# 是为了:
|
|
# a) tune-decision-*.json 回执留痕 (霜砚 / 冰朔可追溯)
|
|
# b) 后续如果在 docker-compose.yml 加上 `env_file: ./.env.tune` +
|
|
# 在 postgres / gitea 服务里用 `${PG_SHARED_BUFFERS}` 引用,
|
|
# 这一份就立刻生效, 不用改 tune-from-env.sh
|
|
#
|
|
# 也就是说: 这个脚本现在做的事 = "决策 + 留档", 不是"实时调 PG".
|
|
# 要让 PG 调优真的生效, 需要在 docker-compose.yml 里手动加引用
|
|
# (TODO 见 §下方).
|
|
#
|
|
# 档位策略 (因果链):
|
|
# tiny <4G : runner 关掉, postgres shared_buffers=64M, gitea cache 减半
|
|
# small 4-6G : runner 关掉, postgres shared_buffers=128M
|
|
# medium 6-12G: runner=optional (默认关), postgres shared_buffers=256M
|
|
# large 12-24G: runner=on, postgres shared_buffers=512M
|
|
# xlarge >=24G: runner=on, postgres shared_buffers=1G
|
|
#
|
|
# 设计理念:
|
|
# 不再硬假设 4C16G. 2C8G 来了也能跑(只是 runner 默认关, 不会同时塞下);
|
|
# 8C32G 来了也能跑(自动放大 PG buffer). 这一层是"动态适配"的根基.
|
|
# ════════════════════════════════════════════════════════════════
|
|
|
|
set -euo pipefail
|
|
|
|
ENV_FILE="${ENV_FILE:-/opt/guanghu/_logs/server-env.json}"
|
|
DATA_ROOT="${DATA_ROOT:-/data}"
|
|
DEPLOY_ROOT="${DEPLOY_ROOT:-/opt/guanghu}"
|
|
|
|
if [ ! -f "$ENV_FILE" ]; then
|
|
echo "❌ [tune] 找不到 $ENV_FILE, 请先跑 detect-env.sh" >&2
|
|
exit 1
|
|
fi
|
|
if ! command -v jq >/dev/null 2>&1; then
|
|
echo "❌ [tune] 需要 jq (apt-get install -y jq)" >&2
|
|
exit 1
|
|
fi
|
|
|
|
SIZE_TIER="$(jq -r '.compute.size_tier' "$ENV_FILE")"
|
|
MEM_MB="$(jq -r '.compute.memory_total_mb' "$ENV_FILE")"
|
|
CPU="$(jq -r '.compute.cpu_count' "$ENV_FILE")"
|
|
|
|
# ─── 档位 → 参数表 ────────────────────────────────────────────
|
|
case "$SIZE_TIER" in
|
|
tiny)
|
|
PG_SHARED_BUFFERS="64MB"
|
|
PG_WORK_MEM="2MB"
|
|
PG_MAX_CONN="40"
|
|
GITEA_CACHE_POOL="50"
|
|
RUNNER_DEFAULT_ENABLED="false"
|
|
GITEA_QUEUE_LENGTH="100"
|
|
NOTE="资源极少, runner 必关, 不要同时跑大型 git push"
|
|
;;
|
|
small)
|
|
PG_SHARED_BUFFERS="128MB"
|
|
PG_WORK_MEM="4MB"
|
|
PG_MAX_CONN="60"
|
|
GITEA_CACHE_POOL="100"
|
|
RUNNER_DEFAULT_ENABLED="false"
|
|
GITEA_QUEUE_LENGTH="200"
|
|
NOTE="2C8G 档. Gitea+PG+Redis 能跑, runner 默认关 (按需手动 docker compose --profile runner up)"
|
|
;;
|
|
medium)
|
|
PG_SHARED_BUFFERS="256MB"
|
|
PG_WORK_MEM="8MB"
|
|
PG_MAX_CONN="100"
|
|
GITEA_CACHE_POOL="100"
|
|
RUNNER_DEFAULT_ENABLED="false"
|
|
GITEA_QUEUE_LENGTH="500"
|
|
NOTE="主流档. runner 默认关, 大型构建任务时再开"
|
|
;;
|
|
large)
|
|
PG_SHARED_BUFFERS="512MB"
|
|
PG_WORK_MEM="16MB"
|
|
PG_MAX_CONN="200"
|
|
GITEA_CACHE_POOL="200"
|
|
RUNNER_DEFAULT_ENABLED="true"
|
|
GITEA_QUEUE_LENGTH="1000"
|
|
NOTE="原计划 4C16G 主灯塔. runner 默认开"
|
|
;;
|
|
xlarge)
|
|
PG_SHARED_BUFFERS="1GB"
|
|
PG_WORK_MEM="32MB"
|
|
PG_MAX_CONN="300"
|
|
GITEA_CACHE_POOL="300"
|
|
RUNNER_DEFAULT_ENABLED="true"
|
|
GITEA_QUEUE_LENGTH="2000"
|
|
NOTE="超规格, 全部组件并行无忧"
|
|
;;
|
|
*)
|
|
echo "❌ [tune] 未知 size_tier=$SIZE_TIER" >&2
|
|
exit 1
|
|
;;
|
|
esac
|
|
|
|
# ─── 写 .env.tune (compose 第二份 .env) ───────────────────────
|
|
TUNE_FILE="$DATA_ROOT/lighthouse/.env.tune"
|
|
mkdir -p "$(dirname "$TUNE_FILE")"
|
|
cat > "$TUNE_FILE" <<EOF
|
|
# Generated by tune-from-env.sh @ $(date -u +%Y-%m-%dT%H:%M:%SZ)
|
|
# 档位: $SIZE_TIER (基于 ${MEM_MB}MB 内存 / ${CPU} 核)
|
|
# 注: $NOTE
|
|
#
|
|
# ⚠️ 作用域说明 (避免误判):
|
|
# - bootstrap.sh source 这个文件, 当前**只读 RUNNER_DEFAULT_ENABLED**,
|
|
# 用它决定是否带 --profile runner 启 runner 容器.
|
|
# - 下面的 PG_* / GITEA_* 字段是**档位决策的快照**, docker-compose.yml
|
|
# 当前并未通过 env_file 引用本文件, 所以这些值不会自动生效到 Postgres
|
|
# / Gitea 容器内. 它们的用途是: (a) 留档可追溯 (b) 未来在 compose 里
|
|
# 加引用就能立刻生效, 无需改本脚本.
|
|
SIZE_TIER=$SIZE_TIER
|
|
PG_SHARED_BUFFERS=$PG_SHARED_BUFFERS
|
|
PG_WORK_MEM=$PG_WORK_MEM
|
|
PG_MAX_CONN=$PG_MAX_CONN
|
|
GITEA_CACHE_POOL=$GITEA_CACHE_POOL
|
|
GITEA_QUEUE_LENGTH=$GITEA_QUEUE_LENGTH
|
|
RUNNER_DEFAULT_ENABLED=$RUNNER_DEFAULT_ENABLED
|
|
EOF
|
|
chmod 644 "$TUNE_FILE"
|
|
|
|
# ─── 决策回执 ─────────────────────────────────────────────────
|
|
TS="$(date -u +%Y%m%d-%H%M%S)"
|
|
RECEIPT="$DEPLOY_ROOT/_logs/tune-decision-$TS.json"
|
|
mkdir -p "$DEPLOY_ROOT/_logs"
|
|
cat > "$RECEIPT" <<EOF
|
|
{
|
|
"_sovereign": "TCS-0002∞ · 国作登字-2026-A-00037559",
|
|
"decided_at": "$(date -u +%Y-%m-%dT%H:%M:%SZ)",
|
|
"input": {
|
|
"size_tier": "$SIZE_TIER",
|
|
"memory_mb": $MEM_MB,
|
|
"cpu_count": $CPU
|
|
},
|
|
"decision": {
|
|
"PG_SHARED_BUFFERS": "$PG_SHARED_BUFFERS",
|
|
"PG_WORK_MEM": "$PG_WORK_MEM",
|
|
"PG_MAX_CONN": $PG_MAX_CONN,
|
|
"GITEA_CACHE_POOL": $GITEA_CACHE_POOL,
|
|
"GITEA_QUEUE_LENGTH": $GITEA_QUEUE_LENGTH,
|
|
"RUNNER_DEFAULT_ENABLED": $RUNNER_DEFAULT_ENABLED
|
|
},
|
|
"note": "$NOTE",
|
|
"tune_file": "$TUNE_FILE"
|
|
}
|
|
EOF
|
|
|
|
echo "═══════════════════════════════════════════════════════════"
|
|
echo " [tune] 动态调优决策"
|
|
echo "═══════════════════════════════════════════════════════════"
|
|
echo " 档位: $SIZE_TIER (${MEM_MB}MB / ${CPU} 核)"
|
|
echo " PG shared_buf: $PG_SHARED_BUFFERS"
|
|
echo " PG max_conn: $PG_MAX_CONN"
|
|
echo " Gitea cache: $GITEA_CACHE_POOL"
|
|
echo " Runner 默认: $RUNNER_DEFAULT_ENABLED"
|
|
echo " 注: $NOTE"
|
|
echo " 写入: $TUNE_FILE"
|
|
echo " 回执: $RECEIPT"
|
|
echo "═══════════════════════════════════════════════════════════"
|