Skip to content

Commit

Permalink
Update key vault readme (Azure#18971)
Browse files Browse the repository at this point in the history
  • Loading branch information
zhichengliu12581 authored Feb 19, 2021
1 parent c58542d commit 5e0d184
Show file tree
Hide file tree
Showing 25 changed files with 244 additions and 109 deletions.
266 changes: 157 additions & 109 deletions sdk/spring/azure-spring-boot-starter-keyvault-certificates/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,34 +20,86 @@ Azure Key Vault Certificates Spring Boot Starter is Spring starter for [Azure Ke
```
[//]: # ({x-version-update-end})

### Creating an Azure Key Vault

1. Log into <https://portal.azure.com>.

1. Click `Create a resource`.

1. Input `Key Vault`.

1. Click `Key Vault`
![Find Azure Key Vault Resource 01](resource/creating-an-azure-key-vault-01.png)

![Find Azure Key Vault Resource 02](resource/creating-an-azure-key-vault-02.png)

1. Click **Create**.

![Create new Key Vault](resource/creating-an-azure-key-vault-03.png)

1. On the **Create key vault** page, input `Subscription`, `Resource group`, `Key vault name` and `Pricing tier`, then click `Review + Create`.

![Specify the options](resource/specify-the-options.png)

![Create Key Vault resource](resource/create-key-vault-resource.png)

1. When complete, click `Go to resource`.

![Go to resource](resource/go-to-resource.png)

1. When the page for your app registration appears, copy your **Vault URI**;

![Save vault uri](resource/save-vault-uri.png)

1. Click **Certificates** in the left navigation pane. Then click **Generate/Import**.

![Create Certificates](resource/create-certificates.png)

1. Enter a **Certificates name**, and enter a **Subject** like `CN=mydomain.com`. then click **create**.

![Specify Certificates Info](resource/specify-certificates-info.png)

1. After the certificate is successfully created, it takes a while for the status to become `Enabled`. You can click **refresh** to check current status.

![Check Certificates status](resource/check-certificates-status.png)

## Key concepts
This starter is based on a JCA Provider for Azure Key Vault which is a JCA provider for certificates in
Azure Key Vault. It is built on four principles:

1. Must be extremely thin to run within a JVM.
1. Must not introduce any library version conflicts with Java app code dependencies.
1. Must not introduce any class loader hierarchy conflicts with Java app code dependencies.
1. Must be ready for "never trust, always verify and credential-free" Zero Trust environments.
This starter allows you to securely manage and tightly control your certificates by using Azure Key Vault or side-load certificates by supplying them as part of the application.

## Examples
### Server side SSL

#### Using a managed identity
#### Using a client ID and client secret

To use the starter for server side SSL, you will need to add the following to
your `application.properties` (if the application is using Spring Cloud Config
Server for its configuration add it to the `bootstrap.yml` of the application)
1. Click **Show portal menu**

```
azure.keyvault.uri=<the URI of the Azure Key Vault to use>
server.ssl.key-alias=<the name of the certificate in Azure Key Vault to use>
server.ssl.key-store-type=AzureKeyVault
```
2. Click **Azure Active Directory**.

Note: make sure the managed identity has access to the Azure Key Vault to access
keys, secrets and certificates.
![Select Azure Active Directory](resource/select-azure-active-directory.png)

#### Using a client ID and client secret
1. From the portal menu, Click **App registrations**,

1. Click **New registration**.

![New registration](resource/new-registration.png)

1. Specify your application, and then Click **Register**.

![Specify application](resource/specify-application.png)

1. When the page for your app registration appears, copy your **Application ID** and the **Tenant ID**;

![Get info for app](resource/get-info-for-app.png)

1. Click **Certificates & secrets** in the left navigation pane. Then click **New client secret**.

1. Add a **Description** and click duration in the **Expires** list. Click **Add**. The value for the key will be automatically filled in.

![Create secrets](resource/create-secrets.png)

1. Copy and save the value of the client secret. (You will not be able to retrieve this value later.)

![Copy secrets](resource/copy-secrets.png)

To use the starter for server side SSL, you will need to add the following to
your `application.properties` (if the application is using Spring Cloud Config
Expand All @@ -65,44 +117,44 @@ server.ssl.key-store-type=AzureKeyVault
Note: make sure the client ID has access to the Azure Key Vault to access
keys, secrets and certificates.

### Client side SSL
Follow the steps below to grant a client with access to Azure Key Vault to access keys, secrets and certificates.

1. Type your key vault name in **Search resources, services, and docs** and click your key vault created before.

![Back to key vault](resource/back-to-key-vault.png)

1. Click **Access policies** in the left navigation pane. Then click **Add Access Policy**.

![Add Access Policy](resource/add-access-policy.png)

1. Select **Key, Secret, &Certificate Management** as **Configure for template(optional)**. Permissions will be added automatically.

![Select configure](resource/select-configure.png)

1. Click **None selected** and choose application created before, click **Select**, then click **Add**.

![Choose application](resource/choose-application.png)

1. Click **Save**.

![Save Access Policy](resource/save-access-policy.png)

#### Using a managed identity

To use the starter for client side SSL, you will need to add the following to
To use the starter for server side SSL, you will need to add the following to
your `application.properties` (if the application is using Spring Cloud Config
Server for its configuration add it to the `bootstrap.yml` of the application)

```
azure.keyvault.uri=<the URI of the Azure Key Vault to use>
server.ssl.key-alias=<the name of the certificate in Azure Key Vault to use>
server.ssl.key-store-type=AzureKeyVault
```

Note: make sure the managed identity has access to the Azure Key Vault to access
keys, secrets and certificates.

If you are using `RestTemplate` use code similar to the example below.

```java
@Bean
public RestTemplate restTemplate() throws Exception {
KeyStore ks = KeyStore.getInstance("AzureKeyVault");
SSLContext sslContext = SSLContexts.custom()
.loadTrustMaterial(ks, new TrustSelfSignedStrategy())
.build();

SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext);

CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();

HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();

requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
return restTemplate;
}
```
### Client side SSL

#### Using a client ID and client secret

Expand All @@ -123,28 +175,67 @@ keys, secrets and certificates.
Then if you are using `RestTemplate` use the code below as a starting
point:

<!-- embedme ../azure-spring-boot/src/samples/java/com/azure/spring/keyvault/KeyVaultJcaClientSample.java#L21-L41 -->
```java
@Bean
public RestTemplate restTemplate() throws Exception {
KeyStore ks = KeyStore.getInstance("AzureKeyVault");
SSLContext sslContext = SSLContexts.custom()
.loadTrustMaterial(ks, new TrustSelfSignedStrategy())
.build();

HostnameVerifier allowAll = (String hostName, SSLSession session) -> true;
SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext, allowAll);

CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();

HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();

requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
return restTemplate;
}
```

#### Using a managed identity

To use the starter for client side SSL, you will need to add the following to
your `application.properties` (if the application is using Spring Cloud Config
Server for its configuration add it to the `bootstrap.yml` of the application)

```
azure.keyvault.uri=<the URI of the Azure Key Vault to use>
```
Note: make sure the managed identity has access to the Azure Key Vault to access
keys, secrets and certificates.

If you are using `RestTemplate` use code similar to the example below.

<!-- embedme ../azure-spring-boot/src/samples/java/com/azure/spring/keyvault/KeyVaultJcaManagedIdentitySample.java#L19-L38 -->
```java
@Bean
public RestTemplate restTemplate() throws Exception {
KeyStore ks = KeyStore.getInstance("AzureKeyVault");
SSLContext sslContext = SSLContexts.custom()
.loadTrustMaterial(ks, new TrustSelfSignedStrategy())
.build();

HostnameVerifier allowAll = (String hostName, SSLSession session) -> true;
SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext, allowAll);

CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();

HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();

requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
return restTemplate;
}
@Bean
public RestTemplate restTemplate() throws Exception {
KeyStore ks = KeyStore.getInstance("AzureKeyVault");
SSLContext sslContext = SSLContexts.custom()
.loadTrustMaterial(ks, new TrustSelfSignedStrategy())
.build();

SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext);

CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();

HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();

requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
return restTemplate;
}
```

### Configuring Spring Cloud Gateway
Expand Down Expand Up @@ -186,49 +277,6 @@ spring:
useInsecureTrustManager: true
```
### Creating an Azure Key Vault
To create an Azure Key Vault use the command line below:
```shell
export KEY_VAULT=mykeyvault
export RESOURCE_GROUP=myresourcegroup
az keyvault create --name ${KEY_VAULT} -g ${RESOURCE_GROUP}
```

### Create a self-signed certificate

To create a self-signed certificate use the command line below:

```shell
export CERTIFICATE_ALIAS=self-signed
az keyvault certificate create --vault-name ${KEY_VAULT} \
-n ${CERTIFICATE_ALIAS} -p "$(az keyvault certificate get-default-policy)"
```

### Assign a managed identity (to an Azure Spring Cloud application)

To assign a managed identity use the command line below:

```shell
export SPRING_CLOUD_APP=myspringcloudapp
az spring-cloud app identity assign --name ${SPRING_CLOUD_APP}
export MANAGED_IDENTITY=$(az spring-cloud app show \
--name ${SPRING_CLOUD_APP} --query identity.principalId --output tsv)
```

### Grant a managed identity with access to Azure Key Vault

To grant access use the command line below:

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

### Side-loading certificates
This starter allows you to side-load certificates by supplying them as part of
Expand Down
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
6 changes: 6 additions & 0 deletions sdk/spring/azure-spring-boot/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,12 @@
<artifactId>spring-core</artifactId>
<version>5.2.10.RELEASE</version> <!-- {x-version-update;org.springframework:spring-core;external_dependency} -->
</dependency>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>4.5.13</version> <!-- {x-version-update;org.apache.httpcomponents:httpclient;external_dependency} -->
<scope>test</scope>
</dependency>
</dependencies>

<build>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
package com.azure.spring.keyvault;

import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.ssl.SSLContexts;
import org.springframework.context.annotation.Bean;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.web.client.RestTemplate;
import org.apache.http.conn.ssl.TrustSelfSignedStrategy;

import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import java.security.KeyStore;

public class KeyVaultJcaClientSample {

@Bean
public RestTemplate restTemplate() throws Exception {
KeyStore ks = KeyStore.getInstance("AzureKeyVault");
SSLContext sslContext = SSLContexts.custom()
.loadTrustMaterial(ks, new TrustSelfSignedStrategy())
.build();

HostnameVerifier allowAll = (String hostName, SSLSession session) -> true;
SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext, allowAll);

CloseableHttpClient httpClient = HttpClients.custom()
.setSSLSocketFactory(csf)
.build();

HttpComponentsClientHttpRequestFactory requestFactory =
new HttpComponentsClientHttpRequestFactory();

requestFactory.setHttpClient(httpClient);
RestTemplate restTemplate = new RestTemplate(requestFactory);
return restTemplate;
}
}
Loading

0 comments on commit 5e0d184

Please sign in to comment.