Skip to content

Commit d56ad5a

Browse files
authored
Merge pull request #20 from dsx-tech/refactoring
Remove redundant class ConfigManager
2 parents d069052 + f536614 commit d56ad5a

File tree

6 files changed

+51
-96
lines changed

6 files changed

+51
-96
lines changed

rhea-core/src/main/kotlin/uk/dsxt/rhea/ConfigManager.kt

-27
This file was deleted.

rhea-core/src/main/kotlin/uk/dsxt/rhea/PropertyGroup.kt

+1-1
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ open class PropertyGroup {
1818

1919
private val group = javaClass.kotlin.simpleName
2020

21-
private fun groupName() = group?.substringBefore("$") ?: reactiveConfigLogger.error("Unexpected name $group")
21+
private fun groupName() = group?.substringBefore("$") ?: ReactiveConfig.reactiveConfigLogger.error("Unexpected name $group")
2222

2323
private fun name(): String = outer() + groupName()
2424

rhea-core/src/main/kotlin/uk/dsxt/rhea/ReactiveConfig.kt

+38-14
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,41 @@
11
package uk.dsxt.rhea
22

3+
import kotlinx.coroutines.CoroutineScope
4+
import kotlinx.coroutines.channels.BroadcastChannel
5+
import kotlinx.coroutines.channels.Channel
6+
import kotlinx.coroutines.flow.Flow
7+
import kotlinx.coroutines.flow.asFlow
38
import kotlinx.coroutines.flow.filter
49
import kotlinx.coroutines.flow.map
10+
import kotlinx.coroutines.launch
11+
import mu.KotlinLogging
12+
import java.util.concurrent.ConcurrentHashMap
13+
import kotlin.coroutines.EmptyCoroutineContext
514

615
/**
7-
* [ConfigSource] that reads configuration from Vault.
16+
* [ReactiveConfig] manages configuration.
817
*
918
* **Note: use [Builder] to build instances of this class.
1019
*/
11-
class ReactiveConfig private constructor(val manager: ConfigManager) {
20+
class ReactiveConfig private constructor(
21+
private val mapOfSources: MutableMap<String, ConfigSource>,
22+
private val configScope: CoroutineScope,
23+
private val channelOfChanges: BroadcastChannel<RawProperty>
24+
) {
25+
private val flowOfChanges: Flow<RawProperty> = channelOfChanges.asFlow()
26+
private val mapOfProperties: MutableMap<String, Reloadable<*>> = ConcurrentHashMap()
27+
28+
companion object {
29+
val reactiveConfigLogger = KotlinLogging.logger {}
30+
}
1231

1332
/**
1433
* Builder for [ReactiveConfig].
1534
*/
1635
class Builder {
17-
private val manager: ConfigManager = ConfigManager()
36+
private val mapOfSources: MutableMap<String, ConfigSource> = ConcurrentHashMap()
37+
private val configScope = CoroutineScope(EmptyCoroutineContext)
38+
private val channelOfChanges: BroadcastChannel<RawProperty> = BroadcastChannel(Channel.BUFFERED)
1839

1940
/**
2041
* Adds configuration [source] in [ReactiveConfig]s built.
@@ -25,8 +46,11 @@ class ReactiveConfig private constructor(val manager: ConfigManager) {
2546
*/
2647
fun addSource(name: String, source: ConfigSource): Builder {
2748
return apply {
28-
manager.mapOfSources[name] = source
29-
manager.addSource(source)
49+
mapOfSources[name] = source
50+
configScope.launch {
51+
source.subscribe(channelOfChanges, configScope)
52+
}
53+
Thread.sleep(100)
3054
}
3155
}
3256

@@ -36,25 +60,25 @@ class ReactiveConfig private constructor(val manager: ConfigManager) {
3660
* @return new instance of [ReactiveConfig]
3761
*/
3862
fun build(): ReactiveConfig {
39-
return ReactiveConfig(manager)
63+
return ReactiveConfig(mapOfSources, configScope, channelOfChanges)
4064
}
4165
}
4266

4367
/**
4468
* @return [Reloadable] that holds the freshest value of property with given [key] and [type].
4569
*/
4670
operator fun <T> get(key: String, type: PropertyType<T>): Reloadable<T>? {
47-
if (manager.mapOfProperties.containsKey(key)) {
48-
with(manager.mapOfProperties[key]) {
71+
if (mapOfProperties.containsKey(key)) {
72+
with(mapOfProperties[key]) {
4973
return this as Reloadable<T>
5074
}
5175
} else {
5276
synchronized(this) {
53-
if (!manager.mapOfProperties.containsKey(key)) {
77+
if (!mapOfProperties.containsKey(key)) {
5478
var isSet = false
5579
var initialValue: T = type.initial
5680

57-
for (source in manager.mapOfSources.values) {
81+
for (source in mapOfSources.values) {
5882
with(type.parse(source.getNode(key))) {
5983
when (this) {
6084
is ParseResult.Success -> {
@@ -71,7 +95,7 @@ class ReactiveConfig private constructor(val manager: ConfigManager) {
7195
if (isSet) {
7296
return Reloadable(
7397
initialValue,
74-
manager.flowOfChanges
98+
flowOfChanges
7599
.filter { rawProperty: RawProperty ->
76100
rawProperty.key == key
77101
}
@@ -89,16 +113,16 @@ class ReactiveConfig private constructor(val manager: ConfigManager) {
89113
.map {
90114
it as T
91115
},
92-
manager.configScope
116+
configScope
93117
).also {
94-
manager.mapOfProperties[key] = it
118+
mapOfProperties[key] = it
95119
}
96120
} else {
97121
reactiveConfigLogger.error("Couldn't find property with key=$key in any config sources")
98122
return null
99123
}
100124
} else {
101-
with(manager.mapOfProperties[key]) {
125+
with(mapOfProperties[key]) {
102126
return this as Reloadable<T>
103127
}
104128
}

rhea-core/src/test/java/uk/dsxt/rhea/ConfigManagerJavaTest.java

-13
This file was deleted.

rhea-core/src/test/kotlin/uk/dsxt/rhea/ConfigManagerTest.kt

-32
This file was deleted.

rhea-core/src/test/kotlin/uk/dsxt/rhea/PropertyGroupTest.kt

+12-9
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,16 @@ package uk.dsxt.rhea
33
import org.spekframework.spek2.Spek
44
import org.spekframework.spek2.style.specification.describe
55
import kotlin.test.assertNotNull
6-
import kotlin.test.assertTrue
6+
import kotlin.test.assertNull
77

8-
object outer : PropertyGroup(){
8+
object outer : PropertyGroup() {
99
val first by booleanType
10+
1011
object inside : PropertyGroup() {
1112
object deeper : PropertyGroup() {
1213
val anotherone by intType.nullable()
1314
}
15+
1416
val third by stringType
1517
}
1618
}
@@ -21,7 +23,7 @@ object PropertyGroupTest : Spek({
2123
.addSource("configMock", source)
2224
.build()
2325

24-
describe("emitting values with our keys"){
26+
describe("emitting values with our keys") {
2527
source.addToMap("outer.inside.deeper.anotherone", null)
2628
source.addToMap("outer.inside.third", "three")
2729
source.addToMap("outer.first", true)
@@ -31,8 +33,9 @@ object PropertyGroupTest : Spek({
3133
val reloadable2 = config[outer.inside.third]
3234
val reloadable3 = config[outer.first]
3335

34-
describe("wait until reloadables will be created"){
35-
while (reloadable3 == null){}
36+
describe("wait until reloadables will be created") {
37+
while (reloadable3 == null) {
38+
}
3639
}
3740

3841
describe("asserting that right keys created")
@@ -42,10 +45,10 @@ object PropertyGroupTest : Spek({
4245
assertNotNull(reloadable2)
4346
assertNotNull(reloadable3)
4447
}
45-
it("keys should be added to the map"){
46-
assertTrue(config.manager.mapOfProperties.containsKey("outer.inside.deeper.anotherone"))
47-
assertTrue(config.manager.mapOfProperties.containsKey("outer.inside.third"))
48-
assertTrue(config.manager.mapOfProperties.containsKey("outer.first"))
48+
it("keys should be added to the map") {
49+
assertNotNull(config["outer.inside.deeper.anotherone", intType.nullable()])
50+
assertNotNull(config["outer.inside.third", stringType])
51+
assertNull(config["outer.firs", booleanType])
4952
}
5053
}
5154
})

0 commit comments

Comments
 (0)