Return Types & Models
Kotlin data classes, enums, and feature-variable accessors
This page documents the public Kotlin types the SDK returns and the enums you pass in. All model types live in com.convert.sdk.core.model; the event constants live in com.convert.sdk.core.event. The SDK never throws from its public decision methods — absent or not-ready data surfaces as null or an empty list.
Variation
VariationReturned by ConvertContext.runExperience(...) (nullable) and runExperiences(...) (as a list). A Kotlin data class with all-nullable fields:
public data class Variation(
val id: String? = null,
val key: String? = null,
val name: String? = null,
val experienceId: String? = null,
val experienceKey: String? = null,
val experienceName: String? = null,
val bucketingAllocation: Double? = null,
val changes: List<JsonElement>? = null,
)key— the merchant-defined variation key from the Convert dashboard; this is what you branch on.id— the variation identifier.bucketingAllocation— the basis-point allocation the visitor hit. Populated on fresh bucketing;nullon a sticky lookup.changes— raw variation changes, asJsonElementvalues.
val variation = ctx.runExperience("homepage-redesign")
when (variation?.key) {
"control" -> renderControl()
"treatment" -> renderTreatment()
null -> renderControl() // not ready / not bucketed / experience absent
}Feature and FeatureStatus
Feature and FeatureStatusReturned by ConvertContext.runFeature(...) (nullable) and runFeatures(...) (as a list):
public data class Feature(
val id: String? = null,
val key: String? = null,
val name: String? = null,
val status: FeatureStatus,
val variables: Map<String, JsonElement>? = null,
val experienceId: String? = null,
val experienceKey: String? = null,
val experienceName: String? = null,
) {
val enabled: Boolean get() = status == FeatureStatus.ENABLED
}
public enum class FeatureStatus { ENABLED, DISABLED }enabledis a convenience forstatus == FeatureStatus.ENABLED.- When a feature is
DISABLED,variablesisnulland the accessors below returnnull.
val feature = ctx.runFeature("checkout-v2")
if (feature?.enabled == true) {
enableCheckoutV2()
}Feature variable accessors
When a feature is ENABLED, variables holds JsonElement values — usually JsonPrimitive scalars. For the common scalar case, use the extension helpers in com.convert.sdk.android (file facade FeatureExtensions):
import com.convert.sdk.android.getString
import com.convert.sdk.android.getInt
import com.convert.sdk.android.getDouble
import com.convert.sdk.android.getBoolean
val color = feature?.getString("ctaColor") ?: "#0066ff"
val limit = feature?.getInt("maxItems") ?: 20
val price = feature?.getDouble("price") ?: 9.99
val experimental = feature?.getBoolean("experimental") == trueCoercion is strict-then-loose: numeric primitives resolve directly; numeric strings fall back through toXxxOrNull(). JsonNull, arrays, nested objects, and absent keys all return null. For structured (JsonObject / JsonArray) variables, read feature.variables?.get("key") and decode the JsonElement yourself with kotlinx.serialization.
GoalData and GoalDataKey
GoalData and GoalDataKeyPassed to ConvertContext.trackConversion(...) to attach transactional data to a conversion:
public data class GoalData(
val key: GoalDataKey? = null,
val value: JsonElement? = null,
)GoalDataKey values and their JSON names on the wire:
| Enum value | JSON name | Typical value |
|---|---|---|
AMOUNT | amount | number |
PRODUCTS_COUNT | productsCount | integer |
TRANSACTION_ID | transactionId | string |
CUSTOM_DIMENSION_1 | customDimension1 | string / number |
CUSTOM_DIMENSION_2 | customDimension2 | string / number |
CUSTOM_DIMENSION_3 | customDimension3 | string / number |
CUSTOM_DIMENSION_4 | customDimension4 | string / number |
CUSTOM_DIMENSION_5 | customDimension5 | string / number |
import com.convert.sdk.core.model.GoalData
import com.convert.sdk.core.model.GoalDataKey
import kotlinx.serialization.json.JsonPrimitive
ctx.trackConversion(
goalKey = "purchase-completed",
goalData = listOf(
GoalData(GoalDataKey.AMOUNT, JsonPrimitive(49.99)),
GoalData(GoalDataKey.PRODUCTS_COUNT, JsonPrimitive(3)),
GoalData(GoalDataKey.TRANSACTION_ID, JsonPrimitive("tx-42")),
),
)LogLevel
LogLevelpublic enum class LogLevel { ERROR, WARN, INFO, DEBUG, TRACE }Passed to Builder.logLevel(...). The default is ERROR. See Configuration Options.
SystemEvents
SystemEventsWell-known event names you can subscribe to with sdk.on(event, callback). Each is a String constant on com.convert.sdk.core.event.SystemEvents:
| Constant | Event name |
|---|---|
READY | ready |
CONFIG_UPDATED | config.updated |
API_QUEUE_RELEASED | api.queue.released |
BUCKETING | bucketing |
CONVERSION | conversion |
SEGMENTS | segments |
LOCATION_ACTIVATED | location.activated |
LOCATION_DEACTIVATED | location.deactivated |
AUDIENCES | audiences |
DATA_STORE_QUEUE_RELEASED | datastore.queue.released |
The shared Event System doc explains when each fires.
EventCallback and SubscriptionToken
EventCallback and SubscriptionTokenpublic fun interface EventCallback {
public fun onEvent(data: Map<String, Any?>)
}EventCallback is a Kotlin fun interface, so Kotlin and Java lambdas both convert to it. sdk.on(event, callback) returns an opaque SubscriptionToken; pass it to sdk.off(event, token) to unsubscribe. See Initialization and Java Interop.
Next steps
- Code Examples — these types in complete flows
- Feature Flags — the shared feature-flag concept doc
Updated 2 days ago