增加docke部署

This commit is contained in:
2026-04-10 16:44:13 +08:00
parent e2f8054794
commit cd4ddb606d
5076 changed files with 701092 additions and 0 deletions

View File

@@ -0,0 +1,41 @@
FROM php:8.1-apache
# 安装 PHP 扩展
RUN apt-get update && apt-get install -y \
libzip-dev \
libpng-dev \
libcurl4-openssl-dev \
&& docker-php-ext-install pdo pdo_mysql mysqli zip gd curl \
&& apt-get clean && rm -rf /var/lib/apt/lists/*
# 启用 Apache mod_rewrite
RUN a2enmod rewrite
# 设置 Apache DocumentRoot
ENV APACHE_DOCUMENT_ROOT /var/www/html
RUN sed -i 's|/var/www/html|${APACHE_DOCUMENT_ROOT}|g' \
/etc/apache2/sites-available/000-default.conf \
/etc/apache2/apache2.conf
# 允许 .htaccess 覆盖
RUN sed -i '/<Directory \/var\/www\/>/,/<\/Directory>/ s/AllowOverride None/AllowOverride All/' /etc/apache2/apache2.conf
# 设置时区
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
# 拷贝应用代码
COPY api/ /var/www/html/
COPY env_config.php /var/www/env_config.php
# .env 由 docker-compose env_file 注入,不打包进镜像
# 设置权限
RUN chown -R www-data:www-data /var/www/html
# 拷贝并设置启动入口脚本(用于替换 JS 中的硬编码域名)
COPY docker/api/docker-entrypoint.sh /usr/local/bin/docker-entrypoint.sh
RUN chmod +x /usr/local/bin/docker-entrypoint.sh
EXPOSE 80
ENTRYPOINT ["docker-entrypoint.sh"]

View File

@@ -0,0 +1,69 @@
#!/bin/bash
set -e
# ============================================
# API 服务启动入口脚本
# 在 Apache 启动前替换静态 JS 文件中的硬编码域名
# ============================================
echo "[entrypoint] Replacing hardcoded domains in JS files..."
# 默认值(与 .env.example 对应)
SITE_API2_URL="${SITE_API2_URL:-https://api2.tscce.cn}"
QQ_CALLBACK_URL="${QQ_CALLBACK_URL:-http://syhd.daoqijuyou77.cn}"
# 替换 api/source/pay/js/common.js 和 api/source/login/js/common.js 中的 g_RequestAddress
for f in /var/www/html/source/pay/js/common.js /var/www/html/source/login/js/common.js; do
if [ -f "$f" ]; then
sed -i "s|var g_RequestAddress = 'https://api2.tscce.cn'|var g_RequestAddress = '${SITE_API2_URL}'|g" "$f"
echo "[entrypoint] Updated: $f"
fi
done
# 替换 QQ 登录配置中的回调地址
QQ_INC="/var/www/html/loginLib/qq/API/comm/inc.php"
if [ -f "$QQ_INC" ]; then
sed -i "s|__QQ_CALLBACK_URL__|${QQ_CALLBACK_URL}|g" "$QQ_INC"
echo "[entrypoint] Updated: $QQ_INC"
fi
# 替换 sample 目录中的硬编码域名
SITE_API_URL="${SITE_API_URL:-https://api.tscce.cn}"
SITE_PAY_NOTIFY_URL="${SITE_PAY_NOTIFY_URL:-http://api.daoqijuyou77.cn}"
for f in /var/www/html/sample/onlinepay/js/common.js; do
if [ -f "$f" ]; then
sed -i "s|var g_RequestAddress = 'https://api.tscce.cn'|var g_RequestAddress = '${SITE_API_URL}'|g" "$f"
echo "[entrypoint] Updated: $f"
fi
done
for f in /var/www/html/sample/offlinepay/js/common.js; do
if [ -f "$f" ]; then
sed -i "s|var g_RequestAddress = 'https://api.daoqijuyou77.cn'|var g_RequestAddress = '${SITE_API_URL}'|g" "$f"
echo "[entrypoint] Updated: $f"
fi
done
for f in /var/www/html/sample/transfer/js/common.js /var/www/html/sample/refund/js/common.js; do
if [ -f "$f" ]; then
sed -i "s|var g_RequestAddress = 'https://api2.tscce.cn'|var g_RequestAddress = '${SITE_API2_URL}'|g" "$f"
sed -i "s|var g_RequestAddress = 'https://api2.daoqijuyou77.cn'|var g_RequestAddress = '${SITE_API2_URL}'|g" "$f"
echo "[entrypoint] Updated: $f"
fi
done
# 替换 sample PHP 文件中的硬编码域名
SAMPLE_DIR="/var/www/html/sample"
if [ -d "$SAMPLE_DIR" ]; then
# onlinepay/test.php 和 onlinepay/index.php
find "$SAMPLE_DIR" -name "*.php" -exec sed -i \
-e "s|https://api.tscce.cn|${SITE_API_URL}|g" \
-e "s|https://api2.tscce.cn|${SITE_API2_URL}|g" \
-e "s|https://api2.daoqijuyou77.cn|${SITE_API2_URL}|g" \
-e "s|https://api.daoqijuyou77.cn|${SITE_API_URL}|g" \
{} +
echo "[entrypoint] Updated: sample/ PHP files"
fi
echo "[entrypoint] Domain replacement complete. Starting Apache..."
# 启动 Apache前台运行
exec apache2-foreground

View File

@@ -0,0 +1,4 @@
#!/bin/bash
# certbot 续签后自动重新加载 Nginx 的 hook
# 此脚本由 certbot 在成功续签后自动调用
docker exec youle-nginx nginx -s reload

View File

@@ -0,0 +1,54 @@
#!/bin/sh
# 每日定时任务(替代 Windows autorun.cmd
# 凌晨 4:00 执行,通过 Docker 内网直连 dlweb 容器
#
# 原 autorun.cmd 流程:
# 1. net stop HttpRequestService (停止 Synchronize.php 轮询)
# 2. POST SynchronizeReportData.php同步报表数据
# 3. net start HttpRequestService (恢复 Synchronize.php 轮询)
#
# Docker 等价实现:通过共享文件 /shared/syncjob.pause 暂停/恢复 syncjob
DLWEB_URL="${DLWEB_INTERNAL_URL:-http://dlweb}"
PAUSE_FILE="/shared/syncjob.pause"
TIMESTAMP=$(date '+%Y-%m-%d %H:%M:%S')
echo "========================================"
echo "[${TIMESTAMP}] 开始执行每日定时任务"
echo "========================================"
# --------------------------------------------------------
# 1. 停止同步服务(等价于 net stop HttpRequestService
# 创建暂停信号文件syncjob 检测到后会跳过轮询
# --------------------------------------------------------
echo "[$(date '+%H:%M:%S')] 暂停 syncjob 同步服务..."
touch "${PAUSE_FILE}"
# 等待当前可能正在执行的请求完成
sleep 5
# --------------------------------------------------------
# 2. 同步报表数据 (SynchronizeReportData.php)
# 从游戏数据库同步 report_agent_day、report_game_day 到代理后台
# 并生成 ct_report_info 报表
# 与原 autorun.cmd 一致:不设超时、不重试,等待自然执行完毕
# --------------------------------------------------------
echo "[$(date '+%H:%M:%S')] 开始同步报表数据..."
RESULT=$(curl -sf -X POST "${DLWEB_URL}/ext/SynchronizeReportData.php" 2>&1)
EXIT_CODE=$?
if [ $EXIT_CODE -eq 0 ]; then
echo "[$(date '+%H:%M:%S')] 报表同步完成: ${RESULT}"
else
echo "[$(date '+%H:%M:%S')] 报表同步失败(${EXIT_CODE}): ${RESULT}"
fi
# --------------------------------------------------------
# 3. 恢复同步服务(等价于 net start HttpRequestService
# 删除暂停信号文件syncjob 恢复正常轮询
# --------------------------------------------------------
echo "[$(date '+%H:%M:%S')] 恢复 syncjob 同步服务..."
rm -f "${PAUSE_FILE}"
echo "========================================"
echo "[$(date '+%Y-%m-%d %H:%M:%S')] 每日定时任务执行完毕"
echo "========================================"

View File

@@ -0,0 +1,25 @@
#!/bin/sh
# cronjob 容器入口:注入环境变量到 crontab启动 crond
# 安装 curl仅首次后续重启容器时已安装则跳过
command -v curl > /dev/null 2>&1 || apk add --no-cache curl > /dev/null 2>&1
# 确保脚本有执行权限Windows 开发环境挂载的文件可能缺少 +x
chmod +x /app/daily-task.sh 2>/dev/null
# 将当前环境变量导出到文件,供 cron 任务使用cron 不会继承容器环境变量)
# 排除特殊变量,导出所有业务相关配置
env | grep -v -E '^(HOME|PATH|HOSTNAME|SHLVL|PWD|_)=' > /etc/environment 2>/dev/null
# 读取调度表达式,默认凌晨 4:00
CRON_SCHEDULE="${CRON_SCHEDULE:-0 4 * * *}"
# 生成 crontab
echo "${CRON_SCHEDULE} . /etc/environment; /app/daily-task.sh >> /proc/1/fd/1 2>&1" > /etc/crontabs/root
echo "[cronjob] schedule: ${CRON_SCHEDULE}"
echo "[cronjob] target: ${DLWEB_INTERNAL_URL:-http://dlweb}"
echo "[cronjob] starting crond..."
# 前台运行 crond
crond -f -l 2

View File

@@ -0,0 +1,43 @@
FROM php:8.1-apache
# 安装 PHP 扩展(包含 Redis
RUN apt-get update && apt-get install -y \
libzip-dev \
libpng-dev \
libcurl4-openssl-dev \
&& docker-php-ext-install pdo pdo_mysql mysqli zip gd curl \
&& pecl install redis \
&& docker-php-ext-enable redis \
&& apt-get clean && rm -rf /var/lib/apt/lists/*
# 启用 Apache mod_rewrite
RUN a2enmod rewrite
# 设置 Apache DocumentRoot 到 dlweb/api
ENV APACHE_DOCUMENT_ROOT /var/www/html/api
RUN sed -i 's|/var/www/html|${APACHE_DOCUMENT_ROOT}|g' \
/etc/apache2/sites-available/000-default.conf \
/etc/apache2/apache2.conf
# 允许 .htaccess 覆盖
RUN sed -i '/<Directory \/var\/www\/>/,/<\/Directory>/ s/AllowOverride None/AllowOverride All/' /etc/apache2/apache2.conf
# 设置时区
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
# 拷贝应用代码
COPY dlweb/ /var/www/html/
COPY env_config.php /var/www/env_config.php
# .env 由 docker-compose env_file 注入,不打包进镜像
# 设置权限
RUN chown -R www-data:www-data /var/www/html
# 拷贝并设置启动入口脚本(用于替换 JS/HTML 中的硬编码域名)
COPY docker/dlweb/docker-entrypoint.sh /usr/local/bin/docker-entrypoint.sh
RUN chmod +x /usr/local/bin/docker-entrypoint.sh
EXPOSE 80
ENTRYPOINT ["docker-entrypoint.sh"]

View File

@@ -0,0 +1,121 @@
#!/bin/bash
set -e
# ============================================
# DLWEB 服务启动入口脚本
# 在 Apache 启动前替换静态 JS/HTML 文件中的硬编码域名
# ============================================
echo "[entrypoint] Replacing hardcoded domains in JS/HTML files..."
# 从环境变量读取,提供默认值
# DLWEB_API_BASE_URL 和 DLWEB_SDK_API_URL 从 API_DOMAIN / DLWEB_DOMAIN 自动推导
DLWEB_API_BASE_URL="https://${API_DOMAIN:-api.daoqijuyou77.cn}"
DLWEB_SETTLE_URL="${DLWEB_SETTLE_URL:-http://dlsettle.daoqijuyou77.cn/mobile/}"
DLWEB_AVATAR_URL="${DLWEB_AVATAR_URL:-https://dlwebv3.tscce.cn/images/noavatar.png}"
DLWEB_SDK_API_URL="https://${DLWEB_DOMAIN:-dlapi.daoqijuyou77.cn}"
DLWEB_SDK_API2_URL="${DLWEB_SDK_API2_URL:-https://api2.tscce.cn}"
DLWEB_PROXY_URL="${DLWEB_PROXY_URL:-https://proxytest.tscce.cn}"
DLWEB_DL_API_V3_URL="${DLWEB_DL_API_V3_URL:-https://dlapiv3.tscce.cn}"
DLWEB_WEB_DOMAIN="${DLWEB_WEB_DOMAIN:-https://dlwebv3.tscce.cn}"
DLWEB_SETTLE_FULL_URL="${DLWEB_SETTLE_FULL_URL:-http://dlsettle.tscce.cn}"
DLWEB_OPERATE_URL="${DLWEB_OPERATE_URL:-https://operate.daoqijuyou77.cn}"
DLWEB_PROXY_77_URL="${DLWEB_PROXY_77_URL:-https://proxytest.daoqijuyou77.cn}"
SITE_GAME_SERVICE_URL="${SITE_GAME_SERVICE_URL:-http://ylyxservice1.daoqijuyou77.cn:1089/index.html}"
DLWEB_DOWNLOAD_CDN_URL="${DLWEB_DOWNLOAD_CDN_URL:-http://tsqiniu1.tscce.cn}"
DLWEB_GAME_IMAGE_URL="${DLWEB_GAME_IMAGE_URL:-http://tsgames.daoqijuyou77.cn}"
DLWEB_SKYGAMES_URL="${DLWEB_SKYGAMES_URL:-https://skygames.tscce.cn}"
JS_DIR="/var/www/html/api/web2/js"
COMP_DIR="/var/www/html/api/web2/components"
HTML_DIR="/var/www/html/api/web2"
# ---- function.js ----
FUNC_JS="$JS_DIR/function.js"
if [ -f "$FUNC_JS" ]; then
# API URL 和 回调地址
sed -i "s|'https://dlapi.daoqijuyou77.cn/Index.php'|'${DLWEB_API_BASE_URL}/Index.php'|g" "$FUNC_JS"
sed -i "s|'https://dlapi.daoqijuyou77.cn/web2/notify.html'|'${DLWEB_API_BASE_URL}/web2/notify.html'|g" "$FUNC_JS"
# 结算地址
sed -i "s|'http://dlsettle.daoqijuyou77.cn/mobile/'|'${DLWEB_SETTLE_URL}'|g" "$FUNC_JS"
sed -i "s|'http://dlsettle.tscce.cn/mobile/'|'${DLWEB_SETTLE_URL}'|g" "$FUNC_JS"
sed -i "s|'https://proxytest.tscce.cn/settle/mobile/'|'${DLWEB_PROXY_URL}/settle/mobile/'|g" "$FUNC_JS"
# 头像,SDK API 地址
sed -i "s|https://dlwebv3.tscce.cn/images/noavatar.png|${DLWEB_AVATAR_URL}|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/source/login/login.php|${DLWEB_SDK_API_URL}/source/login/login.php|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/api/user|${DLWEB_SDK_API_URL}/api/user|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/source/pay/pay.php|${DLWEB_SDK_API_URL}/source/pay/pay.php|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/source/pay/notify.php|${DLWEB_SDK_API_URL}/source/pay/notify.php|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/api/weixin/wx_share_info|${DLWEB_SDK_API_URL}/api/weixin/wx_share_info|g" "$FUNC_JS"
sed -i "s|https://api.daoqijuyou77.cn/api/login/ylnn|${DLWEB_SDK_API_URL}/api/login/ylnn|g" "$FUNC_JS"
echo "[entrypoint] Updated: $FUNC_JS"
fi
# ---- function-a.js ----
FUNC_A_JS="$JS_DIR/function-a.js"
if [ -f "$FUNC_A_JS" ]; then
sed -i "s|'https://dlapi.daoqijuyou77.cn/Index.php'|'${DLWEB_API_BASE_URL}/Index.php'|g" "$FUNC_A_JS"
sed -i "s|'https://dlapi.daoqijuyou77.cn/web2/notify.html'|'${DLWEB_API_BASE_URL}/web2/notify.html'|g" "$FUNC_A_JS"
sed -i "s|https://dlwebv3.tscce.cn/images/noavatar.png|${DLWEB_AVATAR_URL}|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/source/login/login.php|${DLWEB_SDK_API2_URL}/source/login/login.php|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/api/user|${DLWEB_SDK_API2_URL}/api/user|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/source/pay/pay_1.php|${DLWEB_SDK_API2_URL}/source/pay/pay_1.php|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/source/pay/notify.php|${DLWEB_SDK_API2_URL}/source/pay/notify.php|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/api/weixin/wx_share_info|${DLWEB_SDK_API2_URL}/api/weixin/wx_share_info|g" "$FUNC_A_JS"
sed -i "s|https://api2.tscce.cn/api/login/ylnn|${DLWEB_SDK_API2_URL}/api/login/ylnn|g" "$FUNC_A_JS"
echo "[entrypoint] Updated: $FUNC_A_JS"
fi
# ---- tangjian.js ----
TJ_JS="$JS_DIR/tangjian.js"
if [ -f "$TJ_JS" ]; then
sed -i "s|'https://proxytest.tscce.cn/api/Index.php'|'${DLWEB_PROXY_URL}/api/Index.php'|g" "$TJ_JS"
sed -i "s|'https://dlapiv3.tscce.cn/Index.php'|'${DLWEB_DL_API_V3_URL}/Index.php'|g" "$TJ_JS"
echo "[entrypoint] Updated: $TJ_JS"
fi
# ---- public_method.js ----
PM_JS="$JS_DIR/public_method.js"
if [ -f "$PM_JS" ]; then
sed -i "s|http://ylyxservice1.daoqijuyou77.cn:1089/index.html|${SITE_GAME_SERVICE_URL}|g" "$PM_JS"
echo "[entrypoint] Updated: $PM_JS"
fi
# ---- common_mixin.js ----
CM_JS="$COMP_DIR/common_mixin.js"
if [ -f "$CM_JS" ]; then
sed -i "s|https://dlwebv3.tscce.cn/images/noavatar.png|${DLWEB_AVATAR_URL}|g" "$CM_JS"
echo "[entrypoint] Updated: $CM_JS"
fi
# ---- HTML 文件 ----
# links.html
LINKS_HTML="$HTML_DIR/links.html"
if [ -f "$LINKS_HTML" ]; then
sed -i "s|https://dlapi.daoqijuyou77.cn|${DLWEB_API_BASE_URL}|g" "$LINKS_HTML"
sed -i "s|https://operate.daoqijuyou77.cn|${DLWEB_OPERATE_URL}|g" "$LINKS_HTML"
sed -i "s|https://proxytest.daoqijuyou77.cn|${DLWEB_PROXY_77_URL}|g" "$LINKS_HTML"
echo "[entrypoint] Updated: $LINKS_HTML"
fi
# download.html
DOWNLOAD_HTML="$HTML_DIR/download.html"
if [ -f "$DOWNLOAD_HTML" ]; then
sed -i "s|http://tsgames.daoqijuyou77.cn|${DLWEB_GAME_IMAGE_URL}|g" "$DOWNLOAD_HTML"
sed -i "s|http://tsqiniu1.tscce.cn|${DLWEB_DOWNLOAD_CDN_URL}|g" "$DOWNLOAD_HTML"
sed -i "s|https://skygames.tscce.cn|${DLWEB_SKYGAMES_URL}|g" "$DOWNLOAD_HTML"
echo "[entrypoint] Updated: $DOWNLOAD_HTML"
fi
# agent_list_admin.html
ADMIN_HTML="$HTML_DIR/agent_list_admin.html"
if [ -f "$ADMIN_HTML" ]; then
sed -i "s|http://proxytest.tscce.cn/settle/managebak|${DLWEB_PROXY_URL}/settle/managebak|g" "$ADMIN_HTML"
sed -i "s|http://dlsettle.tscce.cn/managebak|${DLWEB_SETTLE_FULL_URL}/managebak|g" "$ADMIN_HTML"
echo "[entrypoint] Updated: $ADMIN_HTML"
fi
echo "[entrypoint] Domain replacement complete. Starting Apache..."
# 启动 Apache前台运行
exec apache2-foreground

View File

@@ -0,0 +1,130 @@
upstream api_service {
server api:80;
}
upstream dlweb_service {
server dlweb:80;
}
upstream wxserver_service {
server wxserver:3000;
}
# =============================================
# 域名路由模式 + SSLLet's Encrypt 自动证书)
#
# 域名由 .env 文件中的 API_DOMAIN / DLWEB_DOMAIN / WX_DOMAIN 自动注入
# 修改域名只需编辑 .env 然后 docker compose restart nginx
#
# ================== 微信域名配置指南 ==================
#
# .env 中配置的 3 个域名对应:
# ${API_DOMAIN} → 网站1: game-docker/api
# ${DLWEB_DOMAIN} → 网站2: game-docker/dlweb/api
# ${WX_DOMAIN} → 网站3: game-docker/wxserver_daoqi
#
# 【微信小程序后台】(mp.weixin.qq.com → 开发管理 → 开发设置)
# - request 合法域名: https://${WX_DOMAIN}
# - 业务域名: ${WX_DOMAIN}
# (验证文件放到 wxserver_daoqi/public/MP_verify_xxx.txt)
#
# 【微信公众号后台】(mp.weixin.qq.com → 设置与开发 → 公众号设置)
# - 业务域名: ${API_DOMAIN}
# (验证文件在 api/ 根目录)
# - JS接口安全域名: ${API_DOMAIN}
# - 网页授权域名: ${WX_DOMAIN}
#
# 【微信支付后台】(pay.weixin.qq.com)
# - 支付授权目录: https://${DLWEB_DOMAIN}/
# - 支付回调通知: 由代码中 notify_url 指定
#
# =============================================
# =============================================
# SSL 通用配置(被各 server 块 include
# =============================================
# 注意: ssl-params.conf 由 init-ssl.sh 生成到
# /etc/nginx/snippets/ssl-params.conf
# ===== HTTP → HTTPS 统一重定向 + ACME 验证 =====
server {
listen 80 default_server;
listen [::]:80 default_server;
server_name _;
# Let's Encrypt 域名验证 (必须保留)
location /.well-known/acme-challenge/ {
root /var/www/certbot;
}
# 健康检查(供内部/负载均衡器使用,不重定向)
location /health {
return 200 'OK';
add_header Content-Type text/plain;
}
# 其余全部 301 重定向到 HTTPS
location / {
return 301 https://$host$request_uri;
}
}
# ===== 网站1: 游戏核心 API (公众号后台) =====
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name ${API_DOMAIN};
ssl_certificate /etc/letsencrypt/live/${API_DOMAIN}/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/${API_DOMAIN}/privkey.pem;
include /etc/nginx/snippets/ssl-params.conf;
location / {
proxy_pass http://api_service;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
# ===== 网站2: 代理管理后台 (微信支付) =====
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name ${DLWEB_DOMAIN};
ssl_certificate /etc/letsencrypt/live/${DLWEB_DOMAIN}/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/${DLWEB_DOMAIN}/privkey.pem;
include /etc/nginx/snippets/ssl-params.conf;
location / {
proxy_pass http://dlweb_service;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
# ===== 网站3: 微信小程序后端 =====
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name ${WX_DOMAIN};
ssl_certificate /etc/letsencrypt/live/${WX_DOMAIN}/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/${WX_DOMAIN}/privkey.pem;
include /etc/nginx/snippets/ssl-params.conf;
location / {
proxy_pass http://wxserver_service;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
}

View File

@@ -0,0 +1,23 @@
# SSL 安全参数 (适用于 Let's Encrypt 证书)
# 此文件被 init-ssl.sh 复制到容器内 /etc/nginx/snippets/ssl-params.conf
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;
# HSTS (取消注释以启用,请确认所有子域都支持 HTTPS 后再启用)
# add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
# OCSP Stapling
ssl_stapling on;
ssl_stapling_verify on;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
# SSL session 优化
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 1d;
ssl_session_tickets off;
# DH 参数 (如果生成了 dhparam.pem)
# ssl_dhparam /etc/nginx/ssl/dhparam.pem;

View File

@@ -0,0 +1,36 @@
#!/bin/sh
# 定时同步任务:每 SYNC_INTERVAL 秒 POST 请求 dlweb 容器的 Synchronize.php
# 通过 Docker 内网直连,不走域名/公网流量
# 支持暂停:当 /shared/syncjob.pause 文件存在时,跳过本轮请求
# 安装 curl仅首次后续重启容器时已安装则跳过
command -v curl > /dev/null 2>&1 || apk add --no-cache curl > /dev/null 2>&1
SYNC_URL="${SYNC_URL:-http://dlweb/ext/Synchronize.php}"
SYNC_INTERVAL="${SYNC_INTERVAL:-30}"
SYNC_PROCESSCOUNT="${SYNC_PROCESSCOUNT:-200}"
PAUSE_FILE="/shared/syncjob.pause"
echo "[syncjob] target: ${SYNC_URL}?processcount=${SYNC_PROCESSCOUNT}"
echo "[syncjob] interval: ${SYNC_INTERVAL}s"
while true; do
# 检查暂停信号cronjob 执行期间会创建此文件)
if [ -f "${PAUSE_FILE}" ]; then
echo "[$(date '+%Y-%m-%d %H:%M:%S')] PAUSED (${PAUSE_FILE} exists), skipping..."
sleep "${SYNC_INTERVAL}"
continue
fi
RESULT=$(curl -sf -X POST "${SYNC_URL}?processcount=${SYNC_PROCESSCOUNT}" 2>&1)
EXIT_CODE=$?
TIMESTAMP=$(date '+%Y-%m-%d %H:%M:%S')
if [ $EXIT_CODE -eq 0 ]; then
echo "[${TIMESTAMP}] OK: ${RESULT}"
else
echo "[${TIMESTAMP}] FAIL(${EXIT_CODE}): ${RESULT}"
fi
sleep "${SYNC_INTERVAL}"
done

View File

@@ -0,0 +1,20 @@
FROM node:18-alpine
WORKDIR /app
# 安装依赖
COPY wxserver_daoqi/package.json ./
RUN npm install --production
# 拷贝应用代码
COPY wxserver_daoqi/ ./
# 设置时区
RUN apk add --no-cache tzdata \
&& cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime \
&& echo "Asia/Shanghai" > /etc/timezone \
&& apk del tzdata
EXPOSE 3000
CMD ["node", "index.js"]