b968ec8aa5
Reverse proxy Nginx (image stable-alpine) qui sert l'app upstream ou une page de maintenance 503 selon l'IP du client. - Modes whitelist/blacklist commutables via MAINTENANCE_MODE - Liste IPv4 via MAINTENANCE_IP_LIST (séparée par virgules, validée au boot) - Logique en directives Nginx natives (geo + map), zéro Lua/njs - Page statique sobre HTML+CSS inline, zéro JS, zéro réseau sortant - Log dédié /var/log/nginx/maintenance.log pour les requêtes bloquées - Validation des env vars dans /docker-entrypoint.d/10-init.sh - Stack Docker + docker-compose pour dev local et tests - 6 cas de tests d'intégration (whitelist/blacklist x autorisée/bloquée + log + nginx -t) - Lint shellcheck propre sur tous les scripts shell
71 lines
1.9 KiB
Bash
71 lines
1.9 KiB
Bash
#!/usr/bin/env bash
|
|
# Helpers partagés par tests/run.sh et tests/cases/*.sh.
|
|
# Ce fichier est sourcé, pas exécuté directement.
|
|
|
|
# shellcheck shell=bash
|
|
|
|
set -euo pipefail
|
|
|
|
PROJECT_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
|
COMPOSE_FILE="$PROJECT_ROOT/docker-compose.test.yml"
|
|
COMPOSE=(docker compose -f "$COMPOSE_FILE" -p maintenance_proxy_tests)
|
|
|
|
PROXY_URL="http://172.28.5.10:8080/"
|
|
|
|
t_log() { echo "[test] $*"; }
|
|
t_fail() { echo "[test] FAIL: $*" >&2; return 1; }
|
|
|
|
# Recrée le conteneur proxy avec les env vars passées, puis attend qu'il
|
|
# réponde sur PROXY_URL (n'importe quel code HTTP suffit, on veut juste
|
|
# qu'Nginx ait fini de booter).
|
|
restart_proxy() {
|
|
local mode="$1"
|
|
local ip_list="$2"
|
|
|
|
MAINTENANCE_MODE="$mode" \
|
|
MAINTENANCE_IP_LIST="$ip_list" \
|
|
"${COMPOSE[@]}" up -d --force-recreate --no-deps proxy >/dev/null
|
|
|
|
local _
|
|
for _ in $(seq 1 30); do
|
|
if "${COMPOSE[@]}" exec -T client \
|
|
curl -s -o /dev/null -w '%{http_code}' --max-time 2 "$PROXY_URL" \
|
|
| grep -qE '^(200|503)$'; then
|
|
return 0
|
|
fi
|
|
sleep 1
|
|
done
|
|
t_fail "le proxy n'a pas démarré dans les 30s (mode=$mode, list=$ip_list)"
|
|
}
|
|
|
|
curl_status() {
|
|
"${COMPOSE[@]}" exec -T client \
|
|
curl -s -o /dev/null -w '%{http_code}' --max-time 5 "$PROXY_URL"
|
|
}
|
|
|
|
curl_body() {
|
|
"${COMPOSE[@]}" exec -T client curl -s --max-time 5 "$PROXY_URL"
|
|
}
|
|
|
|
proxy_exec() {
|
|
"${COMPOSE[@]}" exec -T proxy "$@"
|
|
}
|
|
|
|
assert_eq() {
|
|
local expected="$1"
|
|
local actual="$2"
|
|
local label="${3:-valeur}"
|
|
if [[ "$expected" != "$actual" ]]; then
|
|
t_fail "$label : attendu '$expected', obtenu '$actual'"
|
|
fi
|
|
}
|
|
|
|
assert_contains() {
|
|
local needle="$1"
|
|
local haystack="$2"
|
|
local label="${3:-contenu}"
|
|
if [[ "$haystack" != *"$needle"* ]]; then
|
|
t_fail "$label : '$needle' introuvable dans la sortie"
|
|
fi
|
|
}
|