Skip to main content
The Android SDK is the counterpart to the iOS SDK’s App Attest flow. Your app proves it is genuine and unmodified through Google Play Integrity, Grantiva verifies that proof, and your backend receives the same attestation JWT it already knows how to check. No API key is embedded in your release app — the Play Integrity verdict is the authentication.

Scope: attestation only

The Android SDK ships attestation only. It does not yet include feature flags, feedback and support tickets, push token registration, or user identity. Do not plan an Android release around those.

Requirements

  • minSdk 23EncryptedSharedPreferences requires API 23+
  • compileSdk 34, JDK 17
  • Google Play Services on the device for a real Play Integrity verdict

Install

Initialize

Register your Android package name in the dashboard first — it identifies your tenant the same way Bundle ID + Team ID does on iOS.
The SDK holds the application context internally, so passing an Activity is safe. The constructor is annotated @JvmOverloads, so Java callers get the same defaults. Point at the development environment during integration testing:

Attest

Coroutines

attest() is a suspending function and dispatches its I/O internally, so it is safe to call from any coroutine context. It throws GrantivaError on failure.

Callback overload

For Java and React Native interop, where suspending functions are inconvenient:
The callback is invoked on a background thread.

AttestationResult

DeviceIntelligence carries: The score derives from the Play Integrity verdict: STRONG → 5, DEVICE → 15, BASIC or emulator → 57–60, no verdict → 80. See risk scoring.

Other members

Errors are a sealed GrantivaError: AttestationNotAvailable, NetworkError, ServerError, InvalidConfiguration, TokenExpired, VerificationFailed.

Token caching

Tokens are stored in EncryptedSharedPreferences and reused until 60 seconds before expiry. Call attest() whenever you need a token — it returns the cached copy when one is still valid and only runs a full Play Integrity flow when it has to. There is no need to cache the token yourself.

Emulators and CI

Play Integrity needs real Google Play Services, so it cannot succeed on a bare emulator. Pass an API key to fall back to key auth — the same escape hatch the iOS SDK uses for the Simulator:
The backend treats these requests as unattested and returns a lower-trust token with a risk score of 60.
Never ship an API key in a release build. Key mode skips Play Integrity entirely — anything holding the key can obtain a token.

The device ID is not hardware-bound

This is the one place Android differs materially from iOS, and it affects billing. On iOS the device identity derives from a Secure Enclave key, so it survives app reinstalls. On Android the device ID is a UUID stored in EncryptedSharedPreferences. It is not hardware-bound, so:
  • A fresh install produces a new device ID
  • The new ID counts as a new device against your Monthly Active Devices quota
  • clearStoredData() has the same effect — use it only for sign-out or testing
The JWT’s deviceId claim reflects this, so your backend can account for it rather than assuming an ID is stable across installs.