Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

techtask/Separation-of-credentials-from-endpoints #35

Merged
10 changes: 10 additions & 0 deletions cogboard-app/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,10 @@ tasks.named("processResources") {
dependsOn(":cogboard-webapp:copyReactAppToAppClasspath")
}

tasks.named<Test>("test") {
useJUnitPlatform()
}

dependencies {

"io.knotx:knotx".let { v ->
Expand All @@ -21,6 +25,12 @@ dependencies {
implementation("$v-rx-java2")
}
implementation(kotlin("stdlib-jdk8"))

testImplementation("org.assertj:assertj-core:3.12.2")
testImplementation("org.junit.jupiter:junit-jupiter-api:5.4.2")
testImplementation("org.junit.jupiter:junit-jupiter-params:5.3.1")
testImplementation(gradleTestKit())
testRuntime("org.junit.jupiter:junit-jupiter-engine:5.4.2")
}

repositories {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@ import com.cognifide.cogboard.storage.docker.VolumeStorage
import com.cognifide.cogboard.widget.Widget
import com.cognifide.cogboard.widget.WidgetIndex
import io.vertx.core.AbstractVerticle
import io.vertx.core.json.JsonArray
import io.vertx.core.json.JsonObject
import io.vertx.core.logging.Logger
import io.vertx.core.logging.LoggerFactory
Expand All @@ -15,10 +14,8 @@ class ConfigManager : AbstractVerticle() {

private val widgets = mutableMapOf<String, Widget>()
private lateinit var storage: Storage
private lateinit var endpoints: JsonArray

override fun start() {
endpoints = config().getJsonArray("endpoints")
storage = VolumeStorage(vertx)
listenOnConfigSave()
listenOnWidgetUpdate()
Expand Down Expand Up @@ -78,18 +75,11 @@ class ConfigManager : AbstractVerticle() {
private fun attachEndpoint(config: JsonObject) {
val endpointId = config.getString(CogboardConstants.PROP_ENDPOINT)
endpointId?.let {
config.put(CogboardConstants.PROP_ENDPOINT, endpoints
.stream()
.map { it as JsonObject }
.filter {
endpointId == it.getString("id")
}.findFirst()
.orElse(JsonObject()))
val endpoint = Endpoint.from(config(), endpointId)
config.put(CogboardConstants.PROP_ENDPOINT, endpoint.asJson())}
}
}

companion object {
val LOGGER: Logger = LoggerFactory.getLogger(ConfigManager::class.java)
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
package com.cognifide.cogboard.config

import io.vertx.core.json.JsonArray
import io.vertx.core.json.JsonObject
import java.util.*

class Endpoint(val endpoints: JsonArray, val credentials: JsonArray, val endpointId: String) {

fun asJson(): JsonObject {
return findJsonObjectById(endpointId, endpoints)
.map { attachCredentials(it) }
.orElse(JsonObject())
}

private fun attachCredentials(endpoint: JsonObject): JsonObject {
endpoint.remove(CREDENTIALS).toString().let {
val credentials = findJsonObjectById(it, credentials)
.orElse(JsonObject())
endpoint.put(USER, credentials.getString(USER) ?: "")
endpoint.put(PASSWORD, credentials.getString(PASSWORD) ?: "")
}

return endpoint
}

private fun findJsonObjectById(id: String?, array: JsonArray): Optional<JsonObject> {
return array.stream()
.map { it as JsonObject }
.filter {
id == it.getString(ID)
}.findFirst()
}

companion object {
private const val ID = "id"
private const val CREDENTIALS = "credentials"
private const val ENDPOINTS = "endpoints"
private const val USER = "user"
private const val PASSWORD = "password"

fun from(config: JsonObject, endpointId: String): Endpoint {
val endpoints = config.getJsonArray(ENDPOINTS) ?: JsonArray()
val credentials = config.getJsonArray(CREDENTIALS) ?: JsonArray()
return Endpoint(endpoints, credentials, endpointId)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,8 @@ class GetEndpoints : RoutingHandlerFactory {
copy.stream().forEach {
if (it is JsonObject) {
it.remove("url")
it.remove("user")
it.remove("password")
it.remove("publicUrl")
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice !

it.remove("credentials")
}
}
return copy
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
package com.cognifide.cogboard.config

import io.vertx.core.json.JsonArray
import io.vertx.core.json.JsonObject
import org.junit.jupiter.api.Assertions.assertEquals
import org.junit.jupiter.api.Assertions.assertFalse
import org.junit.jupiter.api.Test

internal class EndpointTest {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really like that You introduced JUnit to the project !


private val endpoints: JsonArray = readJsonArrayFromResource("/com/cognifide/cogboard/config/endpoints-test.json", ENDPOINTS)
private val credentials: JsonArray = readJsonArrayFromResource("/com/cognifide/cogboard/config/endpoints-test.json", CREDENTIALS)

@Test
fun shouldRemoveCredentialsProp() {
val validEndpoint = Endpoint(endpoints, credentials,"validEndpoint").asJson()
Copy link
Collaborator Author

@yahorm yahorm Sep 9, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

next time please use @beforeeach for initialize e.g. endpoint once.

private lateinit var validEndpoint: JsonObject
private lateinit var invalidEndpoint: JsonObject

@BeforeEach
fun init() {
    validEndpoint = Endpoint(endpoints, credentials, "validEndpoint").asJson()
    invalidEndpoint = Endpoint(endpoints, credentials, "invalidEndpoint").asJson()
}

assertFalse(validEndpoint.containsKey("credentials"))

val invalidEndpoint = Endpoint(endpoints, credentials, "invalidEndpoint").asJson()
assertFalse(invalidEndpoint.containsKey("credentials"))
}

@Test
fun shouldAddUserAndPasswordProp() {
val validEndpoint = Endpoint(endpoints, credentials,"validEndpoint").asJson()
assert(validEndpoint.containsKey("user"))
assert(validEndpoint.containsKey("password"))

val invalidEndpoint = Endpoint(endpoints, credentials, "invalidEndpoint").asJson()
assert(invalidEndpoint.containsKey("user"))
assert(invalidEndpoint.containsKey("password"))
}

@Test
fun checkIfUserAndPasswordAreCorrect() {
val endpoint = Endpoint(endpoints, credentials,"validEndpoint").asJson()
assertEquals("user1", endpoint.getString("user"))
assertEquals("password1", endpoint.getString("password"))
}

@Test
fun checkIfUserAndPasswordAreEmptyForInvalidId() {
val endpoint = Endpoint(endpoints, credentials, "invalidEndpoint").asJson()
assertEquals("", endpoint.getString("user"))
assertEquals("", endpoint.getString("password"))
}

@Test
fun shouldReturnValidCredentials() {
val endpoint = Endpoint(endpoints, credentials,"validEndpoint").asJson()
val validEndpoint = JsonObject("""
{
"id" : "validEndpoint",
"label" : "Valid Endpoint",
"url" : "url",
"publicUrl" : "Public Url",
"user" : "user1",
"password" : "password1"
}
""")

assertEquals(validEndpoint, endpoint)
}

@Test
fun shouldReturnEmptyCredentials() {
val endpoint = Endpoint(endpoints, credentials, "invalidEndpoint").asJson()
val invalidEndpoint = JsonObject("""
{
"id" : "invalidEndpoint",
"label" : "Invalid Endpoint",
"url" : "url",
"user" : "",
"password" : ""
}
""")

assertEquals(invalidEndpoint, endpoint)
}

companion object {
private const val ENDPOINTS = "endpoints"
private const val CREDENTIALS = "credentials"

fun readJsonArrayFromResource(pathToJsonResource: String, jsonArrayId: String) : JsonArray {
val endpointsContent = EndpointTest::class.java.getResource(pathToJsonResource).readText()
val endpointsJson = JsonObject(endpointsContent.trimIndent())
return endpointsJson.getJsonArray(jsonArrayId)
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
{
"endpoints": [
{
"id": "validEndpoint",
"label": "Valid Endpoint",
"url": "url",
"publicUrl": "Public Url",
"credentials": "credentials1"
},
{
"id": "invalidEndpoint",
"label": "Invalid Endpoint",
"url": "url",
"credentials": "nonExistingCredentials"
}
],
"credentials": [
{
"id": "credentials1",
"label": "My Credentials 1",
"user": "user1",
"password": "password1"
},
{
"id": "credentials2",
"label": "My Credentials 2",
"user": "user2",
"password": "password2"
}
]
}
22 changes: 18 additions & 4 deletions knotx/conf/initial/endpoints.conf
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,28 @@ endpoints = [
id: "endpoint1",
label: "My Endpoint 1",
url: "url",
user: "username",
password: "password"
publicUrl: "My Public Url",
credentials: "credentials1"
}
{
id: "endpoint2",
label: "My Endpoint 2",
url: "url",
user: "username",
credentials: "credentials2"
}
]

credentials = [
{
id: "credentials1"
label: "My Credentials 1",
user: "user",
password: "password"
}
{
id: "credentials2"
label: "My Credentials 2",
user: "user",
password: "password"
}
]
]