Obtenir un accès REST API dans un contexte utilisateur

Sur cette page

Pour certains scénarios, il peut être nécessaire d'obtenir un accès REST API dans un contexte utilisateur en utilisant le flux d'autorisation de l'appareil. Les étapes pour mettre cela en place ont été documentées en PowerShell, mais tout langage fera l'affaire. Voici comment cela fonctionne :

  1. Interroger l'accès URI de configuration OpenID bien connu pour récupérer les points de terminaison du jeton du serveur et d'autorisation d'appareil :

try {
    $wellKnownResponse = Invoke-RestMethod -Method Get -Uri $wellKnownEndpoint

    $tokenEndpoint = $wellKnownResponse.token_endpoint
    $deviceCodeEndpoint = $wellKnownResponse.device_authorization_endpoint
} catch {
    Write-Error "Error obtaining server information"
    exit
}
  1. Envoyer une requête au point de terminaison d’autorisation de l’appareil afin d’obtenir un code appareil, un code utilisateur, une URL de vérification et une URL de vérification complète, ainsi que des informations sur la durée de validité des codes et la fréquence de vérification. Ensuite, ouvrir un navigateur vers l'URL de vérification complète, ou demander à l'utilisateur de saisir manuellement son code utilisateur et d'approuver la demande d'accès de l'appareil :

$body = "client_id=$clientId&scope=$([uri]::EscapeDataString($scope))"

try {
    $deviceCodeResponse = Invoke-RestMethod -Method Post -Uri $deviceCodeEndpoint `
                            -ContentType "application/x-www-form-urlencoded" -Body $body
} catch {
    Write-Error "Failed to obtain device code: $_"
    exit
}

# Extract values from the response (field names may vary by provider)
$device_code               = $deviceCodeResponse.device_code
$user_code                 = $deviceCodeResponse.user_code
$verification_uri          = $deviceCodeResponse.verification_uri
$verification_uri_complete = $deviceCodeResponse.verification_uri_complete
$interval                  = 10   # in seconds
$expires_in                = $deviceCodeResponse.expires_in   # in seconds

# Provide a default interval if none was returned or if it's zero/null
if (-not $interval -or $interval -eq 0) {
    $interval = 5
    Write-Host "Interval not provided or invalid; defaulting to $interval seconds."
}

# Instead of instructing the user, open the browser to the verification_uri_complete
if ($verification_uri_complete) {
    Write-Host "Opening browser for device authorization..."
    Start-Process $verification_uri_complete
} else {
    Write-Host "verification_uri_complete not provided. Please manually go to $verification_uri and enter the code: $user_code"
}
  1. Démarrer une boucle qui envoie périodiquement une requête au point de terminaison du jeton avec le code appareil et l'ID client jusqu'à ce que le serveur retourne un jeton d'accès :

$startTime = Get-Date
$tokenResponse = $null

while (((Get-Date) - $startTime).TotalSeconds -lt $expires_in) {
    Start-Sleep -Seconds $interval

    try {# Build the POST body to exchange the device code for an access token
        $tokenBody = "grant_type=urn:ietf:params:oauth:grant-type:device_code&client_id=$clientId&device_code=$device_code"
        $tokenResponse = Invoke-RestMethod -Method Post -Uri $tokenEndpoint -ContentType "application/x-www-form-urlencoded" -Body $tokenBody

        if ($tokenResponse.access_token) {
            Write-Host "Access token obtained:" $tokenResponse.access_token
            break
        }
    }
    catch {# Instead of reading the response content (which may be disposed), use the exception message.
        $errorMessage = $_.Exception.Message

        # Check if the exception message indicates that authorization is still pending.
        if ($errorMessage -match "authorization_pending") {
            Write-Host "Authorization pending..."
            continue
        }
        else {
            Write-Error "Error during token polling: $errorMessage"
            break
        }
    }
}

if (-not $tokenResponse -or -not $tokenResponse.access_token) {
    Write-Host "Failed to obtain an access token or authorization expired."
}
  1. Lorsque nécessaire, utiliser le jeton de rafraîchissement obtenu lors de l'étape #1 pour demander un nouveau jeton via le point de terminaison du jeton, garantissant un accès continu à l'application :

$body = "grant_type=refresh_token&authorization=bearer $($tokenResponse.access_token)&refresh_token=$($tokenResponse.refresh_token)&client_id=dvls"

try {
    $refreshResponse = Invoke-RestMethod -Method Post -Uri $tokenEndpoint -ContentType "application/x-www-form-urlencoded" -Body $body

    if ($refreshResponse.access_token) {
        Write-Host "Access token obtained:" $tokenResponse.access_token
        break
    }
} catch {
    Write-Error "Failed to obtain device code: $_"
    exit
}

Voir la documentation d'Okta pour plus d'informations sur le flux d'autorisation de l'appareil.

Voir aussi

Devolutions Forum logo Partagez vos commentaires