Playing protected content with Nagra CONNECT - Android

Nagra CONNECT is the hardware based support for Nagra PRM. Since version 3.102.0 of the Bitmovin Player for Android, playback of Nagra CONNECT PRM-protected content is supported on devices with the necessary hardware capabilities.

Pre-requisites

Before you begin, please ensure you have access to Nagra Documentation, Nagra SSP backend for fetching required tokens and also access to Bitmovin player key to use Bitmovin player. Please refer to links below for respective documentation.

Configuration

1. Application preparation for DRM content playback and Secure Session Management

2. Bitmovin Player Configuration

Once the contentToken as well as the ssmToken are fetched, they can be used with the other required properties to create a NagraConnectConfig and load it into the player.

val contentToken: String = TODO("fetch content token")
val ssmToken: String = TODO("fetch ssm token")

val sourceConfig = SourceConfig(
    url = TODO("CONTENT_MANIFEST_URL"),
    type = SourceType.Dash,
    title = "Nagra Connect Protected Source",
    drmConfig = NagraConnectConfig.Builder()
      .build(
        licenseUrl = TODO("NAGRA_CONNECT_LICENSE_URL"),
        operatorVault = TODO("NAGRA_OPERATOR_VAULT"),
      ).apply {
        httpHeaders = mutableMapOf(
          "nv-authorizations" to "$contentToken,$ssmToken",
          "x-nagra-property" to "nagraOpVault",
          "Content-Type" to "application/json",
          "Accept" to "application/json",
      	)
    },
)

player.load(sourceConfig)

Note: the TODOs represent placeholder for the actual values, which you should have as per the Prerequisites list.

3. Extend setup with fallback to Widevine

As Nagra CONNECT relies on specific hardware, it might be necessary to handle the missing hardware support by falling back to an alternative DRM system like Widevine.

This can be done with the Bitmovin Player by conditionally configuring different DRM systems, and should be done on the configuration side.

val drmConfig = if (isNagraConnectSupported()) {
    createNagraConnectConfig(authorizationHeader)
} else {
    createWidevineConfig(authorizationHeader)
}

val sourceConfig = SourceConfig(
    url = TODO("CONTENT_MANIFEST_URL"),
    type = SourceType.Dash,
    drmConfig = drmConfig,
    title = "Nagra Protected Source",
)

The authorization header consisting of the contentToken and the ssmToken stays the same for both DRM systems, however, the configuration is slightly different (see the full code example for more details).

The full extended setup can be explored here:

And that's it. If you have any issues implementing this please reach out to your Bitmovin and Nagra representatives.