Setup OIDC Filter Chain
Last updated
Was this helpful?
Last updated
Was this helpful?
There are four main filters that can be used to construct an Open ID Connect (OIDC) filter chain:
This filter checks the existence of a request attribute (header, cookie, etc.) and will copy/move it to the next filter in the chain.
This filter does online validation of an access token by calling the /userinfo
endpoint. Note that the response of the /userinfo
API is JSON containing user info, not JSON Web Token (JWT) so if there is a need for an ID token, it needs to be acquired via OIDC Authentication filter.
The main filter that handles and will store access or ID tokens in specified locations.
This filter does offline verification of a JWT (e.g. ID token) using a specified JSON Web Key Set (JWKS). It verifies the signature, audience, and issuer as well as time restriction such as expiration and nbf (not before) time. If the verification fails, the request is rejected.
The following filters may appear required for our OAuth/OIDC flow but are used for very specific cases:
This is a legacy OAuth filter that requires openid
scope and id_token
.
This filter is tightly coupled with Grey Matter JWT Security service.
In this section, we'll cover the layout for a mesh which contains one Edge proxy, one web application with UI accessed via browsers, and one API service which return JSON responses to be consumed by frontend applications.
In a Grey Matter deployment this is simply our sidecar used for edge traffic. It allows all traffic to go through the specified Listeners into the OIDC filter chain.
OIDC Validation filter checks to see if a request contains an access token in a specified location.
If so, validate the token with Identity Provider (IdP) by calling the /userinfo
endpoint and optionally store the response JSON into a specified location. If validation fails, remove the access token from the request so that the following filter can process as if the request did not contain an access token.
Otherwise let the request go through.
OIDC Authentication Filter checks to see if a request contains an access token in a specified location
If so, there is nothing more to do.
Otherwise check whether an access code exists in this request.
If so, exchange the access code for a token with IdP.
Otherwise initiate the authentication process with IdP by redirecting the user to a login page.
Ensure Variables filter ensures that access tokens that are spread out across multiple request attributes, like a bearer token in a header, a cookie, etc., are moved to a consistent location. This alleviates the need for subsequent filters to check multiple request attributes. If a token is not found, the request is rejected.
OIDC Validation filter validates the token with IdP by calling the /userinfo
endpoint and optionally stores the response JSON into a specified location. If validation fails, the request is rejected.
The above implementation works for mesh with a small number of services. However, it requires each and every application/API listener to be aware of OIDC configuration which is cumbersome. The second implementation uses a "gateway" proxy which contains two separate listeners and domains - one for application route, the other for API service route.
It allows any traffic to go through, but using a string pattern match, it splits the traffic into two routes: one for /app
and the other for /services
, This edge proxy can certainly be omitted by a use of different subdomains/ports for application traffic and API traffic, etc.
Gateway proxy is an instance of the gm-proxy with two listeners and domains. Why two domains? Because a domain can be responsible for one port. When we "split" the traffic into two, /app
traffic gets directed to one port (e.g. 8080
) of the gateway proxy while /services
traffic goes to another port (e.g. 9080
).
This set of listener and domain is responsible for localhost:9443/app
traffic. The filters used by the listener are the same as the basic implementation's application sidecar listener.
This set of listener and domain is responsible for localhost:9443/services
traffic. The filters used by the listener are the same as the basic implementation's API service sidecar listener.
Online validation using OIDC Validation Filter adds an API call to IdP for every single request you serve. If you just need to quickly check whether an ID token (or any other JWT)'s signature, you can use Envoy JWT Authentication.
Carefully consider ways to reduce traffic back to IdP. Do static assets for the UI (CSS, images, etc) really need to be protected? Is there a way to cache the validation results so that we only need to ask IdP every 5 minutes, for example?