Apres /ping, /oauth2/start doit renvoyer vers l emetteur configure pour ce client, et l IdP, joint depuis la passerelle, doit servir sa page de connexion. Le secret du client n est pas teste (journal du realm). Port derive de l ecoute ; archive oauth2-proxy plus retransferee a chaque deploiement. Fin de la revue des sondes. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
63 lines
3.7 KiB
Django/Jinja
63 lines
3.7 KiB
Django/Jinja
#!/bin/bash
|
|
# GENERE par Set-OPS (role serveur_oauth2_proxy). Ne pas editer a la main.
|
|
#
|
|
# SONDE « passerelle » — la passerelle repond, et MENE VRAIMENT a la connexion.
|
|
#
|
|
# CE QUI TOMBE AVEC ELLE N'EST PAS ELLE. Cette passerelle porte l'acces aux applications
|
|
# qui n'ont pas de SSO natif — la vigie, la console. Quand elle meurt, les services
|
|
# derriere restent debout et deviennent injoignables : on cherche la panne du mauvais cote.
|
|
#
|
|
# Mise en defaut PAR PARAMETRE : `serveur_oauth2_proxy_sonde_attendu` (premiere etape),
|
|
# `serveur_oauth2_proxy_sonde_retour` (URL de retour que le client n'autorise pas).
|
|
set -uo pipefail
|
|
|
|
PORT={{ serveur_oauth2_proxy_sonde_port }}
|
|
CFG={{ serveur_oauth2_proxy_config }}
|
|
RETOUR='{{ serveur_oauth2_proxy_sonde_retour }}'
|
|
|
|
# PREMIERE ETAPE — LE PROCESSUS REPOND. `check_http` parle deja l'API des greffons Nagios.
|
|
ping=$(/usr/lib/nagios/plugins/check_http -H 127.0.0.1 -p "${PORT}" -u '/ping' \
|
|
-s '{{ serveur_oauth2_proxy_sonde_attendu }}' -t 8 2>&1)
|
|
rc=$?
|
|
(( rc == 0 )) || { echo "La passerelle ne repond pas : $(printf '%s' "${ping}" | tr '\n' ' ' | cut -c1-160)"; exit "${rc}"; }
|
|
|
|
# SECONDE ETAPE — ELLE MENE A LA CONNEXION (2026-09-28). `/ping` repond tant que le
|
|
# processus vit, meme quand plus personne ne peut entrer : client supprime ou renomme
|
|
# dans Keycloak, URL de retour retiree du client, IdP injoignable DEPUIS CETTE MACHINE
|
|
# (resolution, route, pare-feu, autorite de certification). On fait donc le trajet d'un
|
|
# visiteur : `/oauth2/start` doit renvoyer vers l'IdP configure, pour CE client ; et
|
|
# l'IdP, joint d'ici avec le meme magasin de confiance que la passerelle, doit servir sa
|
|
# page de connexion. C'est le meme chemin que prend l'echange du code apres connexion.
|
|
#
|
|
# CE QU'ON NE TESTE PAS, ET POURQUOI : le SECRET du client. Le verifier demande un echange
|
|
# de jeton rate — Keycloak l'ecrit dans le journal de securite du realm. Toutes les
|
|
# 15 minutes, par passerelle, ce serait noyer le journal qu'on lit pour trouver les vraies
|
|
# tentatives. Le cas sain ici n'ecrit RIEN dans ce journal.
|
|
valeur() { grep -m1 -oP "^$1\s*=\s*\[?\"\K[^\"]+" "${CFG}" 2>/dev/null; }
|
|
EMETTEUR=$(valeur oidc_issuer_url); CLIENT=$(valeur client_id); CA=$(valeur provider_ca_files)
|
|
[[ -n "${EMETTEUR}" && -n "${CLIENT}" ]] \
|
|
|| { echo "La passerelle repond, mais sa configuration est illisible (${CFG})."; exit 2; }
|
|
|
|
loc=$(curl -s -o /dev/null -D - --max-time 8 -H 'X-Forwarded-Proto: https' \
|
|
"http://127.0.0.1:${PORT}/oauth2/start?rd=%2F" 2>/dev/null | tr -d '\r' \
|
|
| awk 'tolower($1) == "location:" {print $2; exit}')
|
|
if [[ "${loc}" != "${EMETTEUR}/protocol/openid-connect/auth?"* || "${loc}" != *"client_id=${CLIENT}&"* ]]; then
|
|
echo "La passerelle repond, mais NE RENVOIE PAS vers ${EMETTEUR} pour le client « ${CLIENT} » (renvoie : ${loc:-rien})."
|
|
exit 2
|
|
fi
|
|
[[ -n "${RETOUR}" ]] && loc=$(printf '%s' "${loc}" | sed -E "s#redirect_uri=[^&]*#redirect_uri=${RETOUR}#")
|
|
|
|
page=$(mktemp); trap 'rm -f "${page}"' EXIT
|
|
res=$(curl -s -o "${page}" -w '%{http_code} %{exitcode} %{errormsg}' --max-time 10 \
|
|
${CA:+--cacert "${CA}"} "${loc}" 2>/dev/null)
|
|
code=${res%% *}
|
|
if [[ "${code}" == "000" ]]; then
|
|
echo "La passerelle renvoie vers ${EMETTEUR}, mais cette machine N'ATTEINT PAS l'IdP (curl ${res#* }) — la connexion echouera au retour."
|
|
exit 2
|
|
fi
|
|
if [[ "${code}" != "200" ]]; then
|
|
motif=$(grep -oiE 'Invalid parameter: [a-z_]+|Client not found|Realm does not exist|Page not found' "${page}" | head -1)
|
|
echo "L'IdP REFUSE le trajet de connexion du client « ${CLIENT} » : HTTP ${code}${motif:+ — ${motif}}. Personne ne peut entrer."
|
|
exit 2
|
|
fi
|
|
echo "Passerelle : repond, et mene a la page de connexion de ${EMETTEUR} pour le client « ${CLIENT} »."
|