Current version is 2.6.0, click here for the index

Azure Key Vault JCA client library for Java

The JCA Provider for Azure Key Vault is a Java Cryptography Architecture provider for certificates in Azure Key Vault. It is built on four principles:

  1. Must be extremely thin to run within a JVM.
  2. Must not introduce any library version conflicts with Java app code dependencies.
  3. Must not introduce any class loader hierarchy conflicts with Java app code dependencies.
  4. Must be ready for "never trust, always verify and credential-free" Zero Trust environments.

[Source code] | [API reference documentation] | [Product documentation] | [Samples]

Getting started

Adding the package to your project

Maven dependency for the Azure Key Vault JCA client library. Add it to your project's POM file.

<dependency>
    <groupId>com.azure</groupId>
    <artifactId>azure-security-keyvault-jca</artifactId>
    <version>2.6.0</version>
</dependency>

Prerequisites

az keyvault create --resource-group <your-resource-group-name> --name <your-key-vault-name>

Key concepts

Examples

Server side SSL

If you are looking to integrate the JCA provider to create an SSLServerSocket see the example below.

KeyVaultJcaProvider provider = new KeyVaultJcaProvider();
Security.addProvider(provider);

KeyStore keyStore = KeyVaultKeyStore.getKeyVaultKeyStoreBySystemProperty();

KeyManagerFactory managerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
managerFactory.init(keyStore, "".toCharArray());

SSLContext context = SSLContext.getInstance("TLS");
context.init(managerFactory.getKeyManagers(), null, null);

SSLServerSocketFactory socketFactory = context.getServerSocketFactory();
SSLServerSocket serverSocket = (SSLServerSocket) socketFactory.createServerSocket(8765);

Note if you want to use Azure Managed Identity, you should set the value of azure.keyvault.uri, and the rest of the parameters would be null.

Client side SSL

If you are looking to integrate the JCA provider for client side socket connections, see the Apache HTTP client example below.

KeyVaultJcaProvider provider = new KeyVaultJcaProvider();
Security.addProvider(provider);

KeyStore keyStore = KeyVaultKeyStore.getKeyVaultKeyStoreBySystemProperty();

SSLContext sslContext = SSLContexts
    .custom()
    .loadTrustMaterial(keyStore, new TrustSelfSignedStrategy())
    .build();

SSLConnectionSocketFactory sslConnectionSocketFactory = new SSLConnectionSocketFactory(
    sslContext, (hostname, session) -> true);

PoolingHttpClientConnectionManager manager = new PoolingHttpClientConnectionManager(
    RegistryBuilder.<ConnectionSocketFactory>create()
        .register("https", sslConnectionSocketFactory)
        .build());

String result = null;

try (CloseableHttpClient client = HttpClients.custom().setConnectionManager(manager).build()) {
    HttpGet httpGet = new HttpGet("https://localhost:8766");
    ResponseHandler<String> responseHandler = (HttpResponse response) -> {
        int status = response.getStatusLine().getStatusCode();
        String result1 = "Not success";
        if (status == 204) {
            result1 = "Success";
        }
        return result1;
    };
    result = client.execute(httpGet, responseHandler);
} catch (IOException ioe) {
    ioe.printStackTrace();
}

Note if you want to use Azure managed identity, you should set the value of azure.keyvault.uri, and the rest of the parameters would be null.

File-System certificates

You can load the certificate in the file system as a trusted certificate by configure the following properties.

azure:
  cert-path:
    well-known:     # The file location where you store the well-known certificate
    custom:         # The file location where you store the custom certificate

Key-Less certificates

You can set the private key as [non-exportable] to ensure the security of the key.

Note if you want to use key less certificate, you must add sign permission.

You can add permission in portal:

Or add permission by cli command:

  az keyvault set-policy --name ${KEY_VAULT} \
        --object-id ${MANAGED_IDENTITY} \
        --key-permissions get list sign\
        --secret-permissions get list \
        --certificate-permissions get list

