enhance: 多候选IP探测策略优化DooD模式宿主机检测
CI/CD Pipeline / Build Staging Web Image (pull_request) Has been skipped
CI/CD Pipeline / Build Staging API Image (pull_request) Has been skipped
CI/CD Pipeline / Build Staging Worker Image (pull_request) Has been skipped
CI/CD Pipeline / Deploy Staging (Watchtower auto-deploy) (pull_request) Has been skipped
CI/CD Pipeline / Build Production Worker Image (pull_request) Has been skipped
CI/CD Pipeline / Build Production API Image (pull_request) Has been skipped
CI/CD Pipeline / Staging API Integration Tests (pull_request) Has been skipped
CI/CD Pipeline / ACR Image Cleanup (pull_request) Has been skipped
CI/CD Pipeline / Staging E2E Tests (pull_request) Has been skipped
CI/CD Pipeline / Build Production Web Image (pull_request) Has been skipped
CI/CD Pipeline / Deploy Production (pull_request) Has been skipped
CI/CD Pipeline / Production Browser E2E (pull_request) Has been skipped
CI/CD Pipeline / Check if frontend-only change (pull_request) Successful in 19s
Preview Deploy / Deploy Preview Environment (pull_request) Successful in 49s
CI/CD Pipeline / Frontend Unit Tests (pull_request) Has been skipped
CI/CD Pipeline / Frontend Lint (pull_request) Successful in 2m16s
CI/CD Pipeline / Validate Code Quality And Tests (pull_request) Successful in 3m1s
CI/CD Pipeline / Unit Tests (pull_request) Successful in 3m4s
PR Automation / Auto Approve on CI Green (pull_request) Successful in 3m33s
AI Code Review / AI Code Review (pull_request) Successful in 4m15s
CI/CD Pipeline / Integration Tests (pull_request) Successful in 1m11s
PR Automation / Auto Merge on CI Green + Approved (pull_request) Successful in 5m36s
Preview Cleanup / Cleanup Preview Environment (pull_request) Successful in 27s

