Sophie relit le script de la leçon précédente : « Ton script suppose que l’API répond toujours correctement, et que tous les tickets tiennent dans une seule réponse. En vrai, une API peut tomber en panne, refuser une requête trop fréquente, ou ne renvoyer qu’une partie des résultats à la fois. » Cette dernière leçon de la section couvre les deux réalités qu’on rencontre dès qu’on consomme une API un peu sérieuse.
Les codes de statut HTTP : que signifient-ils
Avant de gérer une erreur, encore faut-il savoir la reconnaître. Quelques codes fréquents à connaître :
| Code | Signification | Exemple de cause |
|---|---|---|
200 | Succès | La requête a fonctionné normalement |
401 | Non autorisé | Authentification manquante ou invalide (voir 9.2) |
403 | Interdit | Authentifié, mais sans les droits nécessaires |
404 | Introuvable | La ressource demandée n’existe pas |
429 | Trop de requêtes | Limite de fréquence (rate limit) dépassée |
500 | Erreur serveur | Problème du côté de l’API elle-même |
Try/catch avec une API : ce qui change
Contrairement aux cmdlets vues en section 5, Invoke-RestMethod lève systématiquement une erreur terminante dès qu’un code de statut d’échec est renvoyé (4xx ou 5xx) — pas besoin d’ajouter -ErrorAction Stop comme pour Get-Service :
try {
$ticket = Invoke-RestMethod -Uri "https://api.nordika-ticketing.local/tickets/99999"
} catch {
$codeStatut = $_.Exception.Response.StatusCode.value__
Write-Warning "Erreur $codeStatut lors de la récupération du ticket : $($_.Exception.Message)"
}$_.Exception.Response.StatusCode permet de récupérer précisément le code HTTP reçu, pour adapter la réaction du script selon le cas.
Gérer spécifiquement le code 429 (limite de fréquence)
Beaucoup d’API imposent une limite de requêtes par minute. Un script un peu robuste doit prévoir ce cas, plutôt que d’échouer immédiatement :
function Invoke-ApiAvecRetry {
param (
[string]$Uri,
[int]$TentativesMax = 3
)
$tentative = 0
while ($tentative -lt $TentativesMax) {
try {
return Invoke-RestMethod -Uri $Uri -ErrorAction Stop
} catch {
$codeStatut = $_.Exception.Response.StatusCode.value__
if ($codeStatut -eq 429) {
Write-Warning "Limite de requêtes atteinte, nouvelle tentative dans 10 secondes..."
Start-Sleep -Seconds 10
$tentative++
} else {
throw
}
}
}
throw "Échec après $TentativesMax tentatives"
}throw (rencontré ici pour la première fois) relance explicitement une erreur : dans le premier cas, pour la faire remonter si ce n’est pas un code 429 gérable ; dans le second, pour signaler l’échec définitif après épuisement des tentatives. Cette fonction reprend directement l’esprit de la boucle while bornée vue en 5.3, appliquée cette fois à un problème réseau plutôt qu’à un service Windows.
La pagination : quand une API ne renvoie pas tout d’un coup
La plupart des API limitent le nombre de résultats renvoyés en une seule requête (souvent 50 ou 100), pour des raisons de performance. Le mécanisme varie selon l’API, mais deux approches dominent.
Pagination par numéro de page :
$tousLesTickets = @()
$page = 1
do {
$reponse = Invoke-RestMethod -Uri "https://api.nordika-ticketing.local/tickets?page=$page&taille=50"
$tousLesTickets += $reponse.resultats
$page++
} while ($reponse.pageSuivante)
Write-Output "$($tousLesTickets.Count) tickets récupérés au total"do { } while ( ) (une variante de la boucle while vue en 5.3) garantit d’exécuter le bloc au moins une fois, avant de vérifier la condition — adapté ici puisqu’on doit forcément récupérer la première page avant de savoir s’il y en a une suivante.
Pagination par curseur (token de continuation) :
$tousLesTickets = @()
$curseur = $null
do {
$uri = "https://api.nordika-ticketing.local/tickets?taille=50"
if ($curseur) { $uri += "&curseur=$curseur" }
$reponse = Invoke-RestMethod -Uri $uri
$tousLesTickets += $reponse.resultats
$curseur = $reponse.curseurSuivant
} while ($curseur)Ce second mécanisme, plus robuste sur des données qui évoluent pendant la pagination (contrairement au numéro de page, qui peut décaler des résultats si des éléments sont ajoutés entre deux appels), est de plus en plus répandu sur les API modernes, notamment Microsoft Graph.
Un exemple concret Nordika : le script complet et robuste
function Get-TousLesTicketsOuverts {
$tousLesTickets = @()
$page = 1
do {
try {
$reponse = Invoke-RestMethod -Uri "https://api.nordika-ticketing.local/tickets?statut=ouvert&page=$page" -ErrorAction Stop
$tousLesTickets += $reponse.resultats
$page++
} catch {
$codeStatut = $_.Exception.Response.StatusCode.value__
if ($codeStatut -eq 429) {
Start-Sleep -Seconds 10
} else {
Write-Warning "Erreur $codeStatut lors de la récupération de la page $page"
break
}
}
} while ($reponse.pageSuivante)
return $tousLesTickets
}
$ticketsOuverts = Get-TousLesTicketsOuverts
Write-Output "$($ticketsOuverts.Count) ticket(s) ouvert(s) au total, toutes pages confondues"Retour d’expérience terrain : un script d’intégration API qui fonctionne parfaitement en test, avec un petit jeu de données, échoue souvent en production dès que le volume réel dépasse une seule page de résultats — un piège classique découvert trop tard si la pagination n’a pas été anticipée dès l’écriture initiale du script.
Source officielle : la documentation Microsoft
about_Throwdétaille le fonctionnement complet dethrow, et la plupart des API documentent leur propre mécanisme de pagination et de limite de fréquence dans leur documentation technique (souvent une page dédiée « Rate Limiting » ou « Pagination »).
Cette leçon referme la boucle logique de toute la section 9 : consommer une API (9.1), s’authentifier (9.2), et gérer sa fiabilité réelle en conditions de production (9.3) — trois briques indissociables dès qu’un script Nordika dépend d’un service externe.
Dans la prochaine leçon, on inverse la perspective : plutôt que de consommer une API, on apprend à en créer une soi-même avec PowerShell, grâce au module Pode.