Bump checkstyle version
[dcaegen2/collectors/hv-ves.git] / hv-collector-ssl / src / test / kotlin / org / onap / dcae / collectors / veshv / ssl / boundary / ServerSslContextFactoryTest.kt
1 /*
2  * ============LICENSE_START=======================================================
3  * dcaegen2-collectors-veshv
4  * ================================================================================
5  * Copyright (C) 2018 NOKIA
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
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
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=========================================================
19  */
20 package org.onap.dcae.collectors.veshv.ssl.boundary
21
22 import arrow.core.Some
23 import arrow.core.toOption
24 import io.netty.handler.ssl.ClientAuth
25 import io.netty.handler.ssl.JdkSslContext
26 import io.netty.handler.ssl.ReferenceCountedOpenSslContext
27 import io.netty.handler.ssl.SslContextBuilder
28 import org.assertj.core.api.Assertions
29 import org.assertj.core.api.Assertions.assertThat
30 import org.jetbrains.spek.api.Spek
31 import org.jetbrains.spek.api.dsl.describe
32 import org.jetbrains.spek.api.dsl.given
33 import org.jetbrains.spek.api.dsl.it
34 import org.jetbrains.spek.api.dsl.on
35 import org.onap.dcae.collectors.veshv.domain.JdkKeys
36 import org.onap.dcae.collectors.veshv.domain.OpenSslKeys
37 import org.onap.dcae.collectors.veshv.domain.SecurityConfiguration
38 import java.nio.file.Paths
39 import kotlin.test.assertTrue
40
41 /**
42  * @author Piotr Jaszczyk <piotr.jaszczyk@nokia.com>
43  * @since June 2018
44  */
45 object ServerSslContextFactoryTest : Spek({
46     val PASSWORD = "onap"
47
48     describe("SslContextFactory (OpenSSL)") {
49         val keys = OpenSslKeys(
50                 privateKey = Paths.get("/", "tmp", "pk.pem"),
51                 cert = Paths.get("/", "tmp", "cert.crt"),
52                 trustedCert = Paths.get("/", "tmp", "clientCa.crt"))
53
54         given("config with security enabled") {
55             val sampleConfig = SecurityConfiguration(keys = Some(keys))
56
57             val cut = object : ServerSslContextFactory() {
58                 override fun createSslContextWithConfiguredCerts(secConfig: SecurityConfiguration) =
59                     SslContextBuilder.forServer(resource("/ssl/ca.crt"), resource("/ssl/server.key")).toOption()
60
61                 private fun resource(path: String) = ServerSslContextFactoryTest.javaClass.getResourceAsStream(path)
62             }
63
64             on("creation of SSL context") {
65                 val result = cut.createSslContext(sampleConfig)
66
67                 it("should be server context") {
68                     assertTrue(result.exists {
69                         it.isServer
70                     })
71                 }
72
73                 it("should use OpenSSL provider") {
74                     assertTrue(result.isDefined())
75                 }
76
77                 /*
78                  * It is too important to leave it untested on unit level.
79                  * Because of the Netty API design we need to do it this way.
80                  */
81                 it("should turn on client authentication") {
82                     val clientAuth: ClientAuth = ReferenceCountedOpenSslContext::class.java
83                             .getDeclaredField("clientAuth")
84                             .run {
85                                 isAccessible = true
86                                 get(result.orNull()) as ClientAuth
87                             }
88                     Assertions.assertThat(clientAuth).isEqualTo(ClientAuth.REQUIRE)
89                 }
90             }
91         }
92
93         given("config with SSL disabled") {
94             val securityConfiguration = SecurityConfiguration(
95                     sslDisable = true,
96                     keys = Some(keys)
97             )
98             val cut = ServerSslContextFactory()
99
100             on("creation of SSL context") {
101                 val result = cut.createSslContext(securityConfiguration)
102
103                 it("should not create any SSL context ") {
104                     assertThat(result.isDefined()).isFalse()
105                 }
106             }
107         }
108     }
109
110     describe("SslContextFactory (JDK)") {
111         val keys = JdkKeys(
112                 keyStore = resourceStreamProvider("/ssl/server.ks.pkcs12"),
113                 keyStorePassword = PASSWORD.toCharArray(),
114                 trustStore = resourceStreamProvider("/ssl/trust.pkcs12"),
115                 trustStorePassword = PASSWORD.toCharArray()
116         )
117
118         given("config without disabled SSL") {
119             val sampleConfig = SecurityConfiguration(keys = Some(keys))
120             val cut = ServerSslContextFactory()
121
122             on("creation of SSL context") {
123                 val result = cut.createSslContext(sampleConfig)
124
125                 it("should work") {
126                     assertTrue(result.isDefined())
127                 }
128
129                 it("should be server context") {
130                     assertTrue(result.exists {
131                         it.isServer
132                     })
133                 }
134
135                 /*
136                  * It is too important to leave it untested on unit level.
137                  * Because of the Netty API design we need to do it this way.
138                  */
139                 it("should turn on client authentication") {
140                     val clientAuth: ClientAuth = JdkSslContext::class.java
141                             .getDeclaredField("clientAuth")
142                             .run {
143                                 isAccessible = true
144                                 get(result.orNull()) as ClientAuth
145                             }
146                     Assertions.assertThat(clientAuth).isEqualTo(ClientAuth.REQUIRE)
147                 }
148
149                 it("should clear passwords so heap dumps won't contain them") {
150                     val xedPassword = PASSWORD.toCharArray()
151                     xedPassword.fill('x')
152                     Assertions.assertThat(keys.keyStorePassword).isEqualTo(xedPassword)
153                     Assertions.assertThat(keys.trustStorePassword).isEqualTo(xedPassword)
154                 }
155             }
156         }
157     }
158 })
159
160 fun resourceStreamProvider(resource: String) = { ServerSslContextFactoryTest::class.java.getResourceAsStream(resource) }