Overview
The Bolt Android SDK provides a managed checkout flow that handles the entire payment experience β shipping, payment entry, 3D Secure challenges, and order completion. To launch checkout, your backend generates an order token and your app passes it to the SDK.
Generating an Order Token (Backend)
Before launching the checkout UI, your backend server must create an order token by calling the Bolt Merchant Orders API. This token represents the cart and is required by the SDK to start checkout.
WARNING
The API key used to authenticate this request is a secret. This call must be made from your server β never from the mobile app.
Request
POST https://api.bolt.com/v1/merchant/orders
Content-Type: application/json
X-Api-Key: <YOUR_MERCHANT_API_KEY>
| Environment | Endpoint |
|---|---|
| Sandbox | https://api-sandbox.bolt.com/v1/merchant/orders |
| Production | https://api.bolt.com/v1/merchant/orders |
Request Body
All amounts are in cents (e.g. 1783 = $17.83).
{
"cart": {
"order_reference": "your-unique-order-id",
"display_id": "ORDER-1234",
"currency": "USD",
"total_amount": 1783,
"tax_amount": 0,
"items": [
{
"name": "Cotton T-Shirt",
"reference": "SKU-001",
"description": "Comfortable cotton tee",
"sku": "SKU-001",
"total_amount": 1930,
"unit_price": 965,
"quantity": 2,
"type": "unknown",
"tax_amount": 0,
"image_url": "https://example.com/tshirt.jpg"
}
],
"shipments": [
{
"cost": 103,
"service": "Standard Shipping"
}
],
"discounts": [
{
"amount": 250,
"type": "discount"
}
]
}
}
Response
{
"token": "bolt-order-token-abc123"
}
Your backend returns this token to your mobile app, which then passes it to the SDK.
End-to-End Flow
βββββββββββββββ ββββββββββββββββββββ ββββββββββββ
β Mobile App βββ(1)βββΆβ Your Backend βββ(2)βββΆβ Bolt API β
β β β β β β
β ββββ(3)βββ (API key stays ββββ(3)βββ β
β β β server-side) β β β
β β ββββββββββββββββββββ ββββββββββββ
β β
β (4) Pass token to BoltCheckout.get().startCheckout(...)
β β
β (5) SDK opens checkout UI β user completes payment
β β
β (6) Receive result via BoltCheckoutDelegate
βββββββββββββββ
- User taps “Checkout” β app sends cart details to your backend.
- Your backend calls
POST /v1/merchant/orderswith the cart and your API key. - Bolt returns the order token; your backend forwards it to the app.
- App passes the token to the SDK.
- SDK presents the checkout experience.
- App receives the result (success, cancelled, or failed).
Implementing the Checkout Flow
To handle the checkout process, register an ActivityResultLauncher and implement BoltCheckoutDelegate to manage the success, error, and cancellation states.
Complete Example (Activity)
import android.content.Intent
import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.result.ActivityResultLauncher
import com.bolt.checkout.BoltCheckout
import com.bolt.checkout.intl.BoltCheckoutDelegate
import com.bolt.checkout.intl.BoltCheckoutResult
import com.bolt.checkout.intl.BoltShippingAddress
import com.bolt.checkout.intl.BoltFrontendShippingAndTaxResult
import com.bolt.checkout.intl.BoltFrontendShippingOption
import com.bolt.checkout.model.BoltCheckoutConfig
import com.bolt.checkout.model.BoltMerchantHints
class MainActivity : ComponentActivity() {
private lateinit var checkoutLauncher: ActivityResultLauncher<Intent>
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
// 1. Register the result launcher
checkoutLauncher = BoltCheckout.get().getBoltCheckoutActivityResultLauncher(
activity = this,
boltCheckoutDelegate = object : BoltCheckoutDelegate {
override fun onCheckoutSuccess(result: BoltCheckoutResult) {
// Handle successful checkout β see API Reference for full result fields
}
override fun onCheckoutError(errorReason: String) {
// Handle SDK, network, or validation errors
}
override fun onCheckoutCancel() {
// Handle the user intentionally closing the checkout
}
// Optional lifecycle callbacks (useful for analytics)
override fun onCheckoutStart() { }
override fun onEmailEnter(email: String) { }
override fun onShippingDetailsComplete(address: BoltShippingAddress) { }
override fun onShippingOptionsComplete() { }
override fun onPaymentSubmit() { }
// Optional bidirectional callbacks (WebView mode only)
override suspend fun check(): Boolean {
// Return false to cancel checkout (e.g. cart validation failed)
return true
}
override suspend fun fetchShippingOptions(
address: BoltShippingAddress
): BoltFrontendShippingAndTaxResult? {
// Return shipping options, or null to fall back to backend-managed shipping
return BoltFrontendShippingAndTaxResult(
shippingOptions = listOf(
BoltFrontendShippingOption(
service = "Standard Shipping",
cost = 599L,
currency = "USD",
reference = "standard",
estimatedDeliveryDate = "2026-04-14",
),
),
taxAmount = 150L,
taxCurrency = "USD",
)
}
},
)
}
// 2. Launch the checkout flow (e.g., triggered by a button tap)
fun onCheckoutButtonClicked() {
val orderToken = "order-token-from-your-backend"
val config = BoltCheckoutConfig(
orderToken = orderToken,
nativeCheckout = false,
hints = BoltMerchantHints(
firstName = "",
lastName = "",
email = "",
phone = "",
addressLine1 = "",
addressLine2 = "",
city = "",
state = "",
zip = "",
country = "", // ISO 3166-1 alpha-2 code, e.g. "US"
companyName = "", // Optional
),
)
BoltCheckout.get().startCheckout(
checkoutConfig = config,
context = this,
checkoutActivityResultLauncher = checkoutLauncher,
)
}
}
Launching from a Fragment
If you are launching checkout from within a Fragment, use the fragment overload:
val checkoutLauncher = BoltCheckout.get().getBoltCheckoutActivityResultLauncher(
fragment = this,
boltCheckoutDelegate = delegate,
)
Pre-Filling Customer Data
Use BoltMerchantHints to pre-fill customer details and reduce friction during checkout:
| Field | Type | Description |
|---|---|---|
firstName |
String |
Customer’s first name. |
lastName |
String |
Customer’s last name. |
email |
String |
Customer’s email address. |
phone |
String |
Customer’s phone number. |
addressLine1 |
String |
Street address line 1. |
addressLine2 |
String |
Street address line 2. |
city |
String |
City. |
state |
String |
State or region. |
zip |
String |
Postal code. |
country |
String |
ISO 3166-1 alpha-2 country code (e.g. "US"). |
companyName |
String |
Optional company name. |
UI Modes
Currently, the SDK supports WebView mode only. The checkout experience is rendered via a Bolt-hosted WebView. Native checkout mode is planned for a future release.