---
title: Background sessions
description: Keep a Meta Ray-Ban session alive when your app backgrounds — the Android foreground service for mic, iOS background modes, and which capabilities survive.
type: guide
platform: all
vendor: meta
related:
  - /docs/sdk/android/lifecycle
  - /docs/guides/handle-disconnects
  - /docs/concepts/sessions
---

By default, capability subscriptions (`glasses.audio.*`, the assistant) run on the SDK's coroutine scope, which is bound to your **process** — not to any Activity. While your app is **foreground**, that's enough. To keep the glasses listening (a voice assistant or live transcription) while your app is **backgrounded**, you need an OS-level keep-alive: a foreground service on Android, background modes on iOS. This guide covers what's required, what survives, and what doesn't.

> Kotlin leads the snippets. Android uses the bundled foreground service; iOS uses background modes — a genuinely different OS mechanism, covered in its own section below.

## What "background session" means

The glasses connection itself doesn't end the moment your app loses focus — but the OS will reclaim a backgrounded process (and with it your `ExtentosGlasses` instance and its transport) under memory pressure or after enough time, unless you hold a foreground service or background-mode budget. So "keeping the session alive" is really "keeping your process alive and the audio path running while backgrounded."

This is a separate concern from *handling* a disconnect when it does happen — see [handle disconnects](/docs/guides/handle-disconnects) for the recovery path.

## Android: the bundled foreground service

For background-surviving **microphone** capture, the library ships a foreground service so you don't write one:

```kotlin
import com.extentos.glasses.core.service.GlassesForegroundService

// AFTER RECORD_AUDIO is granted at runtime — typically in the grant callback:
GlassesForegroundService.start(this)   // 'this' is any Context

// When background capture is no longer needed:
GlassesForegroundService.stop(this)
```

The service is declared for you in the library manifest as:

```xml
<service
    android:name="com.extentos.glasses.core.service.GlassesForegroundService"
    android:foregroundServiceType="microphone"
    android:exported="false" />
```

You don't declare it — you **start** it. The rules that matter (see [Android lifecycle](/docs/sdk/android/lifecycle#background-capture-and-the-foreground-service) and [manifest setup](/docs/sdk/android/manifest#the-bundled-foreground-service)):

- **Permission first.** `RECORD_AUDIO` must already be granted at runtime. On Android 14+, starting a `microphone`-type foreground service without the grant throws `SecurityException` at service-create time and crashes the app.
- **Declare the foreground-service permissions.** Your app's manifest needs `FOREGROUND_SERVICE` and `FOREGROUND_SERVICE_MICROPHONE` (Android 14+) — `getPermissions` derives these from your continuous-capture capabilities. The library declares the `<service>` element; the permissions are app-owned.
- **Start from an Activity, not `Application.onCreate`.** The grant can't exist that early. Start it from your permission-grant callback, or after a `checkSelfPermission(...) == PERMISSION_GRANTED` check.
- **Idempotent.** Calling `start` again while running just updates the notification.
- **Stop it when done** to drop the notification and release the foreground budget.

> **Camera in the background is not covered by the bundled service.** `GlassesForegroundService` is `microphone`-type only. Surviving a `videoFrames()` stream in the background requires a **`camera`-type** foreground service, which Android requires the **consumer app to declare itself** (the library can't declare a camera FGS on your behalf without forcing it on every app). Subclass `GlassesForegroundService` and declare your own `<service android:foregroundServiceType="camera" />` with the matching runtime rules. Most apps only need background mic.

## iOS: background modes

iOS doesn't use foreground services — a backgrounded app keeps running only within a declared **background mode** budget. For an audio-driven glasses session, the relevant `UIBackgroundModes` entries (`bluetooth-central`, `bluetooth-peripheral`, `external-accessory` — plus `audio`, which you must add yourself when you stream the mic; `generateConnectionModule` emits only the three Bluetooth/accessory modes) must be present in Info.plist; `generateConnectionModule(platform: "ios")` includes the background-mode and `UISupportedExternalAccessoryProtocols` keys. iOS background execution is more constrained than an Android foreground service — validate background behavior on a real device before relying on it.

## What survives backgrounding

| Capability | Backgrounded behavior |
|---|---|
| `glasses.audio.transcriptions()` / `recordDiscrete()` / the assistant | Survives **with** the foreground service (Android) / audio background mode (iOS) running. Without it, capture stops when the process is reclaimed. |
| `glasses.audio.speak()` | Plays while the audio path is alive; same keep-alive requirement. |
| `glasses.camera.*` | Needs a **consumer-declared `camera`-type** FGS on Android (not the bundled mic service). |
| The connection state | Persists while the process lives; on process death you re-`create(...)` and reconnect — see [process death](/docs/sdk/android/lifecycle#process-death). The dev-loop pairing identity is persisted to `filesDir`, but the live connection is re-established from scratch. |

Camera-only or strictly foreground apps don't need any of this — the foreground-service declaration is harmless if unused.

## Honest limits

- **The OS can still kill you.** A foreground service and background modes reduce — they don't eliminate — OS reclamation. Under hard memory pressure or aggressive battery-saver/OEM policies, a backgrounded session can still be terminated. Design for it: observe `glasses.connection.state`, handle the `Disconnected` cause, and reconnect cleanly. See [handle disconnects](/docs/guides/handle-disconnects).
- **Battery cost is real.** A live mic + Bluetooth audio path in the background drains both the phone and the glasses. Start the service only while you actually need background capture, and stop it as soon as you don't.
- **Sim ≠ hardware here.** The **browser simulator does not exercise OS background lifecycle at all** — there's no foreground service, no battery-saver kill, no process reclamation in a browser tab. A session that "stays alive when backgrounded" in the simulator tells you nothing about real-device background survival. Verify backgrounding on real hardware.

## Related

- [Android SDK lifecycle](/docs/sdk/android/lifecycle) — the full foreground-service wiring and process-death behavior.
- [Handle disconnects](/docs/guides/handle-disconnects) — recovering when a backgrounded session is killed.
- [Sessions](/docs/concepts/sessions) — the connection-state machine and what persists.
