/*- * -\-\- * docker-client * -- * Copyright (C) 2017 Spotify AB * -- * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * -/-/- */ package com.spotify.docker.client; import static org.hamcrest.Matchers.is; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertThat; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verify; import com.google.common.base.Optional; import com.google.common.io.Resources; import com.spotify.docker.client.DockerCertificates.SslContextFactory; import com.spotify.docker.client.exceptions.DockerCertificateException; import java.nio.file.Path; import java.nio.file.Paths; import java.security.KeyStore; import org.junit.Test; import org.mockito.ArgumentCaptor; public class DockerCertificatesTest { private SslContextFactory factory = mock(SslContextFactory.class); private ArgumentCaptor<KeyStore> keyStore = ArgumentCaptor.forClass(KeyStore.class); private ArgumentCaptor<KeyStore> trustStore = ArgumentCaptor.forClass(KeyStore.class); private ArgumentCaptor<char[]> password = ArgumentCaptor.forClass(char[].class); @Test(expected = DockerCertificateException.class) public void testBadDockerCertificates() throws Exception { // try building a DockerCertificates with specifying a cert path to something that // isn't a cert DockerCertificates.builder() .dockerCertPath(getResourceFile("dockerInvalidSslDirectory")) .build(); } @Test public void testNoDockerCertificatesInDir() throws Exception { final Path certDir = Paths.get(System.getProperty("java.io.tmpdir")); final Optional<DockerCertificatesStore> result = DockerCertificates.builder() .dockerCertPath(certDir) .build(); assertThat(result.isPresent(), is(false)); } @Test public void testDefaultDockerCertificates() throws Exception { DockerCertificates.builder() .dockerCertPath(getCertPath()) .sslFactory(factory) .build(); verify(factory).newSslContext(keyStore.capture(), password.capture(), trustStore.capture()); final KeyStore.PrivateKeyEntry pkEntry = (KeyStore.PrivateKeyEntry) keyStore.getValue() .getEntry("key", new KeyStore.PasswordProtection(password.getValue())); final KeyStore caKeyStore = trustStore.getValue(); assertNotNull(pkEntry); assertNotNull(pkEntry.getCertificate()); assertNotNull(caKeyStore.getCertificate("o=boot2docker")); } @Test public void testDockerCertificatesWithMultiCa() throws Exception { DockerCertificates.builder() .dockerCertPath(getCertPath()) .caCertPath(getVariant("ca-multi.pem")) .sslFactory(factory) .build(); verify(factory).newSslContext(keyStore.capture(), password.capture(), trustStore.capture()); final KeyStore.PrivateKeyEntry pkEntry = (KeyStore.PrivateKeyEntry) keyStore.getValue() .getEntry("key", new KeyStore.PasswordProtection(password.getValue())); assertNotNull(pkEntry); assertNotNull(pkEntry.getCertificate()); assertNotNull(trustStore.getValue().getCertificate( "cn=ca-test,o=internet widgits pty ltd,st=some-state,c=cr")); assertNotNull(trustStore.getValue().getCertificate( "cn=ca-test-2,o=internet widgits pty ltd,st=some-state,c=cr")); } @Test public void testReadPrivateKeyPkcs1() throws Exception { DockerCertificates.builder() .dockerCertPath(getCertPath()) .clientKeyPath(getVariant("key-pkcs1.pem")) .sslFactory(factory) .build(); verify(factory).newSslContext(keyStore.capture(), password.capture(), trustStore.capture()); final KeyStore.PrivateKeyEntry pkEntry = (KeyStore.PrivateKeyEntry) keyStore.getValue() .getEntry("key", new KeyStore.PasswordProtection(password.getValue())); assertNotNull(pkEntry.getPrivateKey()); } @Test public void testReadPrivateKeyPkcs8() throws Exception { DockerCertificates.builder() .dockerCertPath(getCertPath()) .clientKeyPath(getVariant("key-pkcs8.pem")) .sslFactory(factory) .build(); verify(factory).newSslContext(keyStore.capture(), password.capture(), trustStore.capture()); final KeyStore.PrivateKeyEntry pkEntry = (KeyStore.PrivateKeyEntry) keyStore.getValue() .getEntry("key", new KeyStore.PasswordProtection(password.getValue())); assertNotNull(pkEntry.getPrivateKey()); } private Path getResourceFile(String path) { return Paths.get(Resources.getResource(path).getPath()); } private Path getCertPath() { return getResourceFile("dockerSslDirectory"); } private Path getVariant(String filename) { return getResourceFile("dockerSslVariants").resolve(filename); } }