The official native Kotlin SDK for embedding an interactive SeatLayer reserved- seating map in an Android app.
Documentation · Mobile SDK guide · Live demo · AI toolkit · Web and React SDKs
Public preview:
0.1.0is available from JitPack while the permanentio.seatlayer:seatlayer-androidMaven Central namespace is completed.
SeatLayerView, a native AndroidViewthat owns the embedded seat map.- A coroutine-based controller for holds, best available, general admission, tiers, floors, view modes, and zoom.
- Typed Kotlin models,
StateFlowreadiness, andSharedFlowevents. - An origin-restricted AndroidX WebKit bridge with no unrestricted
addJavascriptInterface. - A pinned, checksummed SeatLayer Web SDK bundle for deterministic builds.
- A runnable sample app and protocol/unit tests.
- Android API 24+
- JDK 17 for building the SDK
- An AndroidX application
Add JitPack to dependency resolution:
// settings.gradle.kts
dependencyResolutionManagement {
repositories {
google()
mavenCentral()
maven("https://jitpack.io") {
content {
includeGroup("com.github.seatlayer")
}
}
}
}Add the SDK:
// app/build.gradle.kts
dependencies {
implementation(
"com.github.seatlayer:seatlayer-android:v0.1.0",
)
}For a reproducible production build, pin an exact release tag as shown above.
Do not use JitPack's main-SNAPSHOT coordinate.
The view can be created in Kotlin or placed in XML.
class CheckoutActivity : ComponentActivity() {
private val scope = CoroutineScope(SupervisorJob() + Dispatchers.Main.immediate)
private lateinit var seatMap: SeatLayerView
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
seatMap = SeatLayerView(this)
setContentView(seatMap)
scope.launch {
seatMap.controller.events.collect { event ->
when (event) {
is SeatLayerEvent.SelectionChanged ->
renderSelection(event.seats)
is SeatLayerEvent.HoldExpired ->
showExpiredMessage()
is SeatLayerEvent.Error ->
reportSeatLayerError(event.error)
else -> Unit
}
}
}
scope.launch {
seatMap.load(
SeatLayerConfiguration(
event = "ev_your_event_key",
currency = "USD",
maxSelection = 8,
),
)
}
}
override fun onDestroy() {
seatMap.destroy()
scope.cancel()
super.onDestroy()
}
}load is a suspending function and returns ReadyInfo. Run it from a lifecycle-
appropriate coroutine on Android; the SDK safely moves WebView work to the main
thread.
Seat selection happens inside the map. Your app then creates a short-lived hold:
scope.launch {
val hold = seatMap.controller.hold(ttlMillis = 10 * 60 * 1_000)
if (hold != null) {
checkoutWith(
holdId = hold.holdId,
expiresAt = hold.expiry,
items = hold.items,
)
}
}Create the final booking from your trusted server. Never put a SeatLayer secret or privileged booking credential in an Android application.
val controller = seatMap.controller
val seats = controller.getSelection()
val hold = controller.getCurrentHold()
controller.extendHold()
controller.release()
val best = controller.bestAvailable(quantity = 4)
val ga = controller.holdGeneralAdmission(areaId = "floor", quantity = 2)
controller.setSeatTier(seatId = "A-12", tierId = "adult")
controller.setFloor("balcony")
controller.setViewMode(SeatLayerViewMode.Isometric)
controller.setColorblindSafe(true)
controller.zoomToFit()Before using a newly introduced command with an older bundled Web SDK, inspect the negotiated capability:
if (controller.bundle.value?.supportsCommand("bestAvailable") == true) {
controller.bestAvailable(quantity = 2)
}See the bridge reference for lifecycle, events, errors, and the full command surface.
SeatLayerConfiguration accepts:
| Option | Purpose |
|---|---|
event |
Required public event key. |
apiBase |
Optional SeatLayer API endpoint override. |
publicKey |
Optional public SDK key. Never provide a secret key. |
maxSelection |
Maximum buyer selection. |
locale, messages |
Locale and UI message overrides. |
currency |
Buyer-facing currency. |
colorblindSafe |
Accessible palette preference. |
initialView |
Flat, isometric, or perspective view. |
showsWebSeatTooltip |
Enables the web-rendered tooltip. |
commandTimeoutMillis |
Per-command timeout; defaults to 15 seconds. |
handshakeTimeoutMillis |
Initial ready timeout; defaults to 30 seconds. |
The SDK loads only app-packaged content from
https://appassets.androidplatform.net. Native communication uses AndroidX
WebKit's origin-restricted message listener. File/content access, mixed content,
popups, external navigation, and third-party cookies are disabled.
The bridge is still a client boundary. Treat every event as untrusted input, authorize inventory changes on your server, and finalize bookings server-side.
./gradlew validate
./gradlew :sample:installDebugvalidate runs unit tests, Android lint, release/sample builds, Maven metadata
generation, and the vendored Web SDK checksum.
- Public preview: JitPack release tags and GitHub release artifacts.
- Permanent coordinate:
io.seatlayer:seatlayer-androidon Maven Central after SeatLayer's Central Portal namespace and signing credentials are activated.
Releases follow semantic versioning. See CHANGELOG.md.