Using APIM to Create a JWT Private Token

Using APIM to Create a JWT Private Token

I had a request from a supplier using a third-party for their ERP system, to provide a JWT Public/Private Key pair to be able to authenticate with their endpoints (REST and SOAP).  The requirement was for us to generate the public certificate for the third party system to configure in their system.  Then on every REST and SOAP request we would build the JWT token using the private key that would be used to authorise the request.

NOTE: The third party had specific requirements around what the public/private keys should contain, but the below steps can be modified quite simply to fulfil any systems requirements.

Solution: JWT Authorisation using an APIM Policy

The following steps to accomplish this were:

1. Generate the RSA private key in PEM format

openssl genrsa -out erpsystemname.key 2048
NOTE: There was no requirement to password protect the key

2. Create the self-signed X.509 public certificate using the private key generated above

openssl req -new -x509 -key erpsystemname.key -out erpsystemname.publickey.cer -days 3650
NOTE: The expiry was set to 10 years, this was only for dev purposes, an earlier expiry would be required on a production system and a process for the certificate to be rotated
You are prompted to enter the following certificate information:

  • Country Name (2 Letter code)
  • State or Province Name (full name)
  • Locality Name (eg, city)
  • Organization Name (eg, company)
  • Organizational Unit Name (eg, section)
  • Common Name (e. g, server FQON or YOUR name)
  • Email Address

3. Generate the private key certificate in a PKCS#12 format file (PFX/P12) using the private key that bundles both the private key and certificate into a single, password-protected file

openssl pkcs12 -export -out erpsystemname.pfx -inkey erpsystemname.key -in erpsystemname.publickey.cer

4. Add the private PFX certificate to KeyVault so that it can be added to APIM


It requires a password for creation in KeyVault for extra security, and I named with name “ERPSystemNamePrivateCertificate”:

The certificate will appear here, now to help retrieving the certificate within an APIM policy I manually add the Thumbprint as a Key Vault Secret:

Here is my secret, and I set the expiry for it to match the certificate expiry date:

5. Now in APIM I can add a Named Value referencing the Key Vault Secret containing the private key thumbprint

6. A secondary Named Value was created to store the JWT token expiry time in seconds that will be used in the APIM policy

Named Value Name: ERPSystemNameJWTExpiryInSeconds

7. Now add the certificate to APIM


8. APIM Policy

Everything is now configured so the only thing left is to create an APIM policy to generate the JWT token and use it to authenticate the API requests with the third party system.
The policy I have written to generate the token using the private certificate can only retrieve the certificate using the Thumbprint, which will change when the Certificate in KeyVault is rotated:
context.Deployment.Certificates.TryGetValue(“D710G4G6DS56F3F7F7S3H8Y343D4C26CF95481DC”, out var certificate)
When I try to use the Id=”ERPSystemName” the code fails since it cannot locate the APIM Certificate – I think this is a bug or oversight by Microsoft, I have checked and there is no way to retrieve using the Id and here is a question I raised with a Microsoft response: retrieve-a-certificate-by-id-in-apim-policy
The answer suggests automating the update a KV secret or APIM Named Value with the new Thumbprint when the certificate is rotated.
The policy fragment, named: “erpsystemname-internal-proxy-authorisation”:

And each API call will have something like this:

NOTE: Basic authentication can be used instead if the variable flag “UseBasicAuthentication” is set to true and the variable “ERPSystemNamePassword” is set before running the fragment “erpsystemname-internal-proxy-authorisation”