Please replace ${KEY_VAULT} with your key vault name and replace ${MANAGED_IDENTITY} with your principal's object-id.

Supported key type

Content Type | Key Type | Key Size or Elliptic curve name | Sign algorithm | Support | -------------|----------|---------------------------------|---------------- |-------- | PKCS #12 | RSA | 2048 | RSASSA-PSS | ✔ | PKCS #12 | RSA | 3072 | RSASSA-PSS | ✔ | PKCS #12 | RSA | 4096 | RSASSA-PSS | ✔ | PKCS #12 | EC | P-256 | SHA256withECDSA | ✔ | PKCS #12 | EC | P-384 | SHA384withECDSA | ✔ | PKCS #12 | EC | P-521 | SHA512withECDSA | ✔ | PKCS #12 | EC | P-256K | | ✘ | PEM | RSA | 2048 | RSASSA-PSS | ✔ | PEM | RSA | 3072 | RSASSA-PSS | ✔ | PEM | RSA | 4096 | RSASSA-PSS | ✔ | PEM | EC | P-256 | SHA256withECDSA | ✔ | PEM | EC | P-384 | SHA384withECDSA | ✔ | PEM | EC | P-521 | SHA512withECDSA | ✔ | PEM | EC | P-256K | | ✘ |

Troubleshooting

Configure logging

This module uses JUL (java.util.logging), so to configure things like the logging level you can directly modify the JUL configuration.

Here is an example of a logging.properties file:

# To enable this configuration file, please add this property:
# -Djava.util.logging.config.file="src/test/resources/logging.properties"
#
# The Java logging APIs (java.util.logging) default loads logging.properties from:
# 1. $JAVA_HOME/jre/lib/ (Java 8 and before)
# 2. $JAVA_HOME/conf/ (Java 9 and above)
#
# For more information about this file, please refer to:
# 1. https://docs.oracle.com/javase/8/docs/technotes/guides/logging/overview.html#a1.8
# 2. https://docs.oracle.com/cd/E23549_01/doc.1111/e14568/handler.htm

handlers = java.util.logging.ConsoleHandler
java.util.logging.ConsoleHandler.level = ALL
java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
java.util.logging.SimpleFormatter.format= [%1$tF %1$tT] %3 [%4$-7s] %5$s %n

.level = INFO
com.azure.security.keyvault.jca.level = ALL

General

Azure Key Vault JCA clients raise exceptions. For example, if you try to check a client's identity with a certificate chain that does not include a trusted certificate, a CertificateException will be thrown. In the following snippet, the error is handled gracefully by catching the exception and displaying additional information about the error.

try {
    KeyVaultJcaProvider provider = new KeyVaultJcaProvider();
    Security.addProvider(provider);
    ...
    // Start SSL server socket
    ...
} catch (CertificateException e) {
    System.out.println(e.getMessage());
}

Next steps

Spring Boot

For Spring Boot applications see our Spring Boot starter.

References

  1. Java Cryptography Architecture (JCA) Reference Guide

Additional documentation

For more extensive documentation on Azure Key Vault, see the [API reference documentation].

Contributing

This project welcomes contributions and suggestions. Most contributions require you to agree to a Contributor License Agreement (CLA) declaring that you have the right to, and actually do, grant us the rights to use your contribution. For details, visit https://cla.microsoft.com.

When you submit a pull request, a CLA-bot will automatically determine whether you need to provide a CLA and decorate the PR appropriately (e.g., label, comment). Simply follow the instructions provided by the bot. You will only need to do this once across all repos using our CLA.

This project has adopted the Microsoft Open Source Code of Conduct. For more information see the Code of Conduct FAQ or contact opencode@microsoft.com with any additional questions or comments.

Packages 
Package Description
com.azure.security.keyvault.jca
The Azure Key Vault JCA Provider package.