Scaling Microservices Part 3 - Passport Pattern
Many systems consist of tens- or hundreds of services, each providing different functionality. To deliver a given functionality, one service often needs to call n-number of other services. All of these services often depend on common data that must be retrieved from other services. This leads to a complex call hierarchy and potential performance issues, as seen in the diagram below.
Various methods and patterns can be used to solve this problem; in this part, we will see how the passport pattern can be used to solve it.
What Is the Passport Pattern?
The passport pattern is a method where an edge component, like the API Gateway or the topmost service in the call chain, calls one or more services to get the commonly used data across all the different services. In the diagram above, user profile and authorization data are common data used by all the services. These data can then be passed along to the underlying services as part of the request payload. The services can then use the data from the request instead of getting the data from service calls.
Authentication Token vs Passport Token
Authentication tokens are often issued by third-party identity services and are stored in browser cookies. They usually only contain a subset of the data in a passport token. The passport token is only available server side. It can contain sensitive data and isn't limited to identity data; it can have any data.
Things to Consider
When using the passport pattern, there are some things that you need to decide on:
- What token type to use
- What token signing algorithm to use
- How to transfer the passport token between services
- What component should create the passport token
#1 - What Token Type to Use
JSON Web Token (JWT) is a suitable token type for the passport token. It consists of a JSON payload together with a signature.
#2 - What Token Signing Algorithm to Use
A JWT can be signed using a private secret or a public/private key.
Using a private secret (symmetric) signing algorithm like HS256 is faster, but the private secret must be shared with both the service creating the JWT and the services validating it.
A public/private (asymmetric) key-based signing algorithm like RS256 or ES256 is slower but still preferred in most situations. By using this, only the service responsible for creating the JWT will have access to the private key. The other services will only have access to the public key, which they can use to validate the token.
#3 - How to Transfer the Passport Token Between Services
The passport token can be transferred using the HTTP request header.
#4 - What Component Should Create the Passport Token
Various components and services can create the passport token:
- Edge components like the API Gateway.
- The topmost service in the call stack.
- The Token / Identity Service (STS).
- The services providing common data.
- A new new Common Data Service.
- The passport token creation logic doesn't have to be duplicated; it's in a single place and can be easily modified. However, if there is a breaking change, the services must still be updated to understand the changes.
- It can be more complex to add logic to edge components than to application components.
- Most developers don't run edge components locally on their development machines. Due to this, the passport token won't be sent along locally.
- Some trust their edge components less than their services.
The Topmost Service
- Easy to add things to the application code.
- Will work on local development machines since the service will create the token.
- Systems have many services. To prevent duplication of the passport creation logic, a shared library must be made, kept up to date, and used by all the services. However, this library should be made anyway to ensure that the services share a common way to read and validate the passport token.
The Token Service
- The services usually already have a JWT used for authentication. If the Token Service generates the passport token, then a token with both the identity and the common data can be made. Instead of transferring multiple tokens to the services, one token can be sent along.
- If the common data is unrelated to identity, it might not be architecturally right for the Token Service to have this responsibility.
The Services Providing Common Data
- The private key is moved from the API Gateway or topmost service to the common data services.
- Multiple private/public keys can be used if needed.
- The services need to validate and read data from multiple tokens: the authentication token and 2 passport tokens (user profile JWT and authorization JWT).
A New Common Data Service
A new Common Data Service can be made that provides the common passport data by calling the other services common data services.
- Will get a single passport token instead of multiple tokens.
- The private key is moved from the API Gateway or topmost service to the Common Data Service.
- Performance overhead if the new service must call the other common data sources, unless other scaling techniques are used in addition.
The passport pattern can help with scaling your microservices. It can be used in various ways, and you need to select the method and variation that match your needs and requirements.