App Features
App features let you control application behaviour remotely without releasing a new build. The SDK downloads feature data from the server, caches it locally, and emits an update event whenever the values change.
Accessing the features object
Use the features property on your Magify instance:
val features = magify.features
features implements the Features interface, which exposes typed accessors and an RxJava 2 update observable.
Reading typed values
Every accessor returns a nullable value — it is null when the key does not exist or the stored value cannot be converted to the requested type.
Boolean
val isEnabled: Boolean? = magify.features.getBoolean("dark_mode_enabled")
String
val title: String? = magify.features.getString("onboarding_title")
Long (integer)
val retryCount: Long? = magify.features.getLong("max_retry_count")
Double
val discount: Double? = magify.features.getDouble("discount_rate")
Dictionary (map)
Returns Map<String, Any?>? — suitable for loosely-typed composite values:
val config: Map<String, Any?>? = magify.features.getCustom("paywall_config")
val variant = config?.get("variant") as? String
Raw JSON string
Use getCustomJsonData(key) to obtain the raw JSON representation of a feature value:
val json: String? = magify.features.getCustomJsonData("paywall_config")
Custom object
Use getCustomObject(key, Class<T>) to deserialise a JSON-serialised feature into any class. Returns null when the key is absent or deserialisation fails.
data class PaywallConfig(
val variant: String,
val price: Double
)
val config: PaywallConfig? = magify.features.getCustomObject(
"paywall_config",
PaywallConfig::class.java
)
config?.let {
// use it.variant, it.price
}
Reacting to feature updates
observeUpdate() returns an io.reactivex.Observable<Unit> (RxJava 2) that emits whenever the SDK receives fresh feature values from the server.
magify.features.observeUpdate()
.observeOn(AndroidSchedulers.mainThread())
.subscribe {
// Re-read the values you care about
val isEnabled = magify.features.getBoolean("dark_mode_enabled") ?: false
applyDarkMode(isEnabled)
}
Dispose the subscription when it is no longer needed to avoid memory leaks.
Next step
For server-driven content items, see the Content section.