1 /*******************************************************************************
2 * ============LICENSE_START====================================================
4 * * ===========================================================================
5 * * Copyright © 2017 AT&T Intellectual Property. All rights reserved.
6 * * ===========================================================================
7 * * Licensed under the Apache License, Version 2.0 (the "License");
8 * * you may not use this file except in compliance with the License.
9 * * You may obtain a copy of the License at
11 * * http://www.apache.org/licenses/LICENSE-2.0
13 * * Unless required by applicable law or agreed to in writing, software
14 * * distributed under the License is distributed on an "AS IS" BASIS,
15 * * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * * See the License for the specific language governing permissions and
17 * * limitations under the License.
18 * * ============LICENSE_END====================================================
21 ******************************************************************************/
23 package org.onap.aaf.cadi.cm.test;
25 import static org.junit.Assert.assertThat;
26 import static org.junit.Assert.fail;
27 import static org.hamcrest.CoreMatchers.is;
28 import static org.hamcrest.CoreMatchers.nullValue;
29 import static org.mockito.Mockito.when;
30 import static org.mockito.Mockito.anyInt;
31 import static org.mockito.Mockito.anyString;
33 import org.junit.After;
34 import org.junit.Before;
35 import org.junit.Test;
36 import org.mockito.Mock;
37 import org.mockito.MockitoAnnotations;
39 import java.io.BufferedReader;
41 import java.io.FileInputStream;
42 import java.io.FileReader;
43 import java.io.IOException;
44 import java.io.PrintWriter;
45 import java.nio.charset.StandardCharsets;
46 import java.security.cert.Certificate;
47 import java.security.cert.CertificateEncodingException;
48 import java.security.cert.CertificateException;
49 import java.security.cert.X509Certificate;
50 import java.security.KeyPair;
51 import java.security.Principal;
52 import java.security.PrivateKey;
53 import java.security.PublicKey;
54 import java.util.ArrayList;
55 import java.util.Collection;
56 import java.util.List;
58 import javax.crypto.Cipher;
60 import org.onap.aaf.cadi.configure.CertException;
61 import org.onap.aaf.cadi.configure.Factory;
62 import org.onap.aaf.cadi.configure.Factory.Base64InputStream;
63 import org.onap.aaf.cadi.configure.Factory.StripperInputStream;
64 import org.onap.aaf.misc.env.Env;
65 import org.onap.aaf.misc.env.LogTarget;
66 import org.onap.aaf.misc.env.TimeTaken;
67 import org.onap.aaf.misc.env.Trans;
69 public class JU_Factory {
71 private static final String message = "The quick brown fox jumps over the lazy dog.";
72 private static final String subjectDNText = "subjectDN";
73 private static final String certText = "Some text that might be included in a certificate";
74 private static final String resourceDirName = "src/test/resources";
76 private File resourceDir;
77 private File publicKeyFile;
78 private File privateKeyFile;
79 private File certFile;
81 @Mock private Trans transMock;
82 @Mock private TimeTaken timeTakenMock;
83 @Mock private LogTarget logTargetMock;
84 @Mock private X509Certificate x509CertMock;
85 @Mock private Certificate certMock;
86 @Mock private Principal subjectDN;
90 public void setup() throws CertificateEncodingException {
91 MockitoAnnotations.initMocks(this);
93 resourceDir = new File(resourceDirName);
95 publicKeyFile = new File(resourceDirName, "/publicKey");
96 privateKeyFile = new File(resourceDirName, "/privateKey");
97 publicKeyFile.delete();
98 privateKeyFile.delete();
100 certFile = new File(resourceDirName + "/exampleCertificate.cer");
102 when(transMock.start(anyString(), anyInt())).thenReturn(timeTakenMock);
103 when(transMock.debug()).thenReturn(logTargetMock);
105 when(subjectDN.toString()).thenReturn(subjectDNText);
107 when(x509CertMock.getSubjectDN()).thenReturn(subjectDN);
108 when(x509CertMock.getEncoded()).thenReturn(certText.getBytes());
110 when(certMock.getEncoded()).thenReturn(certText.getBytes());
114 public void tearDown() {
115 publicKeyFile = new File(resourceDirName, "/publicKey");
116 privateKeyFile = new File(resourceDirName, "/privateKey");
117 publicKeyFile.delete();
118 privateKeyFile.delete();
122 public void generateKeyPairTest() throws Exception {
123 // This instatiation isn't actually necessary, but it gets coverage
124 Cipher encryptor = Factory.pkCipher();
125 Cipher decryptor = Factory.pkCipher();
127 KeyPair kp1 = Factory.generateKeyPair(transMock);
128 encryptor = Factory.pkCipher(kp1.getPublic(), true);
129 decryptor = Factory.pkCipher(kp1.getPrivate(), false);
130 byte[] encrypedMessage1 = encryptor.doFinal(message.getBytes(StandardCharsets.UTF_8));
131 String output1 = new String(decryptor.doFinal(encrypedMessage1));
132 assertThat(output1, is(message));
135 when(transMock.start("Generate KeyPair", Env.SUB)).thenReturn(null);
136 KeyPair kp2 = Factory.generateKeyPair(transMock);
137 encryptor = Factory.pkCipher(kp2.getPublic(), true);
138 decryptor = Factory.pkCipher(kp2.getPrivate(), false);
139 byte[] encrypedMessage2 = encryptor.doFinal(message.getBytes(StandardCharsets.UTF_8));
140 String output2 = new String(decryptor.doFinal(encrypedMessage2));
141 assertThat(output2, is(message));
143 KeyPair kp3 = Factory.generateKeyPair(null);
144 encryptor = Factory.pkCipher(kp3.getPublic(), true);
145 decryptor = Factory.pkCipher(kp3.getPrivate(), false);
146 byte[] encrypedMessage3 = encryptor.doFinal(message.getBytes(StandardCharsets.UTF_8));
147 String output3 = new String(decryptor.doFinal(encrypedMessage3));
148 assertThat(output3, is(message));
152 public void keyStringManipTest() throws Exception {
153 KeyPair kp = Factory.generateKeyPair(transMock);
155 String publicKeyString = Factory.toString(transMock, kp.getPublic());
156 String privateKeyString = Factory.toString(transMock, kp.getPrivate());
158 assertThat(publicKeyString.startsWith("-----BEGIN PUBLIC KEY-----"), is(true));
159 assertThat(publicKeyString.endsWith("-----END PUBLIC KEY-----\n"), is(true));
161 assertThat(privateKeyString.startsWith("-----BEGIN PRIVATE KEY-----"), is(true));
162 assertThat(privateKeyString.endsWith("-----END PRIVATE KEY-----\n"), is(true));
164 PublicKey publicKey = Factory.toPublicKey(transMock, publicKeyString);
165 PrivateKey privateKey = Factory.toPrivateKey(transMock, privateKeyString);
167 Cipher encryptor = Factory.pkCipher(publicKey, true);
168 Cipher decryptor = Factory.pkCipher(privateKey, false);
169 byte[] encrypedMessage = encryptor.doFinal(message.getBytes(StandardCharsets.UTF_8));
170 String output = new String(decryptor.doFinal(encrypedMessage));
171 assertThat(output, is(message));
175 public void keyFileManipTest() throws Exception {
176 KeyPair kp = Factory.generateKeyPair(transMock);
178 String privateKeyString = Factory.toString(transMock, kp.getPrivate());
179 writeToFile(privateKeyFile, privateKeyString, "Header:this line has a header");
181 PublicKey publicKey = kp.getPublic();
182 PrivateKey privateKey = Factory.toPrivateKey(transMock, privateKeyFile);
184 Cipher encryptor = Factory.pkCipher(publicKey, true);
185 Cipher decryptor = Factory.pkCipher(privateKey, false);
186 byte[] encrypedMessage = encryptor.doFinal(message.getBytes(StandardCharsets.UTF_8));
187 String output = new String(decryptor.doFinal(encrypedMessage));
188 assertThat(output, is(message));
192 public void certToStringTest() throws IOException, CertException, CertificateEncodingException {
194 when(logTargetMock.isLoggable()).thenReturn(true);
196 certString = Factory.toString(transMock, x509CertMock);
197 assertThat(certString.startsWith("-----BEGIN CERTIFICATE-----"), is(true));
198 assertThat(certString.endsWith("-----END CERTIFICATE-----\n"), is(true));
200 certString = Factory.toString(transMock, certMock);
201 assertThat(certString.startsWith("-----BEGIN CERTIFICATE-----"), is(true));
202 assertThat(certString.endsWith("-----END CERTIFICATE-----\n"), is(true));
205 certString = Factory.toString(transMock, (Certificate)null);
206 fail("Should have thrown an exception");
207 } catch (CertException e) {
208 assertThat(e.getMessage(), is("Certificate not built"));
211 when(certMock.getEncoded()).thenThrow(new CertificateEncodingException());
213 certString = Factory.toString(transMock, certMock);
214 fail("Should have thrown an exception");
215 } catch (CertException e) {
219 when(logTargetMock.isLoggable()).thenReturn(false);
220 certString = Factory.toString(transMock, x509CertMock);
224 public void toX509Test() throws CertificateException, IOException, CertException {
226 Collection<? extends Certificate> certs;
227 when(logTargetMock.isLoggable()).thenReturn(true);
229 String certString = readFromFile(certFile, false);
231 certs = Factory.toX509Certificate(certString);
232 // Contrived way of getting a Certificate out of a Collection
233 output = Factory.toString(transMock, certs.toArray(new Certificate[0])[0]);
234 assertThat(output, is(certString));
236 certs = Factory.toX509Certificate(transMock, certFile);
237 // Contrived way of getting a Certificate out of a Collection
238 output = Factory.toString(transMock, certs.toArray(new Certificate[0])[0]);
239 assertThat(output, is(certString));
241 List<String> certStrings = new ArrayList<>();
242 certStrings.add(certString);
243 certStrings.add(certString);
244 certs = Factory.toX509Certificate(certStrings);
245 // Contrived way of getting a Certificate out of a Collection
246 // it doesn't matter which one we get - they're the same
247 output = Factory.toString(transMock, certs.toArray(new Certificate[0])[0]);
248 assertThat(output, is(certString));
252 public void stripperTest() throws Exception {
253 KeyPair kp = Factory.generateKeyPair(transMock);
254 String privateKeyString = Factory.toString(transMock, kp.getPrivate());
255 writeToFile(privateKeyFile, privateKeyString, "Header:this line has a header");
257 StripperInputStream stripper = new StripperInputStream(privateKeyFile);
259 String expected = cleanupString(privateKeyString);
260 byte[] buffer = new byte[10000];
261 stripper.read(buffer);
262 String output = new String(buffer, 0, expected.length());
263 assertThat(output, is(expected));
267 stripper = new StripperInputStream(new FileInputStream(privateKeyFile));
269 stripper = new StripperInputStream(new BufferedReader(new FileReader(privateKeyFile)));
271 stripper.close(); // also coverage...
275 public void binaryTest() throws IOException {
276 String output = new String(Factory.binary(certFile));
277 String expected = readFromFile(certFile, true);
278 assertThat(output, is(expected));
282 public void signatureTest() throws Exception {
283 KeyPair kp = Factory.generateKeyPair(transMock);
284 String signedString = "Something that needs signing";
285 byte[] signedBytes = Factory.sign(transMock, signedString.getBytes(), kp.getPrivate());
286 String output = Factory.toSignatureString(signedBytes);
287 assertThat(output.startsWith("-----BEGIN SIGNATURE-----"), is(true));
288 assertThat(output.endsWith("-----END SIGNATURE-----\n"), is(true));
289 assertThat(Factory.verify(transMock, signedString.getBytes(), signedBytes, kp.getPublic()), is(true));
293 public void base64ISTest() throws Exception {
294 KeyPair kp = Factory.generateKeyPair(transMock);
296 String privateKeyString = Factory.toString(transMock, kp.getPrivate());
297 String cleaned = cleanupString(privateKeyString);
298 writeToFile(privateKeyFile, cleaned, null);
299 Base64InputStream b64is = new Base64InputStream(privateKeyFile);
300 byte[] buffer = new byte[10000];
304 FileInputStream fis = new FileInputStream(privateKeyFile);
305 b64is = new Base64InputStream(fis);
311 public void getSecurityProviderTest() throws CertException {
312 String[][] params = {
316 assertThat(Factory.getSecurityProvider("PKCS12", params), is(nullValue()));
319 private String cleanupString(String str) {
320 String[] lines = str.split("\n", 0);
321 List<String> rawLines = new ArrayList<>();
322 for (int i = 0; i < lines.length - 2; i++) {
323 rawLines.add(lines[i + 1]);
325 return join("", rawLines);
329 * Note: String.join is not part of JDK 7, which is what we compile to for CADI
331 private String join(String delim, List<String> rawLines) {
332 StringBuilder sb = new StringBuilder();
333 boolean first = true;
334 for(String s : rawLines) {
342 return sb.toString();
345 private void writeToFile(File file, String contents, String header) throws Exception {
346 PrintWriter writer = new PrintWriter(file, "UTF-8");
347 if (header != null) {
348 writer.println(header);
350 writer.println(contents);
354 private String readFromFile(File file, boolean addCR) throws IOException {
355 BufferedReader br = new BufferedReader(new FileReader(file));
356 StringBuilder sb = new StringBuilder();
358 while ((line = br.readLine()) != null) {
359 String lineEnd = (addCR) ? "\r\n" : "\n";
360 sb.append(line + lineEnd);
363 return sb.toString();