top of page
Search
  • admin

Generate JSON Web Key from a PKCS#12 X509Certificate

In my recent project, we needed to generate JSON Web Key (JWK) containing the public key of an X509Certificate using RSA256 signing algorithm of 2048 key size.


Here is just a small piece of my discovery on how to extract the Modulus and Exponent of a public key for generating a JSON Web Key.


Create certificate in Azure Key Vault

We need a certificate to start with. The solution requires the certificate to be stored in Azure Key Vault. Creating one is a very straight forward process. Simply navigate to the Certificate section, and click on Generate/Import.

For demo purpose, I would just fill in the basic details, select PKCS#12 content type. Under Advanced Policy Configuration, select the RSA key type, and 2048 key size. Then, proceed to create the Certificate.


Generate JSON Web Key in C#

Now, we have a certificate to test with. In Visual Studio projects using either .NET Core 5.0 or Framework (version 4.7.2 at the time of writing), import the following NuGet packages:

  • Azure.Security.KeyVaults.Secret

  • Azure.Identity

  • Microsoft.IdentityModels.Tokens

Firstly, initiate connection to the Azure Key Vault, and retrieve the certificate content. I am using SecretClient instead of CertificateClient. You may use CertificateClient, however, it does not return the private key which, in this case, is fine as we don't need.


Then, initialise X509Certificate2 instance from the content, and extract the Modulus and Exponent of its public key to form the JSON Web Key.

//initialise the Secret client connection to Azure Key Vault.
var secretClient = new SecretClient(new Uri("https://ivsdev-mykeyvault.vault.azure.net/"), new DefaultAzureCredential());

//retrieve the certificate content to initialise the X509Certificate instance.
var secretValue = secretClient.GetSecret("MyFirstCertificate");
var certificateString = secretValue.Value.Value;            
var certificate = new X509Certificate2(Convert.FromBase64String(certificateString));            

//extract the RSA Public Key, and its parameters.
var publicKey = certificate.GetRSAPublicKey();
var param = publicKey.ExportParameters(false);

//extract and encode the Modulus and Exponent to Base64 string.
var modulus = Base64UrlEncoder.Encode(param.Modulus);
var exp = Base64UrlEncoder.Encode(param.Exponent);

//assign the parts to the JsonWebKey class.
var jsonwk = new JsonWebKey()
{
    Kty = "RSA",
    Use = "sig",
    Alg = "RS256",
    Kid = "some key id value",
    N = modulus,
    E = exp,
};

//or, simply use your own JSON model 
var myjsonwk = new MyJsonWebKey()
{
    kty = "RSA",
    use = "sig",
    alg = "RS256",
    kid = "some key id value",
    n = modulus,
    e = exp,
};

Microsoft has a JsonWebKey model, however, its serialised string contains other components which are causing problems in the consuming party in my project. So, I ended up creating my own model to fit the purpose, and for a cleaner JSON string.


That's all for now.

0 comments

Recent Posts

See All

Using FetchXmlBuilder to generate OData query

Quite often, we need to specify the attributes to select or the filter conditions on related entities in DataVerse connector in Microsoft Flow. Expand Query is exactly where we can specify those. Howe

Adding custom PCF control to Dynamics 365 CE form

PCF Gallery (https://pcf.gallery/) has a great list of PCF controls available to use - both free and payable controls. Once you have imported the solution to your Dynamics 365 environment, you have to

Comments


bottom of page