提交 b151dba1 authored 作者: 陈泽健's avatar 陈泽健

chore(deploy): Tengine 部署脚本改为 docker load 模式,更新达梦部署及集群部署文档

- X86/ARM tengine 部署脚本重构为 v2.0:docker load 替代源码编译,部署时间从 10 分钟降至 1 分钟
- 新增 X86 集群中间件安装脚本 (auto_middleware_install.sh)
- 更新 X86/ARM 达梦数据库部署脚本及 README
- 新增 Redis 集群配置说明文档
Co-Authored-By: 's avatarClaude <noreply@anthropic.com>
上级 54ee0f0d
此差异已折叠。
#!/bin/bash #!/bin/bash
# ============================================================ # ============================================================
# Tengine 容器一键部署脚本 (ARM 架构) # Tengine 容器一键部署脚本 (ARM)
# 适用于:openEuler 24.03 (aarch64) # 适用于:openEuler 24.03 (aarch64)
# 版本:1.0 # 版本:2.0 — docker load 模式,无需从源码编译
# 日期:2026-07-06 # 日期:2026-07-07
# ============================================================ # ============================================================
set -e set -e
# ==================== 配置变量 ==================== # ==================== 配置变量 ====================
# ARM 服务器 docker 需 sudo(admin 用户),X86 设为空 # ARM 服务器 docker 需 sudo(admin 用户)
DOCKER_CMD="sudo docker" DOCKER_CMD="sudo docker"
# DOCKER_CMD="docker" # X86 用这行
DEPLOY_DIR="/data/temp/tengine"
IMAGE_FILE="${DEPLOY_DIR}/utengine_v1_arm.tar"
IMAGE_NAME="utengine:v1" IMAGE_NAME="utengine:v1"
CONTAINER_NAME="utengine" CONTAINER_NAME="utengine"
OLD_CONTAINER="unginx" OLD_CONTAINER="unginx"
BUILD_DIR="/data/tengine_build"
DOCKERFILE_SRC="/data/Dockerfile.utengine"
TENGINE_TAR="/data/tengine-3.1.0.tar.gz"
# 容器运行参数
HOST_PORT="443" HOST_PORT="443"
CONTAINER_PORT="443" CONTAINER_PORT="443"
# 挂载映射(宿主机:容器:模式)
# 格式: "source:dest:mode" (mode: ro/rw)
declare -a MOUNTS=( declare -a MOUNTS=(
"/data/security/nginx_cert:/data/security/nginx_cert:ro" "/data/security/nginx_cert:/data/security/nginx_cert:ro"
"/data/services/web:/data/services/web:rw" "/data/services/web:/data/services/web:rw"
...@@ -36,7 +31,6 @@ declare -a MOUNTS=( ...@@ -36,7 +31,6 @@ declare -a MOUNTS=(
"/data/middleware/nginx/log:/var/log/tengine:rw" "/data/middleware/nginx/log:/var/log/tengine:rw"
) )
# Tengine 主配置文件(覆盖默认配置)
TENGINE_MAIN_CONF='user root; TENGINE_MAIN_CONF='user root;
worker_processes auto; worker_processes auto;
...@@ -80,30 +74,16 @@ log_step() { echo -e "${BLUE}[STEP]${NC} $1"; } ...@@ -80,30 +74,16 @@ log_step() { echo -e "${BLUE}[STEP]${NC} $1"; }
preflight_check() { preflight_check() {
log_step "执行前置检查..." log_step "执行前置检查..."
# 检查 Docker
if ! command -v ${DOCKER_CMD%% *} &> /dev/null; then if ! command -v ${DOCKER_CMD%% *} &> /dev/null; then
log_error "Docker 未安装" log_error "Docker 未安装"
exit 1 exit 1
fi fi
# 检查基础镜像 if [ ! -f "$IMAGE_FILE" ]; then
if ! ${DOCKER_CMD} image inspect nginx:1.30.2 &> /dev/null; then log_error "镜像文件不存在: $IMAGE_FILE"
log_error "基础镜像 nginx:1.30.2 不存在"
exit 1 exit 1
fi fi
# 检查源码包
if [ ! -f "$TENGINE_TAR" ]; then
log_error "Tengine 源码包不存在: $TENGINE_TAR"
exit 1
fi
if [ ! -f "$DOCKERFILE_SRC" ]; then
log_error "Dockerfile 不存在: $DOCKERFILE_SRC"
exit 1
fi
# 检查挂载源目录
for mount in "${MOUNTS[@]}"; do for mount in "${MOUNTS[@]}"; do
IFS=':' read -r src dest mode <<< "$mount" IFS=':' read -r src dest mode <<< "$mount"
if [ ! -d "$src" ] && [ ! -f "$src" ]; then if [ ! -d "$src" ] && [ ! -f "$src" ]; then
...@@ -112,58 +92,34 @@ preflight_check() { ...@@ -112,58 +92,34 @@ preflight_check() {
fi fi
done done
# 检查端口是否被占用 if ss -tlnp 2>/dev/null | grep -q ":${HOST_PORT} " || netstat -tlnp 2>/dev/null | grep -q ":${HOST_PORT} "; then
if ss -tlnp | grep -q ":${HOST_PORT} "; then
log_warn "端口 ${HOST_PORT} 已被占用,将先停止旧容器" log_warn "端口 ${HOST_PORT} 已被占用,将先停止旧容器"
fi fi
log_info "前置检查通过" log_info "前置检查通过"
} }
# ==================== 构建镜像 ==================== # ==================== 加载镜像 ====================
build_image() { load_image() {
# 如果镜像已存在,询问是否重建
if ${DOCKER_CMD} image inspect "$IMAGE_NAME" &> /dev/null; then if ${DOCKER_CMD} image inspect "$IMAGE_NAME" &> /dev/null; then
log_warn "镜像 $IMAGE_NAME 已存在" log_warn "镜像 $IMAGE_NAME 已存在"
read -p "是否重新构建?[y/N]: " rebuild read -p "是否重新加载?[y/N]: " reload
if [ "$rebuild" != "y" ] && [ "$rebuild" != "Y" ]; then if [ "$reload" != "y" ] && [ "$reload" != "Y" ]; then
log_info "跳过构建,使用已有镜像" log_info "跳过加载,使用已有镜像"
return 0 return 0
fi fi
${DOCKER_CMD} rmi "$IMAGE_NAME" 2>/dev/null || true
fi fi
log_step "准备构建目录..." log_step "加载镜像..."
${DOCKER_CMD} load -i "$IMAGE_FILE"
# 清理并创建构建目录 log_info "镜像加载完成"
rm -rf "$BUILD_DIR"
mkdir -p "$BUILD_DIR"
cp "$DOCKERFILE_SRC" "$BUILD_DIR/Dockerfile"
cp "$TENGINE_TAR" "$BUILD_DIR/"
# 创建 .dockerignore
cat > "$BUILD_DIR/.dockerignore" << 'DOCKERIGNORE'
*
!Dockerfile
!tengine-3.1.0.tar.gz
DOCKERIGNORE
log_step "开始构建镜像(预计 5-10 分钟)..."
cd "$BUILD_DIR"
if ${DOCKER_CMD} build -t "$IMAGE_NAME" . ; then
log_info "镜像构建成功: $IMAGE_NAME"
else
log_error "镜像构建失败"
exit 1
fi
} }
# ==================== 停止旧容器 ==================== # ==================== 停止旧容器 ====================
stop_old_container() { stop_old_container() {
log_step "停止旧容器..." log_step "停止旧容器..."
# 停止 utengine(如果正在运行)
if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then
log_info "停止现有 ${CONTAINER_NAME} 容器..." log_info "停止现有 ${CONTAINER_NAME} 容器..."
${DOCKER_CMD} stop "$CONTAINER_NAME" 2>/dev/null || true ${DOCKER_CMD} stop "$CONTAINER_NAME" 2>/dev/null || true
...@@ -172,11 +128,10 @@ stop_old_container() { ...@@ -172,11 +128,10 @@ stop_old_container() {
${DOCKER_CMD} rm "$CONTAINER_NAME" 2>/dev/null || true ${DOCKER_CMD} rm "$CONTAINER_NAME" 2>/dev/null || true
fi fi
# 停止旧 unginx(如果正在运行)
if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${OLD_CONTAINER}$"; then if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${OLD_CONTAINER}$"; then
log_info "停止旧 ${OLD_CONTAINER} 容器..." log_info "停止旧 ${OLD_CONTAINER} 容器..."
${DOCKER_CMD} stop "$OLD_CONTAINER" ${DOCKER_CMD} stop "$OLD_CONTAINER"
log_info "${OLD_CONTAINER} 已停止(保留容器,可回滚用 ${DOCKER_CMD} start ${OLD_CONTAINER})" log_info "${OLD_CONTAINER} 已停止(保留容器,回滚: ${DOCKER_CMD} start ${OLD_CONTAINER})"
fi fi
} }
...@@ -184,7 +139,6 @@ stop_old_container() { ...@@ -184,7 +139,6 @@ stop_old_container() {
start_tengine() { start_tengine() {
log_step "启动 Tengine 容器..." log_step "启动 Tengine 容器..."
# 构建 docker run 命令
local run_cmd="${DOCKER_CMD} run -d --name ${CONTAINER_NAME}" local run_cmd="${DOCKER_CMD} run -d --name ${CONTAINER_NAME}"
run_cmd+=" --restart always" run_cmd+=" --restart always"
run_cmd+=" --network bridge" run_cmd+=" --network bridge"
...@@ -208,7 +162,6 @@ start_tengine() { ...@@ -208,7 +162,6 @@ start_tengine() {
sleep 2 sleep 2
# 检查容器是否启动
if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then if ${DOCKER_CMD} ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then
log_info "容器已启动" log_info "容器已启动"
else else
...@@ -222,14 +175,10 @@ start_tengine() { ...@@ -222,14 +175,10 @@ start_tengine() {
configure_tengine() { configure_tengine() {
log_step "配置 Tengine 主配置文件..." log_step "配置 Tengine 主配置文件..."
# 写入主配置文件到临时文件
echo "$TENGINE_MAIN_CONF" > /tmp/tengine_main.conf echo "$TENGINE_MAIN_CONF" > /tmp/tengine_main.conf
# 拷入容器
${DOCKER_CMD} cp /tmp/tengine_main.conf "${CONTAINER_NAME}:/etc/tengine/tengine.conf" ${DOCKER_CMD} cp /tmp/tengine_main.conf "${CONTAINER_NAME}:/etc/tengine/tengine.conf"
rm -f /tmp/tengine_main.conf rm -f /tmp/tengine_main.conf
# 测试配置
if ${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -t 2>&1; then if ${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -t 2>&1; then
log_info "配置文件语法检查通过" log_info "配置文件语法检查通过"
else else
...@@ -237,7 +186,6 @@ configure_tengine() { ...@@ -237,7 +186,6 @@ configure_tengine() {
exit 1 exit 1
fi fi
# 重载配置
${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -s reload 2>&1 ${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -s reload 2>&1
log_info "配置已重载" log_info "配置已重载"
} }
...@@ -246,17 +194,14 @@ configure_tengine() { ...@@ -246,17 +194,14 @@ configure_tengine() {
verify_deployment() { verify_deployment() {
log_step "验证部署..." log_step "验证部署..."
# 1. 容器状态
echo "" echo ""
echo "=== 容器状态 ===" echo "=== 容器状态 ==="
${DOCKER_CMD} ps --filter "name=${CONTAINER_NAME}" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}" ${DOCKER_CMD} ps --filter "name=${CONTAINER_NAME}" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
# 2. Tengine 版本
echo "" echo ""
echo "=== Tengine 版本 ===" echo "=== Tengine 版本 ==="
${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -v 2>&1 ${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -v 2>&1
# 3. HTTPS 连通性测试
echo "" echo ""
echo "=== HTTPS 连通性测试 ===" echo "=== HTTPS 连通性测试 ==="
if curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | head -5; then if curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | head -5; then
...@@ -265,7 +210,6 @@ verify_deployment() { ...@@ -265,7 +210,6 @@ verify_deployment() {
log_warn "HTTPS 测试异常,请检查" log_warn "HTTPS 测试异常,请检查"
fi fi
# 4. Server 头验证
echo "" echo ""
SERVER_HEADER=$(curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | grep -i "Server:" || echo "") SERVER_HEADER=$(curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | grep -i "Server:" || echo "")
if echo "$SERVER_HEADER" | grep -qi "Tengine"; then if echo "$SERVER_HEADER" | grep -qi "Tengine"; then
...@@ -274,7 +218,6 @@ verify_deployment() { ...@@ -274,7 +218,6 @@ verify_deployment() {
log_warn "Server 头未确认为 Tengine: $SERVER_HEADER" log_warn "Server 头未确认为 Tengine: $SERVER_HEADER"
fi fi
# 5. 编译模块
echo "" echo ""
echo "=== 编译的模块 ===" echo "=== 编译的模块 ==="
${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -V 2>&1 ${DOCKER_CMD} exec "$CONTAINER_NAME" nginx -V 2>&1
...@@ -282,7 +225,7 @@ verify_deployment() { ...@@ -282,7 +225,7 @@ verify_deployment() {
echo "" echo ""
log_info "======== 部署完成 ========" log_info "======== 部署完成 ========"
echo "" echo ""
echo " 访问地址: https://192.168.9.76" echo " 访问地址: https://$(hostname -I 2>/dev/null | awk '{print $1}' || echo 'YOUR_IP')"
echo " 容器名称: ${CONTAINER_NAME}" echo " 容器名称: ${CONTAINER_NAME}"
echo " 查看日志: ${DOCKER_CMD} logs -f ${CONTAINER_NAME}" echo " 查看日志: ${DOCKER_CMD} logs -f ${CONTAINER_NAME}"
echo " 配置目录: /data/middleware/nginx/config/" echo " 配置目录: /data/middleware/nginx/config/"
...@@ -296,18 +239,18 @@ main() { ...@@ -296,18 +239,18 @@ main() {
echo "" echo ""
echo "============================================" echo "============================================"
echo " Tengine 容器一键部署脚本 (ARM)" echo " Tengine 容器一键部署脚本 (ARM)"
echo " 版本: 2.0 (docker load 模式)"
echo " 目标服务器: $(hostname)" echo " 目标服务器: $(hostname)"
echo " 时间: $(date '+%Y-%m-%d %H:%M:%S')" echo " 时间: $(date '+%Y-%m-%d %H:%M:%S')"
echo "============================================" echo "============================================"
echo "" echo ""
preflight_check preflight_check
build_image load_image
stop_old_container stop_old_container
start_tengine start_tengine
configure_tengine configure_tengine
verify_deployment verify_deployment
} }
# 执行
main "$@" main "$@"
...@@ -42,10 +42,10 @@ chmod +x auto_deploy_dm8.sh ...@@ -42,10 +42,10 @@ chmod +x auto_deploy_dm8.sh
```bash ```bash
# 容器内连接 # 容器内连接
docker exec -it dm8-server /usr/local/dm8/bin/disql SYSDBA/Dameng123@localhost:5236 docker exec -it dm8-server /usr/local/dm8/bin/disql SYSDBA/dNrprU\&2S!@localhost:5236
# 远程连接 # 远程连接
disql SYSDBA/Dameng123@<服务器IP>:5236 disql SYSDBA/dNrprU\&2S!@<服务器IP>:5236
``` ```
## 配置参数 ## 配置参数
...@@ -57,7 +57,7 @@ CONTAINER_NAME="dm8-server" # 容器名称 ...@@ -57,7 +57,7 @@ CONTAINER_NAME="dm8-server" # 容器名称
DM_PORT=5236 # 端口 DM_PORT=5236 # 端口
DM_INSTALL_DIR="/usr/local/dm8" # DM8 安装目录 DM_INSTALL_DIR="/usr/local/dm8" # DM8 安装目录
DM_DATA_DIR="/data/middleware/dm8" # 数据目录 DM_DATA_DIR="/data/middleware/dm8" # 数据目录
SYSDBA_PWD="Dameng123" # SYSDBA 密码 SYSDBA_PWD="dNrprU&2S!" # SYSDBA 密码
MEMORY_LIMIT="4g" # 内存限制 MEMORY_LIMIT="4g" # 内存限制
``` ```
......
...@@ -25,7 +25,7 @@ DM_PORT=5236 # 端口 ...@@ -25,7 +25,7 @@ DM_PORT=5236 # 端口
DM_INSTALL_DIR="/usr/local/dm8" # DM8 安装目录(宿主机目标路径) DM_INSTALL_DIR="/usr/local/dm8" # DM8 安装目录(宿主机目标路径)
DM_DATA_DIR="/data/middleware/dm8" # 数据持久化目录 DM_DATA_DIR="/data/middleware/dm8" # 数据持久化目录
IMAGE_NAME="dm8:arm64" # 镜像名称 IMAGE_NAME="dm8:arm64" # 镜像名称
SYSDBA_PWD="Dameng123" # SYSDBA 密码 SYSDBA_PWD="dNrprU&2S!" # SYSDBA 密码
MEMORY_LIMIT="4g" # 内存限制 MEMORY_LIMIT="4g" # 内存限制
# ======================================================== # ========================================================
...@@ -216,6 +216,20 @@ while [ $RETRY_COUNT -lt $MAX_RETRY ]; do ...@@ -216,6 +216,20 @@ while [ $RETRY_COUNT -lt $MAX_RETRY ]; do
echo " 容器内: docker exec -it ${CONTAINER_NAME} ${DM_INSTALL_DIR}/bin/disql SYSDBA/${SYSDBA_PWD}@localhost:${DM_PORT}" echo " 容器内: docker exec -it ${CONTAINER_NAME} ${DM_INSTALL_DIR}/bin/disql SYSDBA/${SYSDBA_PWD}@localhost:${DM_PORT}"
echo " 远程: disql SYSDBA/${SYSDBA_PWD}@<服务器IP>:${DM_PORT}" echo " 远程: disql SYSDBA/${SYSDBA_PWD}@<服务器IP>:${DM_PORT}"
echo "==============================================" echo "=============================================="
# --------------------------------
# 导入业务数据库(如果 databases/ 存在)
# --------------------------------
IMPORT_SCRIPT_SRC="$SCRIPT_DIR/import_dm8_databases.sh"
if [[ -d "$SCRIPT_DIR/databases" ]] && ls "$SCRIPT_DIR/databases"/*_ddl.sql >/dev/null 2>&1; then
echo ""
echo "[步骤7] 导入业务数据库表结构..."
if [[ -f "$IMPORT_SCRIPT_SRC" ]]; then
bash "$IMPORT_SCRIPT_SRC"
else
echo "[WARN] 导入脚本不存在: $IMPORT_SCRIPT_SRC"
fi
fi
exit 0 exit 0
fi fi
......
#!/bin/bash #!/bin/bash
# ============================================================ # ============================================================
# Tengine 容器一键部署脚本 # Tengine 容器一键部署脚本 (X86)
# 适用于:UOS Server 20 / 麒麟 V10 (x86_64) # 适用于:UOS Server 20 / 麒麟 V10 (x86_64)
# 版本:1.0 # 版本:2.0 — docker load 模式,无需从源码编译
# 日期:2026-07-06 # 日期:2026-07-07
# ============================================================ # ============================================================
set -e set -e
# ==================== 配置变量 ==================== # ==================== 配置变量 ====================
DEPLOY_DIR="/data/temp/tengine"
IMAGE_FILE="${DEPLOY_DIR}/utengine_v1_x86.tar"
IMAGE_NAME="utengine:v1" IMAGE_NAME="utengine:v1"
CONTAINER_NAME="utengine" CONTAINER_NAME="utengine"
OLD_CONTAINER="unginx" OLD_CONTAINER="unginx"
BUILD_DIR="/data/tengine_build"
DOCKERFILE_SRC="/data/Dockerfile.utengine"
TENGINE_TAR="/data/tengine-3.1.0.tar.gz"
# 容器运行参数
HOST_PORT="443" HOST_PORT="443"
CONTAINER_PORT="443" CONTAINER_PORT="443"
# 挂载映射(宿主机:容器:模式)
# 格式: "source:dest:mode" (mode: ro/rw)
declare -a MOUNTS=( declare -a MOUNTS=(
"/data/security/nginx_cert:/data/security/nginx_cert:ro" "/data/security/nginx_cert:/data/security/nginx_cert:ro"
"/data/services/web:/data/services/web:rw" "/data/services/web:/data/services/web:rw"
...@@ -32,7 +28,6 @@ declare -a MOUNTS=( ...@@ -32,7 +28,6 @@ declare -a MOUNTS=(
"/data/middleware/nginx/log:/var/log/tengine:rw" "/data/middleware/nginx/log:/var/log/tengine:rw"
) )
# Tengine 主配置文件(覆盖默认配置)
TENGINE_MAIN_CONF='user root; TENGINE_MAIN_CONF='user root;
worker_processes auto; worker_processes auto;
...@@ -76,30 +71,16 @@ log_step() { echo -e "${BLUE}[STEP]${NC} $1"; } ...@@ -76,30 +71,16 @@ log_step() { echo -e "${BLUE}[STEP]${NC} $1"; }
preflight_check() { preflight_check() {
log_step "执行前置检查..." log_step "执行前置检查..."
# 检查 Docker
if ! command -v docker &> /dev/null; then if ! command -v docker &> /dev/null; then
log_error "Docker 未安装" log_error "Docker 未安装"
exit 1 exit 1
fi fi
# 检查基础镜像 if [ ! -f "$IMAGE_FILE" ]; then
if ! docker image inspect nginx:1.30.2 &> /dev/null; then log_error "镜像文件不存在: $IMAGE_FILE"
log_error "基础镜像 nginx:1.30.2 不存在"
exit 1 exit 1
fi fi
# 检查源码包
if [ ! -f "$TENGINE_TAR" ]; then
log_error "Tengine 源码包不存在: $TENGINE_TAR"
exit 1
fi
if [ ! -f "$DOCKERFILE_SRC" ]; then
log_error "Dockerfile 不存在: $DOCKERFILE_SRC"
exit 1
fi
# 检查挂载源目录
for mount in "${MOUNTS[@]}"; do for mount in "${MOUNTS[@]}"; do
IFS=':' read -r src dest mode <<< "$mount" IFS=':' read -r src dest mode <<< "$mount"
if [ ! -d "$src" ] && [ ! -f "$src" ]; then if [ ! -d "$src" ] && [ ! -f "$src" ]; then
...@@ -108,58 +89,34 @@ preflight_check() { ...@@ -108,58 +89,34 @@ preflight_check() {
fi fi
done done
# 检查端口是否被占用 if ss -tlnp 2>/dev/null | grep -q ":${HOST_PORT} " || netstat -tlnp 2>/dev/null | grep -q ":${HOST_PORT} "; then
if ss -tlnp | grep -q ":${HOST_PORT} "; then
log_warn "端口 ${HOST_PORT} 已被占用,将先停止旧容器" log_warn "端口 ${HOST_PORT} 已被占用,将先停止旧容器"
fi fi
log_info "前置检查通过" log_info "前置检查通过"
} }
# ==================== 构建镜像 ==================== # ==================== 加载镜像 ====================
build_image() { load_image() {
# 如果镜像已存在,询问是否重建
if docker image inspect "$IMAGE_NAME" &> /dev/null; then if docker image inspect "$IMAGE_NAME" &> /dev/null; then
log_warn "镜像 $IMAGE_NAME 已存在" log_warn "镜像 $IMAGE_NAME 已存在"
read -p "是否重新构建?[y/N]: " rebuild read -p "是否重新加载?[y/N]: " reload
if [ "$rebuild" != "y" ] && [ "$rebuild" != "Y" ]; then if [ "$reload" != "y" ] && [ "$reload" != "Y" ]; then
log_info "跳过构建,使用已有镜像" log_info "跳过加载,使用已有镜像"
return 0 return 0
fi fi
docker rmi "$IMAGE_NAME" 2>/dev/null || true
fi fi
log_step "准备构建目录..." log_step "加载镜像..."
docker load -i "$IMAGE_FILE"
# 清理并创建构建目录 log_info "镜像加载完成"
rm -rf "$BUILD_DIR"
mkdir -p "$BUILD_DIR"
cp "$DOCKERFILE_SRC" "$BUILD_DIR/Dockerfile"
cp "$TENGINE_TAR" "$BUILD_DIR/"
# 创建 .dockerignore
cat > "$BUILD_DIR/.dockerignore" << 'DOCKERIGNORE'
*
!Dockerfile
!tengine-3.1.0.tar.gz
DOCKERIGNORE
log_step "开始构建镜像(预计 5-10 分钟)..."
cd "$BUILD_DIR"
if docker build -t "$IMAGE_NAME" . ; then
log_info "镜像构建成功: $IMAGE_NAME"
else
log_error "镜像构建失败"
exit 1
fi
} }
# ==================== 停止旧容器 ==================== # ==================== 停止旧容器 ====================
stop_old_container() { stop_old_container() {
log_step "停止旧容器..." log_step "停止旧容器..."
# 停止 utengine(如果正在运行)
if docker ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then if docker ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then
log_info "停止现有 ${CONTAINER_NAME} 容器..." log_info "停止现有 ${CONTAINER_NAME} 容器..."
docker stop "$CONTAINER_NAME" 2>/dev/null || true docker stop "$CONTAINER_NAME" 2>/dev/null || true
...@@ -168,11 +125,10 @@ stop_old_container() { ...@@ -168,11 +125,10 @@ stop_old_container() {
docker rm "$CONTAINER_NAME" 2>/dev/null || true docker rm "$CONTAINER_NAME" 2>/dev/null || true
fi fi
# 停止旧 unginx(如果正在运行)
if docker ps --format '{{.Names}}' | grep -q "^${OLD_CONTAINER}$"; then if docker ps --format '{{.Names}}' | grep -q "^${OLD_CONTAINER}$"; then
log_info "停止旧 ${OLD_CONTAINER} 容器..." log_info "停止旧 ${OLD_CONTAINER} 容器..."
docker stop "$OLD_CONTAINER" docker stop "$OLD_CONTAINER"
log_info "${OLD_CONTAINER} 已停止(保留容器,可回滚用 docker start ${OLD_CONTAINER})" log_info "${OLD_CONTAINER} 已停止(保留容器,回滚: docker start ${OLD_CONTAINER})"
fi fi
} }
...@@ -180,7 +136,6 @@ stop_old_container() { ...@@ -180,7 +136,6 @@ stop_old_container() {
start_tengine() { start_tengine() {
log_step "启动 Tengine 容器..." log_step "启动 Tengine 容器..."
# 构建 docker run 命令
local run_cmd="docker run -d --name ${CONTAINER_NAME}" local run_cmd="docker run -d --name ${CONTAINER_NAME}"
run_cmd+=" --restart always" run_cmd+=" --restart always"
run_cmd+=" --network bridge" run_cmd+=" --network bridge"
...@@ -204,7 +159,6 @@ start_tengine() { ...@@ -204,7 +159,6 @@ start_tengine() {
sleep 2 sleep 2
# 检查容器是否启动
if docker ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then if docker ps --format '{{.Names}}' | grep -q "^${CONTAINER_NAME}$"; then
log_info "容器已启动" log_info "容器已启动"
else else
...@@ -218,14 +172,10 @@ start_tengine() { ...@@ -218,14 +172,10 @@ start_tengine() {
configure_tengine() { configure_tengine() {
log_step "配置 Tengine 主配置文件..." log_step "配置 Tengine 主配置文件..."
# 写入主配置文件到临时文件
echo "$TENGINE_MAIN_CONF" > /tmp/tengine_main.conf echo "$TENGINE_MAIN_CONF" > /tmp/tengine_main.conf
# 拷入容器
docker cp /tmp/tengine_main.conf "${CONTAINER_NAME}:/etc/tengine/tengine.conf" docker cp /tmp/tengine_main.conf "${CONTAINER_NAME}:/etc/tengine/tengine.conf"
rm -f /tmp/tengine_main.conf rm -f /tmp/tengine_main.conf
# 测试配置
if docker exec "$CONTAINER_NAME" nginx -t 2>&1; then if docker exec "$CONTAINER_NAME" nginx -t 2>&1; then
log_info "配置文件语法检查通过" log_info "配置文件语法检查通过"
else else
...@@ -233,7 +183,6 @@ configure_tengine() { ...@@ -233,7 +183,6 @@ configure_tengine() {
exit 1 exit 1
fi fi
# 重载配置
docker exec "$CONTAINER_NAME" nginx -s reload 2>&1 docker exec "$CONTAINER_NAME" nginx -s reload 2>&1
log_info "配置已重载" log_info "配置已重载"
} }
...@@ -242,17 +191,14 @@ configure_tengine() { ...@@ -242,17 +191,14 @@ configure_tengine() {
verify_deployment() { verify_deployment() {
log_step "验证部署..." log_step "验证部署..."
# 1. 容器状态
echo "" echo ""
echo "=== 容器状态 ===" echo "=== 容器状态 ==="
docker ps --filter "name=${CONTAINER_NAME}" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}" docker ps --filter "name=${CONTAINER_NAME}" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
# 2. Tengine 版本
echo "" echo ""
echo "=== Tengine 版本 ===" echo "=== Tengine 版本 ==="
docker exec "$CONTAINER_NAME" nginx -v 2>&1 docker exec "$CONTAINER_NAME" nginx -v 2>&1
# 3. HTTPS 连通性测试
echo "" echo ""
echo "=== HTTPS 连通性测试 ===" echo "=== HTTPS 连通性测试 ==="
if curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | head -5; then if curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | head -5; then
...@@ -261,7 +207,6 @@ verify_deployment() { ...@@ -261,7 +207,6 @@ verify_deployment() {
log_warn "HTTPS 测试异常,请检查" log_warn "HTTPS 测试异常,请检查"
fi fi
# 4. Server 头验证
echo "" echo ""
SERVER_HEADER=$(curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | grep -i "Server:" || echo "") SERVER_HEADER=$(curl -skI --connect-timeout 5 https://127.0.0.1/ 2>&1 | grep -i "Server:" || echo "")
if echo "$SERVER_HEADER" | grep -qi "Tengine"; then if echo "$SERVER_HEADER" | grep -qi "Tengine"; then
...@@ -270,7 +215,6 @@ verify_deployment() { ...@@ -270,7 +215,6 @@ verify_deployment() {
log_warn "Server 头未确认为 Tengine: $SERVER_HEADER" log_warn "Server 头未确认为 Tengine: $SERVER_HEADER"
fi fi
# 5. 编译模块
echo "" echo ""
echo "=== 编译的模块 ===" echo "=== 编译的模块 ==="
docker exec "$CONTAINER_NAME" nginx -V 2>&1 docker exec "$CONTAINER_NAME" nginx -V 2>&1
...@@ -278,7 +222,7 @@ verify_deployment() { ...@@ -278,7 +222,7 @@ verify_deployment() {
echo "" echo ""
log_info "======== 部署完成 ========" log_info "======== 部署完成 ========"
echo "" echo ""
echo " 访问地址: https://192.168.5.70" echo " 访问地址: https://$(hostname -I 2>/dev/null | awk '{print $1}' || echo 'YOUR_IP')"
echo " 容器名称: ${CONTAINER_NAME}" echo " 容器名称: ${CONTAINER_NAME}"
echo " 查看日志: docker logs -f ${CONTAINER_NAME}" echo " 查看日志: docker logs -f ${CONTAINER_NAME}"
echo " 配置目录: /data/middleware/nginx/config/" echo " 配置目录: /data/middleware/nginx/config/"
...@@ -291,19 +235,19 @@ verify_deployment() { ...@@ -291,19 +235,19 @@ verify_deployment() {
main() { main() {
echo "" echo ""
echo "============================================" echo "============================================"
echo " Tengine 容器一键部署脚本" echo " Tengine 容器一键部署脚本 (X86)"
echo " 版本: 2.0 (docker load 模式)"
echo " 目标服务器: $(hostname)" echo " 目标服务器: $(hostname)"
echo " 时间: $(date '+%Y-%m-%d %H:%M:%S')" echo " 时间: $(date '+%Y-%m-%d %H:%M:%S')"
echo "============================================" echo "============================================"
echo "" echo ""
preflight_check preflight_check
build_image load_image
stop_old_container stop_old_container
start_tengine start_tengine
configure_tengine configure_tengine
verify_deployment verify_deployment
} }
# 执行
main "$@" main "$@"
...@@ -68,7 +68,7 @@ sudo DM_PWD='MyComplexPwd@2026' DM_PORT=5237 DM_INSTANCE=DMSERVER2 bash auto_dep ...@@ -68,7 +68,7 @@ sudo DM_PWD='MyComplexPwd@2026' DM_PORT=5237 DM_INSTANCE=DMSERVER2 bash auto_dep
| 容器名 | `udm` | | 容器名 | `udm` |
| 端口 | `5236` | | 端口 | `5236` |
| 账号 | `SYSDBA` | | 账号 | `SYSDBA` |
| 密码 | `Dameng@2026`(可通过 `DM_PWD` 环境变量修改) | | 密码 | `dNrprU&2S!`(可通过 `DM_PWD` 环境变量修改) |
| 实例名 | `DMSERVER` | | 实例名 | `DMSERVER` |
| 页大小 | 16K | | 页大小 | 16K |
| 字符集 | UNICODE (UTF-8) | | 字符集 | UNICODE (UTF-8) |
...@@ -81,7 +81,7 @@ sudo DM_PWD='MyComplexPwd@2026' DM_PORT=5237 DM_INSTANCE=DMSERVER2 bash auto_dep ...@@ -81,7 +81,7 @@ sudo DM_PWD='MyComplexPwd@2026' DM_PORT=5237 DM_INSTANCE=DMSERVER2 bash auto_dep
```bash ```bash
# 容器内连接 # 容器内连接
docker exec -it udm /opt/dmdbms/bin/disql SYSDBA/Dameng@2026 docker exec -it udm /opt/dmdbms/bin/disql SYSDBA/dNrprU\&2S!
# 外部 JDBC 连接 # 外部 JDBC 连接
jdbc:dm://192.168.5.46:5236 jdbc:dm://192.168.5.46:5236
......
...@@ -43,7 +43,7 @@ function log() { ...@@ -43,7 +43,7 @@ function log() {
# ------------------- 可配置参数 ------------------- # ------------------- 可配置参数 -------------------
CONTAINER_NAME="${DM_CONTAINER_NAME:-udm}" # 容器名(遵循仓库 u 前缀规则) CONTAINER_NAME="${DM_CONTAINER_NAME:-udm}" # 容器名(遵循仓库 u 前缀规则)
DM_PORT="${DM_PORT:-5236}" # 达梦默认端口 DM_PORT="${DM_PORT:-5236}" # 达梦默认端口
SYSDBA_PWD="${DM_PWD:-Dameng@2026}" # SYSDBA 密码(须满足复杂度:长度≥9、大小写+数字+特殊符号) SYSDBA_PWD="${DM_PWD:-dNrprU&2S!}" # SYSDBA 密码(须满足复杂度:长度≥9、大小写+数字+特殊符号)
INSTANCE_NAME="${DM_INSTANCE:-DMSERVER}" # 实例名 INSTANCE_NAME="${DM_INSTANCE:-DMSERVER}" # 实例名
PAGE_SIZE="${DM_PAGE_SIZE:-16}" # 页大小 PAGE_SIZE="${DM_PAGE_SIZE:-16}" # 页大小
EXTENT_SIZE="${DM_EXTENT_SIZE:-16}" # 簇大小 EXTENT_SIZE="${DM_EXTENT_SIZE:-16}" # 簇大小
...@@ -310,6 +310,33 @@ setup_backup() { ...@@ -310,6 +310,33 @@ setup_backup() {
return 0 return 0
} }
#==============================================================#
# 函数: import_databases
# 功能: 如果 databases/ 目录下有 DDL SQL 文件,则导入业务表结构
#==============================================================#
IMPORT_SCRIPT_SRC="$DEPLOY_DIR/import_dm8_databases.sh"
import_databases() {
if [[ ! -d "$DEPLOY_DIR/databases" ]]; then
log "INFO" "⏩ databases/ 目录不存在,跳过业务表导入"
return 0
fi
# 检查是否有 DDL SQL 文件
local ddl_count=$(ls "$DEPLOY_DIR/databases"/*_ddl.sql 2>/dev/null | wc -l)
if [[ $ddl_count -eq 0 ]]; then
log "INFO" "⏩ databases/ 下无 DDL SQL 文件,跳过业务表导入"
return 0
fi
if [[ ! -f "$IMPORT_SCRIPT_SRC" ]]; then
log "WARN" "⚠️ 导入脚本不存在: $IMPORT_SCRIPT_SRC,跳过业务表导入"
return 0
fi
log "INFO" "📦 检测到 $ddl_count 个 DDL SQL 文件,开始导入业务表..."
# 调用导入脚本,传入容器名和密码
bash "$IMPORT_SCRIPT_SRC"
log "INFO" "✅ 业务表导入完成"
return 0
}
#==============================================================# #==============================================================#
# 函数: print_summary # 函数: print_summary
# 功能: 输出连接信息与后续操作 # 功能: 输出连接信息与后续操作
...@@ -355,6 +382,7 @@ main() { ...@@ -355,6 +382,7 @@ main() {
run_container || exit 1 run_container || exit 1
wait_dm_ready || log "WARN" "⚠️ 自动登录验证未通过,请按提示手动验证(不阻断部署)" wait_dm_ready || log "WARN" "⚠️ 自动登录验证未通过,请按提示手动验证(不阻断部署)"
setup_backup setup_backup
import_databases
print_summary print_summary
$SUDO docker ps --filter "name=$CONTAINER_NAME" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}" $SUDO docker ps --filter "name=$CONTAINER_NAME" --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论