From b4824ddf71adca32068e831b51602a389e646e14 Mon Sep 17 00:00:00 2001 From: ouyangxq <775153912@qq.com> Date: Sun, 20 Sep 2026 21:49:30 +0800 Subject: [PATCH] fix: harden blue-green routing and gateway migration --- deploy/scripts/deploy-blue-green-service.sh | 26 ++++++++++++------- .../blue-green-deployment-contract.test.mjs | 2 ++ 2 files changed, 18 insertions(+), 10 deletions(-) diff --git a/deploy/scripts/deploy-blue-green-service.sh b/deploy/scripts/deploy-blue-green-service.sh index 462bc5527..ad1f4b5b0 100644 --- a/deploy/scripts/deploy-blue-green-service.sh +++ b/deploy/scripts/deploy-blue-green-service.sh @@ -219,10 +219,15 @@ bootstrap_legacy_routes() { switch_gateway_proxy() { [ "$SERVICE" = "gateway" ] || [ "$SERVICE" = "gateway-overseas" ] || return 0 if [ "$SERVICE" = "gateway" ]; then required_alias=gateway-active; else required_alias=gateway-overseas-active; fi - for frontend in firstleg-prod-admin-web-blue firstleg-prod-admin-web-green \ - firstleg-prod-client-web-blue firstleg-prod-client-web-green; do - if docker inspect "$frontend" >/dev/null 2>&1 \ - && ! docker exec "$frontend" nginx -T 2>&1 | grep -q "$required_alias"; then + for frontend_service in admin-web client-web; do + frontend_state="$STATE_ROOT/frontend-$frontend_service.active" + if [ ! -s "$frontend_state" ]; then + echo "$frontend_service 尚未完成首次蓝绿迁移,拒绝切换 Gateway" >&2 + return 1 + fi + IFS='|' read -r frontend_slot frontend frontend_port frontend_image < "$frontend_state" + if ! docker inspect "$frontend" >/dev/null 2>&1 \ + || ! docker exec "$frontend" nginx -T 2>&1 | grep -q "$required_alias"; then echo "$frontend 尚未使用稳定上游 $required_alias,拒绝切换 Gateway" >&2 return 1 fi @@ -256,12 +261,13 @@ switch_gateway_proxy() { reload_frontend_proxies() { [ "$SERVICE" = "gateway" ] || [ "$SERVICE" = "gateway-overseas" ] || return 0 - for frontend in firstleg-prod-admin-web-blue firstleg-prod-admin-web-green \ - firstleg-prod-client-web-blue firstleg-prod-client-web-green; do - if docker inspect "$frontend" >/dev/null 2>&1; then - docker exec "$frontend" nginx -t - docker exec "$frontend" nginx -s reload - fi + for frontend_service in admin-web client-web; do + frontend_state="$STATE_ROOT/frontend-$frontend_service.active" + [ -s "$frontend_state" ] || return 1 + IFS='|' read -r frontend_slot frontend frontend_port frontend_image < "$frontend_state" + docker inspect "$frontend" >/dev/null 2>&1 || return 1 + docker exec "$frontend" nginx -t + docker exec "$frontend" nginx -s reload done } diff --git a/scripts/blue-green-deployment-contract.test.mjs b/scripts/blue-green-deployment-contract.test.mjs index 0321df845..259f4b28f 100644 --- a/scripts/blue-green-deployment-contract.test.mjs +++ b/scripts/blue-green-deployment-contract.test.mjs @@ -43,6 +43,8 @@ test('gateway cutover is atomic and restores nginx config on validation failure' const script = await read('deploy/scripts/deploy-blue-green-service.sh') assert.match(script, /api-cn\.buggoglobal\.com\.conf/) assert.match(script, /api-global\.buggoglobal\.com\.conf/) + assert.match(script, /尚未完成首次蓝绿迁移,拒绝切换 Gateway/) + assert.match(script, /frontend-\$frontend_service\.active/) assert.match(script, /尚未使用稳定上游 \$required_alias,拒绝切换 Gateway/) assert.match(script, /reload_frontend_proxies/) assert.match(script, /cp -f "\$config" "\$backup"/)