mirror of
https://github.com/ThearchyHelios/AgentLab.git
synced 2026-11-15 00:21:58 +00:00
复核 R-d5(dev.sh 读 .env 不全):认 KEY = value(等号两边有空格,和后端的 dotenv 一致);放开发库密码的数据目录也照「环境变量 > backend/.env > .env」读 AGENTLAB_DATA_DIR,相对路径按后端的工作目录 backend/ 算,.postgres-dev 落在后端实际用的数据目录下。单测:等号带空格、export、行尾注释、backend/.env 优先、相对的数据目录
This commit is contained in:
+2
-1
@@ -53,7 +53,8 @@
|
|||||||
|
|
||||||
# ---- 开发用 PostgreSQL(./scripts/dev.sh --postgres)----
|
# ---- 开发用 PostgreSQL(./scripts/dev.sh --postgres)----
|
||||||
# 这几项只有 dev.sh 读:写成环境变量或写在这个 .env 里都行(环境变量优先)。数据在 docker 数据卷里,
|
# 这几项只有 dev.sh 读:写成环境变量或写在这个 .env 里都行(环境变量优先)。数据在 docker 数据卷里,
|
||||||
# 密码第一次自动生成在 data/.postgres-dev/,dev.sh 照它设 AGENTLAB_DATABASE_URL(盖过上面写的)
|
# 密码第一次自动生成在数据目录(和后端一样照 AGENTLAB_DATA_DIR,缺省 data/)的 .postgres-dev/ 里,
|
||||||
|
# dev.sh 照它设 AGENTLAB_DATABASE_URL(盖过上面写的)
|
||||||
# AGENTLAB_DEV_PG_CONTAINER=agentlab-dev-postgres
|
# AGENTLAB_DEV_PG_CONTAINER=agentlab-dev-postgres
|
||||||
# AGENTLAB_DEV_PG_PORT=55432
|
# AGENTLAB_DEV_PG_PORT=55432
|
||||||
# AGENTLAB_DEV_PG_VOLUME=agentlab-dev-pgdata
|
# AGENTLAB_DEV_PG_VOLUME=agentlab-dev-pgdata
|
||||||
|
|||||||
@@ -813,7 +813,7 @@ def test_env_example_lists_every_database_pool_and_multiprocess_setting():
|
|||||||
names = {f"AGENTLAB_{name.upper()}" for name in Settings.model_fields if name.startswith(prefixes)}
|
names = {f"AGENTLAB_{name.upper()}" for name in Settings.model_fields if name.startswith(prefixes)}
|
||||||
assert {"AGENTLAB_DATABASE_URL", "AGENTLAB_DATABASE_DIRECT_URL", "AGENTLAB_DB_PGBOUNCER", "AGENTLAB_WORKERS",
|
assert {"AGENTLAB_DATABASE_URL", "AGENTLAB_DATABASE_DIRECT_URL", "AGENTLAB_DB_PGBOUNCER", "AGENTLAB_WORKERS",
|
||||||
"AGENTLAB_WORKER_LEASE_S", "AGENTLAB_DB_STARTUP_TIMEOUT", "AGENTLAB_SCHEDULER_TICK_S"} <= names
|
"AGENTLAB_WORKER_LEASE_S", "AGENTLAB_DB_STARTUP_TIMEOUT", "AGENTLAB_SCHEDULER_TICK_S"} <= names
|
||||||
dev = set(re.findall(r"dev_pg_setting (AGENTLAB_DEV_PG_[A-Z_]+)", (REPO / "scripts" / "dev.sh").read_text()))
|
dev = set(re.findall(r"dotenv_setting (AGENTLAB_DEV_PG_[A-Z_]+)", (REPO / "scripts" / "dev.sh").read_text()))
|
||||||
assert len(dev) == 4
|
assert len(dev) == 4
|
||||||
example = (REPO / ".env.example").read_text(encoding="utf-8")
|
example = (REPO / ".env.example").read_text(encoding="utf-8")
|
||||||
listed = set(re.findall(r"^# (AGENTLAB_[A-Z_]+)=", example, re.M))
|
listed = set(re.findall(r"^# (AGENTLAB_[A-Z_]+)=", example, re.M))
|
||||||
@@ -827,9 +827,12 @@ def test_dev_script_reads_its_postgres_settings_from_dotenv(tmp_path):
|
|||||||
(root / "scripts").mkdir(parents=True)
|
(root / "scripts").mkdir(parents=True)
|
||||||
(root / "frontend" / "node_modules").mkdir(parents=True)
|
(root / "frontend" / "node_modules").mkdir(parents=True)
|
||||||
shutil.copy(REPO / "scripts" / "dev.sh", root / "scripts" / "dev.sh")
|
shutil.copy(REPO / "scripts" / "dev.sh", root / "scripts" / "dev.sh")
|
||||||
(root / "backend").symlink_to(REPO / "backend")
|
(root / ".env").write_text("AGENTLAB_DEV_PG_CONTAINER=from-root-env\nAGENTLAB_DEV_PG_PORT = 55491 # 注释\n"
|
||||||
(root / ".env").write_text("AGENTLAB_DEV_PG_CONTAINER=from-root-env\nAGENTLAB_DEV_PG_PORT=55491\n"
|
"export AGENTLAB_DEV_PG_VOLUME = 'quoted-vol' \nAGENTLAB_DATA_DIR=from-root\n")
|
||||||
"AGENTLAB_DEV_PG_VOLUME='quoted-vol' \n")
|
# backend/.env 比 .env 优先(同后端):数据目录写相对路径,按后端的工作目录 backend/ 算
|
||||||
|
(root / "backend").mkdir()
|
||||||
|
(root / "backend" / ".env").write_text("AGENTLAB_DATA_DIR = ../devdata\n")
|
||||||
|
(root / "backend" / "app").symlink_to(REPO / "backend" / "app")
|
||||||
bin_dir = tmp_path / "bin"
|
bin_dir = tmp_path / "bin"
|
||||||
bin_dir.mkdir()
|
bin_dir.mkdir()
|
||||||
log = tmp_path / "docker.log"
|
log = tmp_path / "docker.log"
|
||||||
@@ -839,7 +842,7 @@ def test_dev_script_reads_its_postgres_settings_from_dotenv(tmp_path):
|
|||||||
'container) exit 1 ;; run) exit 1 ;; esac\nexit 0\n')
|
'container) exit 1 ;; run) exit 1 ;; esac\nexit 0\n')
|
||||||
for f in bin_dir.iterdir():
|
for f in bin_dir.iterdir():
|
||||||
f.chmod(0o755)
|
f.chmod(0o755)
|
||||||
env = {"PATH": f"{bin_dir}:/usr/bin:/bin:/usr/sbin:/sbin", "HOME": str(tmp_path), "AGENTLAB_DATA_DIR": str(tmp_path / "data"),
|
env = {"PATH": f"{bin_dir}:/usr/bin:/bin:/usr/sbin:/sbin", "HOME": str(tmp_path),
|
||||||
"AGENTLAB_DEV_PG_IMAGE": "postgres:from-env", "AGENTLAB_PORT": "18799", "LANG": "C.UTF-8"}
|
"AGENTLAB_DEV_PG_IMAGE": "postgres:from-env", "AGENTLAB_PORT": "18799", "LANG": "C.UTF-8"}
|
||||||
out = subprocess.run(["bash", str(root / "scripts" / "dev.sh"), "--postgres"], capture_output=True, text=True, env=env,
|
out = subprocess.run(["bash", str(root / "scripts" / "dev.sh"), "--postgres"], capture_output=True, text=True, env=env,
|
||||||
timeout=60)
|
timeout=60)
|
||||||
@@ -848,7 +851,10 @@ def test_dev_script_reads_its_postgres_settings_from_dotenv(tmp_path):
|
|||||||
assert "--name from-root-env" in run and "127.0.0.1:55491:5432" in run, ".env 里的生效"
|
assert "--name from-root-env" in run and "127.0.0.1:55491:5432" in run, ".env 里的生效"
|
||||||
assert "quoted-vol:/var/lib/postgresql/data" in run, "引号和行尾空白去掉"
|
assert "quoted-vol:/var/lib/postgresql/data" in run, "引号和行尾空白去掉"
|
||||||
assert run.endswith("postgres:from-env"), "环境变量优先"
|
assert run.endswith("postgres:from-env"), "环境变量优先"
|
||||||
(root / "backend").unlink()
|
data = root / "backend" / ".." / "devdata"
|
||||||
|
assert f"{data}/.postgres-dev/password:/run/agentlab/password:ro" in run, "密码放在后端实际用的数据目录里"
|
||||||
|
assert (root / "devdata" / ".postgres-dev" / "pgpass").exists()
|
||||||
|
(root / "backend" / "app").unlink()
|
||||||
|
|
||||||
|
|
||||||
def test_dev_script_refuses_unknown_arguments_and_documents_postgres():
|
def test_dev_script_refuses_unknown_arguments_and_documents_postgres():
|
||||||
|
|||||||
+19
-12
@@ -73,19 +73,24 @@ fi
|
|||||||
export AGENTLAB_PORT="$API_PORT"
|
export AGENTLAB_PORT="$API_PORT"
|
||||||
|
|
||||||
# ---- --postgres:本地开发用的 PostgreSQL ----
|
# ---- --postgres:本地开发用的 PostgreSQL ----
|
||||||
# 这几项(AGENTLAB_DEV_PG_*)只有这个脚本用。和后端的配置一样认 .env:环境变量 > backend/.env > .env > 缺省(后端的 settings
|
# 这几项(AGENTLAB_DEV_PG_*,还有数据目录 AGENTLAB_DATA_DIR)和后端的配置一样认 .env:环境变量 > backend/.env > .env > 缺省
|
||||||
# 读这两个文件,后一个优先)。不 source:.env 是给后端按 KEY=VALUE 读的,不是 shell(值里的 $、空格、反引号不该被执行)
|
# (后端的 settings 读这两个文件,后一个优先)。写法照后端的 dotenv:KEY=value、KEY = value、export KEY=value、引号、行尾 # 注释。
|
||||||
|
# 不 source:.env 是给后端按 KEY=VALUE 读的,不是 shell(值里的 $、空格、反引号不该被执行)
|
||||||
dotenv_value() {
|
dotenv_value() {
|
||||||
local key="$1" file line val="" found=""
|
local key="$1" file line name val="" found=""
|
||||||
for file in "$ROOT/.env" "$ROOT/backend/.env"; do
|
for file in "$ROOT/.env" "$ROOT/backend/.env"; do
|
||||||
[ -f "$file" ] || continue
|
[ -f "$file" ] || continue
|
||||||
while IFS= read -r line || [ -n "$line" ]; do
|
while IFS= read -r line || [ -n "$line" ]; do
|
||||||
line="${line%$'\r'}"
|
line="${line%$'\r'}"
|
||||||
line="${line#"${line%%[![:space:]]*}"}"
|
line="${line#"${line%%[![:space:]]*}"}"
|
||||||
line="${line#export }"
|
line="${line#export }"
|
||||||
case "$line" in
|
case "$line" in *=*) ;; *) continue ;; esac
|
||||||
"$key="*) val="${line#*=}"; found=1 ;;
|
name="${line%%=*}"
|
||||||
esac
|
name="${name%"${name##*[![:space:]]}"}"
|
||||||
|
[ "$name" = "$key" ] || continue
|
||||||
|
val="${line#*=}"
|
||||||
|
val="${val#"${val%%[![:space:]]*}"}"
|
||||||
|
found=1
|
||||||
done < "$file"
|
done < "$file"
|
||||||
done
|
done
|
||||||
[ -n "$found" ] || return 1
|
[ -n "$found" ] || return 1
|
||||||
@@ -96,18 +101,20 @@ dotenv_value() {
|
|||||||
esac
|
esac
|
||||||
printf '%s' "$val"
|
printf '%s' "$val"
|
||||||
}
|
}
|
||||||
dev_pg_setting() {
|
dotenv_setting() {
|
||||||
local value
|
local value
|
||||||
value="$(printenv "$1" 2>/dev/null || true)"
|
value="$(printenv "$1" 2>/dev/null || true)"
|
||||||
[ -n "$value" ] || value="$(dotenv_value "$1" || true)"
|
[ -n "$value" ] || value="$(dotenv_value "$1" || true)"
|
||||||
printf '%s' "${value:-$2}"
|
printf '%s' "${value:-$2}"
|
||||||
}
|
}
|
||||||
if [ -n "$WITH_PG" ]; then
|
if [ -n "$WITH_PG" ]; then
|
||||||
PG_CONTAINER="$(dev_pg_setting AGENTLAB_DEV_PG_CONTAINER agentlab-dev-postgres)"
|
PG_CONTAINER="$(dotenv_setting AGENTLAB_DEV_PG_CONTAINER agentlab-dev-postgres)"
|
||||||
PG_PORT="$(dev_pg_setting AGENTLAB_DEV_PG_PORT 55432)"
|
PG_PORT="$(dotenv_setting AGENTLAB_DEV_PG_PORT 55432)"
|
||||||
PG_VOLUME="$(dev_pg_setting AGENTLAB_DEV_PG_VOLUME agentlab-dev-pgdata)"
|
PG_VOLUME="$(dotenv_setting AGENTLAB_DEV_PG_VOLUME agentlab-dev-pgdata)"
|
||||||
PG_IMAGE="$(dev_pg_setting AGENTLAB_DEV_PG_IMAGE postgres:16)"
|
PG_IMAGE="$(dotenv_setting AGENTLAB_DEV_PG_IMAGE postgres:16)"
|
||||||
DEV_DATA="${AGENTLAB_DATA_DIR:-$ROOT/data}"
|
# 密码文件放在后端实际用的数据目录里:和后端一样读 AGENTLAB_DATA_DIR,相对路径按后端的工作目录(backend/)算
|
||||||
|
DEV_DATA="$(dotenv_setting AGENTLAB_DATA_DIR "$ROOT/data")"
|
||||||
|
case "$DEV_DATA" in /*) ;; *) DEV_DATA="$ROOT/backend/$DEV_DATA" ;; esac
|
||||||
case "$PG_PORT" in ''|*[!0-9]*) echo "AGENTLAB_DEV_PG_PORT 要是端口号:$PG_PORT"; exit 2 ;; esac
|
case "$PG_PORT" in ''|*[!0-9]*) echo "AGENTLAB_DEV_PG_PORT 要是端口号:$PG_PORT"; exit 2 ;; esac
|
||||||
command -v docker >/dev/null || { echo "--postgres 要用 docker,没找到它"; exit 1; }
|
command -v docker >/dev/null || { echo "--postgres 要用 docker,没找到它"; exit 1; }
|
||||||
docker version --format '{{.Server.Version}}' >/dev/null 2>&1 || { echo "连不上 docker 服务,先把 Docker 启动起来"; exit 1; }
|
docker version --format '{{.Server.Version}}' >/dev/null 2>&1 || { echo "连不上 docker 服务,先把 Docker 启动起来"; exit 1; }
|
||||||
|
|||||||
Reference in New Issue
Block a user