Cloud
Azure VNet Integration : diagnostiquer une sortie réseau avant de modifier l'application
Un runbook opérationnel pour qualifier une panne de sortie réseau Azure App Service ou Functions en séparant VNet Integration, DNS, UDR, NSG, NAT, logs et rollback.
Une panne de sortie réseau Azure ressemble souvent à une panne applicative. L’API appelée ne répond plus, un worker voit des timeouts, une Function accumule les retries, ou un fournisseur SaaS refuse une adresse IP qui n’était pas attendue. Pourtant, quand App Service ou Functions utilisent VNet Integration, le problème peut venir du DNS, d’une route UDR, d’un NSG, d’un NAT Gateway, d’un firewall, ou d’un changement de dépendance.
Le cas d’usage est un workload Azure qui doit sortir vers une API privée, un service Azure, un endpoint Internet contrôlé ou une dépendance interne depuis un subnet d’intégration. L’objectif du runbook est de prouver où la sortie se casse avant de modifier le code, ouvrir largement les flux ou supprimer une route.
Lire la sortie comme une chaîne opérable
VNet Integration ne rend pas l’application joignable en privé. Elle influence surtout les flux sortants de l’application vers un VNet. Il faut donc lire l’incident comme une chaîne de sortie, pas comme un problème d’exposition entrante.
Workload
App Service, Function App, WebJob ou worker interne
Configuration VNet Integration active
Subnet dedie et capacite suffisante
Resolution
FQDN cible resolu depuis le contexte de l'application
DNS prive, forwarder ou resolver coherent avec la destination
Aucune hypothese basee seulement sur le poste admin
Routage
Route systeme ou UDR appliquee au subnet d'integration
Next hop attendu: Internet, Virtual Appliance, Firewall, Virtual Network ou None
Route specifique qui ne capture pas trop large
Filtrage et sortie
NSG du subnet
Azure Firewall ou NVA si present
NAT Gateway ou IP de sortie attendue
Regles cote destination
Preuves
Horodatage du test
Hostname et port testes
Adresse resolue
IP de sortie observee
Logs application, firewall ou destination Cette lecture évite deux confusions fréquentes : chercher un Private Endpoint alors que le flux est sortant, ou corriger le code alors que la route a changé.
Classer le symptôme avant la correction
Le même timeout peut venir d’une résolution DNS, d’un next hop incorrect, d’un port filtré, d’un NAT absent ou d’une règle côté destination. Il faut d’abord classer le symptôme avec le point de test.
Symptome observe
Nom non resolu ou mauvaise adresse
Verifier DNS, forwarders, zones privees et resolution depuis le workload
Timeout vers une adresse correcte
Verifier UDR, next hop, firewall, NSG et route de retour
Connexion refusee immediatement
Verifier port, service cible, listener, proxy ou regle cote destination
403 cote API ou SaaS
Verifier identite applicative et IP de sortie autorisee
Fonctionnement depuis le poste admin mais pas depuis l'app
Refaire le test depuis le subnet d'integration ou une sonde equivalente
Incident apres changement reseau
Comparer UDR, NSG, NAT Gateway, DNS et firewall avant de redeployer l'application La règle d’exploitation est simple : tant qu’un test depuis le chemin de sortie réel n’existe pas, l’hypothèse applicative reste fragile.
Vérifier l’intégration et le subnet
La première vérification consiste à confirmer que l’application utilise bien le subnet attendu, puis à lire les contrôles appliqués à ce subnet. Une configuration correcte hier peut avoir été remplacée par une intégration vers un autre subnet ou par une route plus large.
RG=rg-prod-app
APP=app-prod-orders
VNET_RG=rg-prod-network
VNET=vnet-prod-spoke
SUBNET=snet-app-outbound
az webapp vnet-integration list -g "$RG" -n "$APP" -o table
az network vnet subnet show -g "$VNET_RG" --vnet-name "$VNET" -n "$SUBNET" --query "{name:name,addressPrefix:addressPrefix,routeTable:routeTable.id,nsg:networkSecurityGroup.id,natGateway:natGateway.id,delegations:delegations[].serviceName}" -o jsonc
az network route-table route list --ids $(az network vnet subnet show -g "$VNET_RG" --vnet-name "$VNET" -n "$SUBNET" --query routeTable.id -o tsv) --query "[].{name:name,prefix:addressPrefix,nextHop:nextHopType,nextHopIp:nextHopIpAddress}" -o table Pour Functions, adaptez la commande d’intégration au type d’application. Le point important n’est pas la commande elle-même, mais la preuve : le workload sort par le subnet que vous êtes en train de diagnostiquer.
Tester DNS depuis le bon contexte
Le DNS est souvent le premier écart entre un poste admin et l’application. Une dépendance peut résoudre vers une adresse privée depuis un subnet, vers une adresse publique depuis un autre, ou vers un ancien endpoint à cause d’un forwarder.
TARGET_HOST=api.internal.example
TARGET_PORT=443
# A lancer depuis une console applicative, un conteneur de diagnostic,
# une VM temporaire dans un subnet equivalent, ou une sonde controlee.
nslookup "$TARGET_HOST"
dig +short "$TARGET_HOST"
curl -vk --connect-timeout 5 "https://$TARGET_HOST/health"
# Si la destination doit voir une IP de sortie fixe, comparer avec l'IP attendue.
curl -s https://ifconfig.me Une VM dans le même VNet n’est pas toujours équivalente au subnet d’intégration, surtout si UDR, NSG ou NAT sont appliqués différemment. Elle reste utile si elle documente clairement son subnet, ses routes et ses règles.
Lire UDR, NSG et NAT ensemble
Une route peut envoyer le flux vers un firewall, un NSG peut bloquer un port, et un NAT Gateway peut changer l’adresse vue par la destination. Les lire séparément produit des diagnostics incomplets.
Question de diagnostic
La destination est-elle privee ou publique ?
Le prefixe le plus specifique pointe-t-il vers le bon next hop ?
Le firewall ou la NVA a-t-il une regle sortante explicite ?
Le NSG autorise-t-il le port depuis le subnet d'integration ?
Le NAT Gateway est-il attache au bon subnet ?
La destination autorise-t-elle l'IP de sortie observee ?
La route de retour est-elle symetrique quand un chemin prive est utilise ? Ce point est particulièrement important après un changement Terraform. Une UDR 0.0.0.0/0 vers un firewall peut être correcte, mais elle doit être accompagnée des règles firewall, DNS et NAT correspondantes.
Corréler avec les logs applicatifs et réseau
Les logs applicatifs disent ce que le runtime observe. Les logs réseau disent si le flux atteint une couche de contrôle. Il faut les rapprocher par fenêtre de temps, hostname, port, IP et identifiant de requête si disponible.
let Window = 2h;
let TargetHost = "api.internal.example";
AppTraces
| where TimeGenerated > ago(Window)
| where Message has_any (TargetHost, "timeout", "NameResolution", "SocketException", "connection refused", "403")
| project TimeGenerated, AppRoleName, SeverityLevel, Message, OperationId
| order by TimeGenerated desc Si vous utilisez Azure Firewall, NSG flow logs ou les logs de la destination, ajoutez la même fenêtre de temps. L’absence de log firewall pour un test documenté oriente vers DNS, route, NSG local ou mauvais point de test. Un deny explicite oriente vers la règle. Une réponse 403 avec flux visible oriente plutôt vers identité, allowlist d’IP ou politique de la destination.
Choisir la correction minimale
La correction doit viser la couche prouvée. Ouvrir temporairement toutes les sorties ou supprimer la route par défaut peut restaurer le service, mais cela masque la cause et crée souvent un second incident de sécurité.
Cause prouvee
Mauvaise resolution DNS
Correction: zone, forwarder, resolver ou configuration DNS de l'app
Validation: le hostname retourne l'adresse attendue depuis le chemin workload
UDR trop large ou mauvais next hop
Correction: route plus specifique ou next hop corrige
Validation: le flux atteint le firewall ou la destination attendue
NSG ou firewall bloque le port
Correction: regle ciblee source, destination, port, protocole
Validation: deny disparu et requete applicative visible
NAT ou IP de sortie inattendue
Correction: NAT Gateway, route ou allowlist destination alignee
Validation: la destination voit l'IP approuvee
Identite ou politique destination
Correction: droit applicatif ou allowlist precise
Validation: meme requete reussit sans ouvrir le reseau plus largement Le bon changement est celui qui explique le symptôme et dont la validation peut être rejouée.
Préparer un rollback qui garde les preuves
Le rollback doit être décidé par couche : DNS, route, NSG, NAT, firewall ou version applicative. Il ne doit pas effacer les logs utiles ni rendre impossible la comparaison avant/après.
Changement recent
Route table ou UDR
Rollback: restaurer la route precedente ou retirer la route fautive
Preuve: next hop observe et test de connexion documente
NSG ou firewall
Rollback: revenir a la regle precedente ou appliquer une exception ciblee temporaire
Preuve: deny identifie, scope source/destination/port limite
NAT Gateway ou IP de sortie
Rollback: rattacher le NAT precedent ou restaurer l'allowlist connue
Preuve: IP de sortie observee par la destination
DNS ou forwarder
Rollback: restaurer la resolution precedente
Preuve: FQDN resolu avec horodatage depuis le workload
Deploiement applicatif
Rollback: revenir a la version precedente seulement si le chemin reseau est propre
Preuve: meme dependance joignable avec logs propres Conclusion
Une panne de sortie avec VNet Integration se traite comme une chaîne de production : workload, DNS, subnet d’intégration, UDR, NSG, firewall, NAT, destination, logs et rollback. Le diagnostic doit prouver si l’application ne sait plus résoudre, ne sait plus router, est filtrée, sort avec la mauvaise IP ou est refusée par la dépendance.
La décision devient alors défendable : corriger DNS quand le nom est faux, UDR quand le next hop est mauvais, NSG ou firewall quand le deny est prouvé, NAT quand l’IP de sortie dérive, et l’application seulement quand le chemin réseau est propre.