authlib/loginpass

Azure's userinfo endpoint not working in v2

salty-horse opened this issue · 4 comments

When using v2 of the Azure API, in profile() it tries to call /openid/userinfo.

However, according to the passport-azure-ad node package (sorry, this is the best documentation I could find) userinfo does not work with v2, and one needs to extract that information from id_token.

These are the adaptations that need to be made for v2:

  1. JWK_SET_URL should be '{}{}/discovery/v2.0/keys' instead of '{}{}/discovery/keys'.
  2. The profile needs to be fetched by callingparse_openid, which extracts it from the id_token.
  3. For the above to work, iss claim validation needs to be disabled by calling create_azure_backend with claims_options={}. This is because Microsoft reports specifies its issuer is "https://login.microsoftonline.com/{tenantid}/v2.0", and expects you replace {tenantid} with the value they provide in the tid claim. Without this replacement, validation fails. For additional reference, here's a blog post that covers this issue.

@salty-horse can you send a PR for this issue?

Is it OK to remove the issuer validation? I'm not sure how to replace the tenant ID without modifying authlib code.

@salty-horse You can disable it by setting claims_options:

    "iss": {"essential": False},

However, according to your description, it seems you can use claims_options:

def validate_iss(claims, value):
    iss = "https://login.microsoftonline.com/{}/v2.0".format(claims['tid'])
    return iss == value

claims_options = {
    "iss": {"essential":  True, "validate": validate_iss},
}