Koin: interpolate environment variable into property from .properties

Created on 31 Aug 2018  路  4Comments  路  Source: InsertKoinIO/koin

Is your feature request related to a problem? Please describe.
I am trying to load certain configuration values from koin.properties file, whilst also allowing for properties to be overriden or interpolated with values from environment variables. My objective here is to allow for allowing the launching of the application to be fully configurable from the command line anywhere, following 12-factor app principle number 3.

Describe the solution you'd like
I would like to be able to have in my main/resources/koin.properties file something like

service.clientId=${SERVICE_CLIENT_ID}
service.secret=${SERVICE_SECRET}
service.baseUrl=http://${SERVICE_HOST}/api/customers

Those caps-lock variables would come from environment variables, allowing substitution in run-time. In parallel, in my test/resources/koin.properties, I could then choose not to use env vars, instead hard-wiring it to whatever mocked server details I want to use in my tests.

Describe alternatives you've considered

I considered using the environment variables directly, with the useEnvironmentProperties = true option on startKoin, but I'm not sure I want to use such an implicit approach to things. Also, using the env vars directly like that bars me from having interpolated values like shown above.

It appears that apache commons configuration already supports this kind of thing, but it's not clear to me how I could swap the property resolver provided by Koin with the commons' implementation.

Target Koin project

koin-core, I think?

question

All 4 comments

You can use Environment/Koin properties file from one side, and use the extraProperties in test. It should let you use the same properties but not filled with the same source.

@arnaudgiuliani that's a good idea and, upon discussing it with my project team, we decided it is good enough for our use case.

Even then, I'd suggest considering interpolation in the future, because it might be useful in cases where one wants to have property style key names (lowercase with dots) that accept interpolation from env vars.

--
For reference, if anyone comes across this thread in the future, here's something I came up with to achieve interpolation of config properties. I simply created a ConfigSource component that can be injected anywhere, and that uses StringSubstitutor to interpolate stuff. Maybe this could be integrated into Koin at some point ;)

class ConfigSource : KoinComponent {
    fun get(key: String) : String {
        val rawValue = getProperty<String>(key)
        val withProperties = StringSubstitutor.replaceSystemProperties(rawValue)
        return StringSubstitutor.replace(this, System.getenv())
    }
}

Making that concept more first class would be great. It helps allow your core code to be ignorant of environment variables, all configured wherever you do your Koin injection.

I whipped up something similar with the Lightbend config and config 4k that worked pretty well, but in looking at the Koin code, it looked non-trivial to swap out property providers.

Making PropertyRegistry an interface (or an open class) and swappable in the KoinContext (even at build time) would make this pretty straightforward. Populating ahead of time is difficult if you want to perform a translation on key names, similar to how Spring will pull the property spring.datasource.url from the SPRING_DATASOURCE_URL environment variable.

I'd be game for writing up a PR if others would find this helpful and it has a shot at being accepted into core? As it's written today, PropertyRegistry is sealed and instantiated inside Koin only.

EDIT: I believe I hijacked this thread to suggest doing only part of what you've suggested here. I'm particularly interested in allowing env variables to overwrite koin.properties. However I suspect if we're allowing the PropertyRegistry implementation to be swapped, both of our requirements would be met.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

pchmielowski picture pchmielowski  路  3Comments

haroldadmin picture haroldadmin  路  3Comments

caleb-allen picture caleb-allen  路  4Comments

hkelidari picture hkelidari  路  3Comments

guymclean picture guymclean  路  3Comments