org.jitsi.metaconfig.Delegates.kt Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of jitsi-metaconfig Show documentation
Show all versions of jitsi-metaconfig Show documentation
jitsi-metaconfig helps solve the problems around the evolution of configuration properties
The newest version!
/*
* Copyright @ 2018 - present 8x8, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jitsi.metaconfig
import org.jitsi.metaconfig.supplier.ConfigSourceSupplier
import org.jitsi.metaconfig.supplier.ConfigValueSupplier
import org.jitsi.metaconfig.supplier.FallbackSupplier
import kotlin.reflect.KProperty
import kotlin.reflect.typeOf
/**
* A delegate for a configuration property which takes a [ConfigValueSupplier]
*/
open class ConfigDelegate(private val supplier: ConfigValueSupplier) {
open operator fun getValue(thisRef: Any, property: KProperty<*>): T {
return supplier.get()
}
}
/**
* A config property delegate which will return null if the property isn't found
*/
class OptionalConfigDelegate(private val supplier: ConfigValueSupplier) {
operator fun getValue(thisRef: Any, property: KProperty<*>): T? {
return try {
supplier.get()
} catch (e: ConfigException.UnableToRetrieve.ConditionNotMet) {
throw e
} catch (t: ConfigException.UnableToRetrieve) {
null
}
}
}
/**
* Create a [ConfigDelegate] for a single property (no fallback) from only a key and source and fill in
* the type automatically, enables doing:
* val port: Int by config("app.server.port".from(configSource))
* Instead of:
* val port: Int by config("app.server.port".from(configSource).asType())
* Since the inline function can fill in the type on its own.
*
* throws [ConfigException.UnableToRetrieve] if the property couldn't be retrieved
*/
inline fun config(supplier: ConfigSourceSupplier): ConfigDelegate = ConfigDelegate(supplier)
/**
* Create a [ConfigDelegate] which will query multiple [ConfigValueSupplier]s, in order, for a
* given property.
*
* throws [ConfigException.UnableToRetrieve] if the property couldn't be retrieved
*/
inline fun config(block: SupplierBuilder.() -> Unit): ConfigDelegate {
val supplierBuilder = SupplierBuilder(typeOf()).apply(block)
return if (supplierBuilder.suppliers.size == 1) {
// Avoid wrapping in a FallbackSupplier if we don't need one
ConfigDelegate(supplierBuilder.suppliers.first())
} else {
ConfigDelegate(FallbackSupplier(supplierBuilder.suppliers))
}
}
/**
* Create a [ConfigValueSupplier] which can be used for a non-member field, e.g.:
*
* fun main(args: Array) {
* val port: ConfigValueSupplier = configSupplier {
* retrieve("app.port".from(configSource))
* }
* }
*/
inline fun configSupplier(block: SupplierBuilder.() -> Unit): ConfigValueSupplier {
val supplier = SupplierBuilder(typeOf()).apply(block)
return FallbackSupplier(supplier.suppliers)
}
/**
* Create an [OptionalConfigDelegate] for a single property (no fallback) from only a key and source (filling in
* the type automatically), returns null if the property couldn't be retrieved
*/
inline fun optionalconfig(supplier: ConfigSourceSupplier): OptionalConfigDelegate =
OptionalConfigDelegate(supplier)
/**
* Create an [OptionalConfigDelegate] which queries multiple [ConfigValueSupplier]s for a property, returning
* null if the property couldn't be retrieved
*/
inline fun optionalconfig(block: SupplierBuilder.() -> Unit): OptionalConfigDelegate {
val supplierBuilder = SupplierBuilder(typeOf()).apply(block)
return if (supplierBuilder.suppliers.size == 1) {
// Avoid wrapping in a FallbackSupplier if we don't need one
OptionalConfigDelegate(supplierBuilder.suppliers.first())
} else {
OptionalConfigDelegate(FallbackSupplier(supplierBuilder.suppliers))
}
}