Skip to content

Configuring OpenID Connect for the Admin Portal

To authenticate users using an external identity provider, we provide support for OpenID Connect (abbreviated to OIDC). On top of the standard OIDC capabilities, we provide a simple custom authorization method that relies on Django groups.

Scope

This document covers all the fields required to get Authentication and Authorization to work in the Admin via OIDC. It is required that you already have an identity provider (also known as IDP, OpenID Provider, or OP) setup.

Identity Provider Setup

Configuration of an identity provider varies on your provider of choice and is not covered in this document.

When your identity provider asks for a callback URL, use https://<Admin Portal URL>/oidc/callback/ where the URL is the domain the client (the browser) uses to reach the Admin Portal.

Configuration

Here's a settings snippet that defines a full OIDC configuration using example.powerdns.com as an identity provider. We will describe the fields in the next subsections.

PF_OIDC_ENABLED = True

OIDC_OP_AUTHORIZATION_ENDPOINT = 'https://example.powerdns.com/auth/authorization'
OIDC_OP_TOKEN_ENDPOINT = 'https://example.powerdns.com/auth/token'
OIDC_OP_USER_ENDPOINT = 'https://example.powerdns.com/auth/userinfo'
OIDC_OP_JWKS_ENDPOINT = 'https://example.powerdns.com/auth/jwks'

OIDC_RP_SCOPES = 'openid email'
OIDC_RP_CLIENT_ID = 'givenByIDP_54309563'
OIDC_RP_CLIENT_SECRET = 'g1v3nBy1DP'
OIDC_RP_SIGN_ALGO = 'RS256'

PF_OIDC_EMAIL_FALLBACK_CLAIM = None
PF_OIDC_ROLES_CLAIM = 'roles'
PF_OIDC_ROLES_MAP = {
    'idp-role': 'django-group',
    'other-idp-role': 'other-django-group',
}
PF_OIDC_STAFF_ROLES = ['idp-staff-role']
PF_OIDC_SUPERUSER_ROLES = ['idp-superuser-role']

Authentication

Authentication with OIDC leverages the mozilla-django-oidc Python package. This section covers the fields required for a minimal secure configuration, you may find more fields to fine-tune the settings to your identity provider in the official package documentation.

Note that some identity providers may only issue the required endpoints through discovery endpoint. In that case, you will need to fetch the discovery endpoint by hand and find the desired endpoints in the JSON response.

  • OIDC_OP_AUTHORIZATION_ENDPOINT points to the authorization endpoint.
  • OIDC_OP_TOKEN_ENDPOINT points to the identity provider token endpoint.
  • OIDC_OP_USER_ENDPOINT points to where the authentication backend will fetch user information.
  • OIDC_OP_JWKS_ENDPOINT points to the JWKS endpoint exposed by the identity provider.
    • It not required in the case of symetric encryption, though asymetric encryption should be prefered in production.
    • An alternative to this field is to provide a signing key in PEM or DER format under the field OIDC_RP_IDP_SIGN_KEY.
    • See OIDC_RP_SIGN_ALGO below to define which encryption method to use.
  • OIDC_RP_SCOPES defines the OIDC 'scope' that we require.
    • Those are space-separated values.
    • openid and email are the default values. It should be enough.
  • OIDC_RP_CLIENT_ID is issued by the identity provider to identify the Admin Portal.
  • OIDC_RP_CLIENT_SECRET is also issued by the identity provider.
  • OIDC_RP_SIGN_ALGO defines the desired algorithm for encryption.
    • Your identity provider will determine which algorithms are available.
    • e.g. HS256 (symetric), RS256 (asymetric)
  • PF_OIDC_EMAIL_FALLBACK_CLAIM defines an optional top-level claim to use when the standard email claim is missing, null or empty. It defaults to None (no fallback).
    • A populated standard email claim always takes precedence. Otherwise, the fallback value is copied into email before claims verification, user lookup and user creation. If a fallback is configured but neither claim has a populated value, authentication fails.
    • For example, if your identity provider supplies a custom_email claim, set PF_OIDC_EMAIL_FALLBACK_CLAIM = 'custom_email'.
    • The selected value is stored as the user's email and used to match existing accounts. Choose a unique, stable fallback value; it may not be a deliverable email address. If the standard email claim becomes available later with a different value, login can create a separate account.

Authorization

With OIDC, Authorization, that is user permissions, are issued through groups. Those groups must be defined using an existing Admin Portal user with sufficient rights, and associated with permissions.

In order to assign a user to groups, we expect the identity provider to provide a list of roles, that we match with local groups.

Roles may change over time and those changes will be matched in the Admin. For example, removal of a role that appears in PF_OIDC_ROLES_MAP, PF_OIDC_STAFF_ROLES or PF_OIDC_SUPERUSER_ROLES will trigger removal of the user from the associated group, or remove staff or superuser privileges.

Note that for a user to access the Admin GUI, it must have a staff role.

  • PF_OIDC_ROLES_CLAIM defines the name of the OIDC claim that provides the array of roles associated to the user.
    • A claim is a top-level key in the JSON passed through tokens and userinfo.
    • Some identity providers only allow a fixed claim name; others allow custom claims.
  • PF_OIDC_ROLES_MAP is a dict that maps IDP roles to group names.
    • Keys of the map are the roles that we desire to map to a group.
    • Unknown roles are ignored.
  • PF_OIDC_STAFF_ROLES list all the IDP roles that will set the is_staff flag on the Django user.
    • Without this flag, a user will only be able to connect with OIDC. Access to the Admin GUI will be forbidden.
  • PF_OIDC_SUPERUSER_ROLES list all the IDP roles that will set the is_superuser flag on the Django user.
    • Superusers have heightened privileges that may not be desired in production, and a non-OIDC superuser may be preferred for those administration tasks.