An experiment in style and technique in Kotlin.
Layers is a list of maps that appears as a single map. It uses rules
to provide a single value for each key, based on all values for that key in
the list of maps. For example, if the key "BOB" has values 1, 2, and 3 in
different layers, and the rule were "sum", then the value of "BOB" in the map
would be 6. Changing the rule to "latest of" for "BOB" would result in the map
having 3 for the value of that key.
(See Layers Java for an older approach in Java.)
To build, use ./mvnw verify or ./batect build (for a CI-like experience).
There are no run-time dependencies.
This code relies on JDK 11 or newer.
- DependencyCheck scans for dependency security issues
- detekt runs static code analysis for Kotlin
- JUnit runs tests
- JaCoCo measures code coverage
- ktlint keeps code tidy
Use ./mvnw (Maven) or ./batect build (Batect) to build, run tests, and
create a demo program. Use ./run.sh or ./batect run to run the demo.
Batect works "out of the box", however, an important optimization is to avoid redownloading plugins and dependencies from within a Docker container.
This shares Maven plugin and dependency downloads with the Docker container run by Batect.
It is difficult to express in Kotlin the structure of functions without providing their names (think interfaces; meta-programming may be required), but for all functions which express map state (construction or mutation), functions come in three styles:
foo(vararg state: Pair<String, Entry<*>>): T
x = x.foo("a" to 3.toValue()) // Merge into existing mutable mapfoo(state: EntryMap): T
x = x.foo(mapOf("a" to 3.toValue())) // Merge into existing mutable mapfoo(state: MutableMap<String, Entry<*>>.() -> Unit): T
x = x.foo {
this["a"] = 3.toValue() // Mutate existing mutable map
}Example functions following these patterns include new and edit.
Actual declarations take advantage of these type aliases:
EntryMap = Map<String, Entry<*>>EditMap = MutableMap<String, Entry<*>>EditBlock = EditMap.() -> Unit
layers— an immutable list of layers, ordered from most recent to oldest. The top-most in the list is the current layercurrent— the current, editable layer. Make updates against the _ current_ layer
EditableLayer
is a subtype of
Layer.
edit— edits with a block. AllMapmethods apply. A sample:editableLayer.edit { this["BOB"] = 3.toEntry() }
A layers rule which returns a constant value.
See
ConstantRule
.
A layers rule which returns the latest value (the value in the most recently
layer to a Layers).
See
LatestOfRule
.
A layers rule which sums all values added to a Layers.
See
SumOfRule
.
- Rationalize uses of
Mapas input vsMutableMapreused as a property or delegated argument - Incorporate the spike having generic key and value types