diff --git a/spring-credhub-core/src/main/java/org/springframework/credhub/configuration/SslCertificateUtils.java b/spring-credhub-core/src/main/java/org/springframework/credhub/configuration/SslCertificateUtils.java index ae8980d..50dc694 100644 --- a/spring-credhub-core/src/main/java/org/springframework/credhub/configuration/SslCertificateUtils.java +++ b/spring-credhub-core/src/main/java/org/springframework/credhub/configuration/SslCertificateUtils.java @@ -16,7 +16,6 @@ package org.springframework.credhub.configuration; -import javax.net.ssl.KeyManagerFactory; import javax.net.ssl.SSLContext; import javax.net.ssl.TrustManager; import javax.net.ssl.TrustManagerFactory; @@ -67,13 +66,10 @@ class SslCertificateUtils { SSLContext getSSLContext(String[] caCertFiles) { try { - KeyManagerFactory keyManagerFactory = createKeyManagerFactory(caCertFiles); TrustManagerFactory trustManagerFactory = createTrustManagerFactory(caCertFiles); SSLContext sslContext = SSLContext.getInstance("TLS"); - sslContext.init(keyManagerFactory.getKeyManagers(), - trustManagerFactory.getTrustManagers(), - null); + sslContext.init(null, trustManagerFactory.getTrustManagers(), null); return sslContext; } catch (GeneralSecurityException e) { @@ -100,27 +96,13 @@ class SslCertificateUtils { .getTrustManagers(); if (trustManagers.length != 1 || !(trustManagers[0] instanceof X509TrustManager)) { - throw new IllegalStateException("Unexpected default trust managers:" + throw new IllegalStateException("Unexpected default trust managers: " + Arrays.toString(trustManagers)); } return (X509TrustManager) trustManagers[0]; } - private KeyManagerFactory createKeyManagerFactory(String[] caCertFiles) { - try { - KeyStore keyStore = loadCertificateStore(caCertFiles); - - KeyManagerFactory keyManagerFactory = KeyManagerFactory - .getInstance(KeyManagerFactory.getDefaultAlgorithm()); - keyManagerFactory.init(keyStore, new char[0]); - - return keyManagerFactory; - } catch (GeneralSecurityException e) { - throw new IllegalStateException("Error creating KeyManagerFactory: " + e.getMessage(), e); - } - } - private KeyStore loadCertificateStore(String[] caCertFiles) { try { KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType()); @@ -139,7 +121,7 @@ class SslCertificateUtils { List certs = new ArrayList<>(); for (String fileName : caCertFiles) { BufferedInputStream bufferedStream = getFileStream(fileName); - certs.add(generateCertificate(fileName, bufferedStream)); + certs.addAll(generateCertificates(fileName, bufferedStream)); } return certs.toArray(new X509Certificate[0]); } @@ -149,15 +131,23 @@ class SslCertificateUtils { FileInputStream fileStream = new FileInputStream(new File(fileName)); return new BufferedInputStream(fileStream); } catch (FileNotFoundException e) { - throw new IllegalArgumentException("CA cert file not found: " + fileName, e); + throw new IllegalArgumentException("Certificate file not found: " + fileName, e); } } - private X509Certificate generateCertificate(String fileName, InputStream inputStream) { + private List generateCertificates(String fileName, InputStream inputStream) { + int minCertLength = ("-----BEGIN CERTIFICATE-----" + "-----END CERTIFICATE-----").length(); + try { - return (X509Certificate) CertificateFactory.getInstance("X.509") - .generateCertificate(inputStream); - } catch (CertificateException e) { + CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509"); + List certs = new ArrayList<>(); + + do { + certs.add((X509Certificate) certificateFactory.generateCertificate(inputStream)); + } while (inputStream.available() > minCertLength); + + return certs; + } catch (CertificateException | IOException e) { throw new IllegalStateException("Error reading certificate from file " + fileName + ": " + e.getMessage(), e); } @@ -165,12 +155,12 @@ class SslCertificateUtils { private void addCertsToCertificateStore(KeyStore keyStore, X509Certificate[] certs) { try { - int count = 0; for (X509Certificate cert : certs) { - keyStore.setCertificateEntry("" + count++, cert); + String alias = cert.getSubjectX500Principal().getName(); + keyStore.setCertificateEntry(alias, cert); } } catch (KeyStoreException e) { - throw new IllegalStateException("Error creating new truststore: " + e.getMessage(), e); + throw new IllegalStateException("Error creating new certificate store: " + e.getMessage(), e); } } } diff --git a/spring-credhub-core/src/main/java/org/springframework/credhub/core/permissionV2/CredHubPermissionV2Operations.java b/spring-credhub-core/src/main/java/org/springframework/credhub/core/permissionV2/CredHubPermissionV2Operations.java index a9ddc65..2e91018 100644 --- a/spring-credhub-core/src/main/java/org/springframework/credhub/core/permissionV2/CredHubPermissionV2Operations.java +++ b/spring-credhub-core/src/main/java/org/springframework/credhub/core/permissionV2/CredHubPermissionV2Operations.java @@ -46,6 +46,7 @@ public interface CredHubPermissionV2Operations { /** * Add permissions to an existing credential. * + * @param id the CredHub-assigned ID of the permission; must not be {@literal null} * @param path the path of the credentials; must not be {@literal null} * @param permission a permission to add * @return the details if the added permission diff --git a/spring-credhub-docs/build.gradle b/spring-credhub-docs/build.gradle index 62305b1..55bd95a 100644 --- a/spring-credhub-docs/build.gradle +++ b/spring-credhub-docs/build.gradle @@ -33,3 +33,5 @@ asciidoctor { 'nofooter': true, 'allow-uri-read': '' } + +configurations.archives.artifacts.clear() diff --git a/spring-credhub-docs/src/docs/asciidoc/boot-configuration.adoc b/spring-credhub-docs/src/docs/asciidoc/boot-configuration.adoc index f2620c4..edf886a 100644 --- a/spring-credhub-docs/src/docs/asciidoc/boot-configuration.adoc +++ b/spring-credhub-docs/src/docs/asciidoc/boot-configuration.adoc @@ -1,3 +1,6 @@ +:credhub-api-mtls: {credhub-api-home}version/2.0/#mutual-tls +:credhub-api-oauth: {credhub-api-home}version/2.0/#uaa-oauth2 + [[boot-configuration]] == Spring Boot Configuration @@ -6,7 +9,7 @@ With the proper configuration, Spring CredHub will auto-configure a connection t === Mutual TLS Authentication -An application running on Cloud Foundry can authenticate to a CredHub server deployed to the same platform using https://github.com/cloudfoundry-incubator/credhub/blob/master/docs/mutual-tls.md[mutual TLS]. +An application running on Cloud Foundry can authenticate to a CredHub server deployed to the same platform using mutual TLS. Mutual TLS is the default authentication scheme when no other authentication credentials are provided. To use mutual TLS authentication to a CredHub server, simply provide the URL of the CredHub server as an application property: @@ -15,6 +18,8 @@ To use mutual TLS authentication to a CredHub server, simply provide the URL of include::{examples-dir}/config-minimal.yml[] ---- +See the {credhub-api-mtls}[CredHub documentation] for more information on mutual TLS authentication. + An application running on Cloud Foundry can use the internal address `https://credhub.service.cf.internal:8844` to communicate with a CredHub server deployed to the same platform. === OAuth2 Authentication @@ -27,6 +32,7 @@ Spring CredHub supports client credentials grant tokens for authentication with include::{examples-dir}/config-oauth2.yml[] ---- -The OAuth2 client identified by the `client-id` must have CredHub scopes such as `credhub.read` or `credhub.write` to perform most operations. +The OAuth2 client identified by the `client-id` must have CredHub scopes such as `credhub.read` or `credhub.write` to perform most operations. +See the {credhub-api-oauth}[CredHub documentation] for more information on OAuth2 authentication with UAA. diff --git a/spring-credhub-docs/src/docs/asciidoc/getting-started.adoc b/spring-credhub-docs/src/docs/asciidoc/getting-started.adoc index 41d0f38..9fbd81d 100644 --- a/spring-credhub-docs/src/docs/asciidoc/getting-started.adoc +++ b/spring-credhub-docs/src/docs/asciidoc/getting-started.adoc @@ -7,7 +7,7 @@ This library is intended to provide full coverage of the CredHub API - all opera Spring CredHub has been optimized to work with Spring Boot applications. To include Spring CredHub in a Spring Boot application, add a dependency to the project build file. -=== Maven dependencies +=== Maven Dependencies Add the Spring CredHub starter to the `dependencies` section of the build file: @@ -19,7 +19,7 @@ Add the Spring CredHub starter to the `dependencies` section of the build file: -=== Gradle dependencies +=== Gradle Dependencies Add the Spring CredHub starter to the `dependencies` section of the build file: diff --git a/spring-credhub-docs/src/docs/asciidoc/index.adoc b/spring-credhub-docs/src/docs/asciidoc/index.adoc index dfdb034..8688f14 100644 --- a/spring-credhub-docs/src/docs/asciidoc/index.adoc +++ b/spring-credhub-docs/src/docs/asciidoc/index.adoc @@ -10,8 +10,9 @@ Scott Frederick; :examples-dir: ../../test/java/com/example/credhub/ :credhub-home: https://docs.cloudfoundry.org/credhub/ -:credhub-api: https://credhub-api.cfapps.io/ +:credhub-api-home: https://credhub-api.cfapps.io/ :cloudfoundry-home: https://www.cloudfoundry.org/ +:apidocs-home: https://docs.spring.io/spring-credhub/docs/{revnumber}/api/index.html (C) 2017-2018 The original authors. @@ -21,7 +22,7 @@ NOTE: _Copies of this document may be made for your own use and for distribution Spring CredHub provides client-side support for storing, retrieving, and deleting credentials from a {credhub-home}[CredHub] server running in a {cloudfoundry-home}[Cloud Foundry] platform. -CredHub provides an {credhub-api}[HTTP API] to securely store, generate, retrieve, and delete credentials of various types. Spring CredHub provides a Java binding for the CredHub API, making it easy to integrate Spring applications with CredHub. +CredHub provides an {credhub-api-home}[HTTP API] to securely store, generate, retrieve, and delete credentials of various types. Spring CredHub provides a Java binding for the CredHub API, making it easy to integrate Spring applications with CredHub. toc::[] diff --git a/spring-credhub-docs/src/docs/asciidoc/operations.adoc b/spring-credhub-docs/src/docs/asciidoc/operations.adoc index 205fb9a..6b89a07 100644 --- a/spring-credhub-docs/src/docs/asciidoc/operations.adoc +++ b/spring-credhub-docs/src/docs/asciidoc/operations.adoc @@ -1,15 +1,21 @@ +:apidocs-credentials: {apidocs-home}?org/springframework/credhub/core/credential/CredHubCredentialOperations.html +:apidocs-certificates: {apidocs-home}?org/springframework/credhub/core/certificate/CredHubCertificateOperations.html +:apidocs-permissions: {apidocs-home}?org/springframework/credhub/core/permission/CredHubPermissionOperations.html +:apidocs-permissionsV2: {apidocs-home}?org/springframework/credhub/core/permissionV2/CredHubPermissionV2Operations.html +:apidocs-interpolation: {apidocs-home}?org/springframework/credhub/core/interpolation/CredHubInterpolationOperations.html +:apidocs-info: {apidocs-home}?org/springframework/credhub/core/info/CredHubInfoOperations.html + +:credhub-api-credentials: {credhub-api-home}version/2.0/#credentials +:credhub-api-certificates: {credhub-api-home}version/2.0/#certificates +:credhub-api-permissions: {credhub-api-home}version/1.9/#permissions +:credhub-api-permissionsV2: {credhub-api-home}version/2.0/#permissions +:credhub-api-interpolation: {credhub-api-home}version/2.0/#interpolate-endpoint +:credhub-api-info: {credhub-api-home}version/2.0/#get-version + [[operations]] == Introduction to CredHubOperations The interface `org.springframework.credhub.core.CredHubOperations` and the implementation `org.springframework.credhub.core.CredHubTemplate` are the central class in Spring CredHub. -A Spring bean of this type is created using Spring Boot auto-configuration when application properties are properly configured. -Application classes can autowire an instance of this bean to interact with a CredHub server. - -[source,java,%autofit] ----- -include::{examples-dir}/CredHubService.java[] ----- - `CredHubOperations` provides access to additional operations interfaces that model the full CredHub API: [source,java,%autofit] @@ -24,6 +30,11 @@ CredHubCredentialOperations credentials(); */ CredHubPermissionOperations permissions(); +/** + * Get the operations for adding, retrieving, and deleting credential permissions. + */ +CredHubPermissionV2Operations permissionsV2(); + /** * Get the operations for retrieving, regenerating, and updating certificates. */ @@ -40,4 +51,30 @@ CredHubInterpolationOperations interpolation(); CredHubInfoOperations info(); ---- +=== Mapping to CredHub API + +Each method of the `Operations` interfaces maps directly to one endpoint of the CredHub HTTP API. +The following table shows the mapping between the CredHub API and the appropriate Spring CredHub `Operations` interface. + +|======= +| {credhub-api-credentials}[CredHub Credentials API] | {apidocs-credentials}[CredHubCredentialOperations] +| {credhub-api-permissions}[CredHub Permissions API] (v1) | {apidocs-permissions}[CredHubPermissionOperations] +| {credhub-api-permissionsV2}[CredHub Permissions API] (v2) | {apidocs-permissionsV2}[CredHubPermissionV2Operations] +| {credhub-api-certificates}[CredHub Certificates API] | {apidocs-certificates}[CredHubCertificateOperations] +| {credhub-api-interpolation}[CredHub Interpolation API] | {apidocs-interpolation}[CredHubInterpolationOperations] +| {credhub-api-info}[CredHub Information API] | {apidocs-info}[CredHubInfoOperations] +|======= + +=== CredHubOperations Auto-configuration + +A `CredHubOperations` Spring bean is created using Spring Boot auto-configuration when application properties are properly configured. +Application classes can autowire an instance of this bean to interact with a CredHub server. + +[source,java,%autofit] +---- +include::{examples-dir}/CredHubService.java[] +---- + + +