108 lines
4.6 KiB
Bash
108 lines
4.6 KiB
Bash
#!/usr/bin/env bash
|
||
# m11b-1a 实库验证:拉起一次性本地 MariaDB(独立 datadir + 独立端口),
|
||
# 用**部署同款路径**(mariadb CLI + DELIMITER)装载生成器产出的 DDL,
|
||
# 再跑 tests/test_m11b1a_ddl_runtime.py 的 A+B 两层,结束后彻底销毁。
|
||
#
|
||
# 为什么自造库而不是连 projects/pbls/env/test.json:
|
||
# verify_db()/prune_partitions 会真做 DROP PARTITION 与 INSERT/DELETE 探针,
|
||
# 在共享测试库上跑等于拿别人的数据做破坏性实验;且本沙箱内 3306 端口的
|
||
# MariaDB 对 pbls 账号是 unix_socket 鉴权(1698 Access denied),根本连不上。
|
||
# 连接参数(user/dbname/password)仍从 env/test.json 读取,不硬编码凭据。
|
||
#
|
||
# 装载方式说明:生成器产出的 B/C 段含多语句过程体,按文件头注释规定必须用
|
||
# mysql/mariadb CLI(DELIMITER)执行;故本 runner 用 CLI 装载,
|
||
# 顺带证明 --emit/full_script() 产出的 SQL 在 MariaDB 10.6 上可原样执行。
|
||
#
|
||
# 用法:bash tests/run_m11b1a_localdb.sh (退出码 0 = 全 PASS)
|
||
set -u
|
||
HERE="$(cd "$(dirname "$0")" && pwd)"
|
||
MODULE_DIR="$(dirname "$HERE")"
|
||
D="${TMPDIR:-/tmp}/m11b1a_localdb_$$"
|
||
PORT="${M11B1A_DB_PORT:-13306}"
|
||
SOCK="$D/my.sock"
|
||
LOG="$D/server.err"
|
||
|
||
cleanup() {
|
||
if [[ -f "$D/my.pid" ]]; then
|
||
kill "$(cat "$D/my.pid")" 2>/dev/null || true
|
||
sleep 1
|
||
fi
|
||
pkill -f "datadir=$D" 2>/dev/null || true
|
||
rm -rf "$D"
|
||
}
|
||
trap cleanup EXIT INT TERM
|
||
|
||
echo "[runner] datadir=$D port=$PORT"
|
||
mkdir -p "$D"
|
||
|
||
mariadb-install-db --user="$(id -un)" --datadir="$D" \
|
||
--auth-root-authentication-method=normal > "$D/install.log" 2>&1 || {
|
||
echo "[runner] FAIL: mariadb-install-db 失败"; tail -20 "$D/install.log"; exit 1; }
|
||
|
||
mariadbd --user="$(id -un)" --datadir="$D" --socket="$SOCK" \
|
||
--port="$PORT" --bind-address=127.0.0.1 --pid-file="$D/my.pid" \
|
||
--skip-name-resolve --log-error="$LOG" > /dev/null 2>&1 &
|
||
|
||
for i in $(seq 1 40); do
|
||
if mariadb --protocol=tcp -h 127.0.0.1 -P "$PORT" -u root -e "SELECT 1" >/dev/null 2>&1; then
|
||
echo "[runner] mariadbd ready (${i}s)"; break
|
||
fi
|
||
sleep 1
|
||
done
|
||
|
||
if ! mariadb --protocol=tcp -h 127.0.0.1 -P "$PORT" -u root -e "SELECT VERSION()" >/dev/null 2>&1; then
|
||
echo "[runner] FAIL: mariadbd 未在 40s 内就绪"; tail -20 "$LOG" 2>/dev/null; exit 1
|
||
fi
|
||
|
||
# 按 env/test.json 建库建号(凭据只在进程内使用,不 echo、不落盘、不 commit)
|
||
python3 - "$MODULE_DIR" "$PORT" <<'PY' || exit 1
|
||
import json, os, subprocess, sys
|
||
module_dir, port = sys.argv[1], sys.argv[2]
|
||
ws = os.path.dirname(os.path.dirname(module_dir))
|
||
db = json.load(open(os.path.join(ws, "projects", "pbls", "env", "test.json"), encoding="utf-8"))["db"]
|
||
name, user, pw = db["dbname"], db["user"], db["password"]
|
||
sql = ("CREATE DATABASE IF NOT EXISTS `%s` CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci;\n"
|
||
"CREATE USER IF NOT EXISTS '%s'@'%%' IDENTIFIED BY '%s';\n"
|
||
"GRANT ALL PRIVILEGES ON *.* TO '%s'@'%%' WITH GRANT OPTION;\n"
|
||
"FLUSH PRIVILEGES;\n"
|
||
% (name, user, pw.replace("'", "''"), user))
|
||
r = subprocess.run(["mariadb", "--protocol=tcp", "-h", "127.0.0.1", "-P", port, "-u", "root"],
|
||
input=sql, capture_output=True, text=True)
|
||
if r.returncode:
|
||
print("[runner] FAIL: 建库建号失败(错误信息已脱敏): %s" % r.stderr.replace(pw, "***")[:300])
|
||
sys.exit(1)
|
||
print("[runner] db=%s user=%s 就绪(一次性库,与项目 test/prod 无关)" % (name, user))
|
||
PY
|
||
|
||
# 生成器产出的完整脚本(A 建表 + B append-only + C 分区维护 + D 一次性改造)落到临时目录,
|
||
# 用 mariadb CLI(支持 DELIMITER)装载 —— 与部署执行路径一致。
|
||
python3 - "$MODULE_DIR" "$D/full.sql" <<'PY' || exit 1
|
||
import importlib.util, os, sys
|
||
module_dir, out = sys.argv[1], sys.argv[2]
|
||
script = os.path.join(module_dir, "scripts", "pbl_runtime_event_ddl.py")
|
||
spec = importlib.util.spec_from_file_location("pbl_runtime_event_ddl", script)
|
||
mod = importlib.util.module_from_spec(spec)
|
||
spec.loader.exec_module(mod)
|
||
open(out, "w", encoding="utf-8").write(mod.full_script())
|
||
print("[runner] full_script() 渲染 %d bytes -> %s" % (os.path.getsize(out), out))
|
||
PY
|
||
|
||
echo "[runner] 装载 DDL(mariadb CLI + DELIMITER)"
|
||
mariadb --protocol=tcp -h 127.0.0.1 -P "$PORT" -u root pbls < "$D/full.sql" 2> "$D/load.err"
|
||
LOAD_RC=$?
|
||
if [[ "$LOAD_RC" != "0" ]]; then
|
||
echo "[runner] FAIL: DDL 装载 rc=$LOAD_RC"
|
||
sed -e "s/'[^']*'@/'***'@/g" "$D/load.err" | head -20
|
||
else
|
||
echo "[runner] DDL 装载 rc=0(stderr 见下,应为空)"
|
||
head -5 "$D/load.err"
|
||
fi
|
||
|
||
export M11B1A_LOCAL_DB=1
|
||
export M11B1A_DB_HOST=127.0.0.1
|
||
export M11B1A_DB_PORT="$PORT"
|
||
python3 "$HERE/test_m11b1a_ddl_runtime.py"
|
||
rc=$?
|
||
echo "[runner] harness rc=$rc"
|
||
exit $rc
|