This commit is contained in:
2026-07-20 00:54:25 +08:00
parent 6759f34eb7
commit 08d163f623
2 changed files with 109 additions and 36 deletions
+56 -13
View File
@@ -43,29 +43,72 @@ bash scripts/ci/step_install_ffmpeg.sh
# --- DooD模式检测:确定宿主机访问地址 ---
# DooD模式下,docker run启动的容器跑在宿主机Docker上
# 需要用宿主机IP访问映射端口
# 检测策略:host.docker.internal -> 默认网关 -> 127.0.0.1
# 检测策略:host.docker.internal -> docker0桥接IP -> 容器IP直连 -> 默认网关 -> 127.0.0.1
detect_docker_host() {
# 1. 尝试 host.docker.internalrunner配置了--add-host时可用)
local test_port="${1:-5432}"
# 候选IP列表
local candidates=()
# 1. host.docker.internalrunner配置了--add-host时可用)
if python3 -c "import socket; socket.gethostbyname('host.docker.internal')" 2>/dev/null; then
echo "host.docker.internal"
return 0
candidates+=("host.docker.internal")
fi
# 2. 尝试默认网关(Docker容器默认网关即宿主机)
local gateway=""
gateway=$(ip route 2>/dev/null | grep default | awk '{print $3}' | head -1)
if [ -n "$gateway" ] && [ "$gateway" != "127.0.0.1" ]; then
echo "$gateway"
return 0
# 2. docker0 桥接网关 (172.17.0.1)
candidates+=("172.17.0.1")
# 3. 默认网关(容器网络的网关即宿主机)
local gw=""
gw=$(ip route 2>/dev/null | grep default | awk '{print $3}' | head -1)
if [ -n "$gw" ] && [ "$gw" != "127.0.0.1" ]; then
candidates+=("$gw")
fi
# 3. 回退到 127.0.0.1
# 4. 宿主机可能的IP:容器同网段的.1或.254
local my_ip=""
my_ip=$(hostname -I 2>/dev/null | awk '{print $1}')
if [ -n "$my_ip" ]; then
# 尝试同网段的常见宿主机IP
local subnet=$(echo "$my_ip" | cut -d. -f1-3)
candidates+=("${subnet}.1")
candidates+=("${subnet}.254")
fi
# 5. 127.0.0.1 最后尝试
candidates+=("127.0.0.1")
# 测试每个候选IP
for candidate in "${candidates[@]}"; do
if python3 -c "
import socket
s = socket.socket()
s.settimeout(2)
try:
s.connect(('$candidate', $test_port))
s.close()
print('ok')
except:
pass
" 2>/dev/null | grep -q ok; then
echo "$candidate"
return 0
fi
done
# 都失败则返回127.0.0.1
echo "127.0.0.1"
return 0
return 1
}
# 获取宿主机IP(先尝试用共享PG端口5433测试,再回退到其他端口)
if [ -S /var/run/docker.sock ]; then
DOCKER_HOST_IP=$(detect_docker_host)
# 先用共享PG端口5433探测
DOCKER_HOST_IP=$(detect_docker_host 5433)
if [ "$DOCKER_HOST_IP" = "127.0.0.1" ]; then
# 如果共享PG端口探测失败,说明不在DooD或共享PG不可用,再试其他端口
DOCKER_HOST_IP=$(detect_docker_host 22)
fi
echo "检测到DooD模式(/var/run/docker.sock已挂载),宿主机地址: $DOCKER_HOST_IP"
else
DOCKER_HOST_IP="127.0.0.1"
+53 -23
View File
@@ -182,48 +182,78 @@ echo "=== [8/8] Alembic migrations validation ==="
# --- DooD模式检测:确定宿主机访问地址 ---
# DooD模式下,docker run启动的容器跑在宿主机Docker上
# 需要用宿主机IP访问映射端口
# 检测策略:host.docker.internal -> 默认网关 -> 127.0.0.1
# 检测策略:host.docker.internal -> docker0桥接IP -> 容器IP直连 -> 默认网关 -> 127.0.0.1
detect_docker_host() {
# 1. 尝试 host.docker.internalrunner配置了--add-host时可用)
local test_port="${1:-5432}"
# 候选IP列表
local candidates=()
# 1. host.docker.internalrunner配置了--add-host时可用)
if python3 -c "import socket; socket.gethostbyname('host.docker.internal')" 2>/dev/null; then
# 确认端口可达性(用一个常用端口快速检测)
candidates+=("host.docker.internal")
fi
# 2. docker0 桥接网关 (172.17.0.1)
candidates+=("172.17.0.1")
# 3. 默认网关(容器网络的网关即宿主机)
local gw=""
gw=$(ip route 2>/dev/null | grep default | awk '{print $3}' | head -1)
if [ -n "$gw" ] && [ "$gw" != "127.0.0.1" ]; then
candidates+=("$gw")
fi
# 4. 宿主机可能的IP:容器同网段的.1或.254
local my_ip=""
my_ip=$(hostname -I 2>/dev/null | awk '{print $1}')
if [ -n "$my_ip" ]; then
# 尝试同网段的常见宿主机IP
local subnet=$(echo "$my_ip" | cut -d. -f1-3)
candidates+=("${subnet}.1")
candidates+=("${subnet}.254")
fi
# 5. 127.0.0.1 最后尝试
candidates+=("127.0.0.1")
# 测试每个候选IP
for candidate in "${candidates[@]}"; do
if python3 -c "
import socket
s = socket.socket()
s.settimeout(1)
s.settimeout(2)
try:
s.connect(('host.docker.internal', 5433))
s.connect(('$candidate', $test_port))
s.close()
print('ok')
except:
# 端口不通不代表host不对,可能只是没服务
print('ok')
" 2>/dev/null; then
echo "host.docker.internal"
pass
" 2>/dev/null | grep -q ok; then
echo "$candidate"
return 0
fi
fi
done
# 2. 尝试默认网关(Docker容器默认网关即宿主机)
local gateway=""
gateway=$(ip route 2>/dev/null | grep default | awk '{print $3}' | head -1)
if [ -n "$gateway" ] && [ "$gateway" != "127.0.0.1" ]; then
echo "$gateway"
return 0
fi
# 3. 回退到 127.0.0.1
# 都失败则返回127.0.0.1
echo "127.0.0.1"
return 0
return 1
}
# 获取宿主机IP(先尝试用共享PG端口5433测试,再回退到其他端口)
if [ -S /var/run/docker.sock ]; then
PG_HOST=$(detect_docker_host)
echo "检测到DooD模式(/var/run/docker.sock已挂载),宿主机地址: $PG_HOST"
# 先用共享PG端口5433探测
DOCKER_HOST_IP=$(detect_docker_host 5433)
if [ "$DOCKER_HOST_IP" = "127.0.0.1" ]; then
# 如果共享PG端口探测失败,说明不在DooD或共享PG不可用,再试其他端口
DOCKER_HOST_IP=$(detect_docker_host 22)
fi
echo "检测到DooD模式(/var/run/docker.sock已挂载),宿主机地址: $DOCKER_HOST_IP"
else
PG_HOST="127.0.0.1"
DOCKER_HOST_IP="127.0.0.1"
echo "非DooD模式,使用 127.0.0.1"
fi
PG_HOST="$DOCKER_HOST_IP"
echo "PG host: $PG_HOST"
# 指数退避TCP连接检查函数