Skip to main content

DRM Encryption (CBCS)

DRM Encryption (CBCS) allows you to use a single set of encryption keys for both FairPlay and Widevine DRM. By this we can create a single set of encrypted media files and use them for both Widevine and FairPlay.

Shaka Packager Command

To encrypt your content using Shaka Packager, use the cbcs protection scheme and include both protection systems.

To obtain the DRM Encryption Key, IV, and URI, please check Obtaining DRM Encryption Keys (CBCS).

packager \
in=input.mp4,stream=video,output=video.mp4 \
in=input.mp4,stream=audio,output=audio.mp4 \
--enable_raw_key_encryption \
--keys "label=:key_id=<content_id>:key=<key>:iv=<IV>" \
--protection_scheme cbcs \
--protection_systems Widevine,FairPlay \
--hls_key_uri <HLS_URI> \
--clear_lead 0 \
--hls_master_playlist_output video.m3u8 \
--mpd_output video.mpd

Field Definitions

NameTypeDescriptionRequired
content_idstringA unique identifier for the content (must be a valid UUID).Yes
keystringThe 16-byte hex encryption key used for both DRM systems.Yes
ivstringThe 16-byte hex initialization vector.Yes
HLS_URIstringThe URI used for HLS/FairPlay (e.g., skd://...).Yes

Obtaining DRM Encryption Keys (CBCS)

This API returns encryption metadata compatible with both FairPlay and Widevine.

Endpoint

POST https://app.tpstreams.com/api/v1/{{org_code}}/drm_encryption_keys/

Request Payload

The request body must contain a base64 encoded JSON string and a security signature.

NameTypeDescriptionRequired
org_codestringYour unique organization code.Yes
requeststringBase64 encoded JSON containing the content_id.Yes
signaturestringAES-CBC encrypted SHA1 hash of the request data.Yes

Sample Request Body

{
"request": "eyJjb250ZW50X2lkIjogImNmNmMzMGRkNTBjMTQ5MmU4MjM0NGVhM2UxMzlZGExZCJ9",
"signature": "JzwEMcwgf4Tp1b6o5x0HbM08o7PuXA6XnwTmWeHF0g4="
}

Response

{
"content_id": "cf6c30dd50c1492e82344ea3e139da1d",
"key": "3ab60de900d64edf9cb25a76f81794e6",
"iv": "f70bce4094fd4612abac60d9809c5b0c",
"uri": "skd://e5573f8bb8ac47ea839a65beae73263d"
}

Generating the Request Payload (Python)

Use the following Python script to generate the required request and signature fields. You will need your organization's AES Signing Key and IV (provided in your dashboard).

import base64
import binascii
import hashlib
import json

from Cryptodome.Cipher import AES
from Cryptodome.Util.Padding import pad

def generate_signature(data, key, iv):
hash = hashlib.sha1(data.encode()).digest()
cipher = AES.new(
binascii.unhexlify(key),
AES.MODE_CBC,
binascii.unhexlify(iv),
)
padded_hash = pad(hash, AES.block_size, style="pkcs7")
signature = cipher.encrypt(padded_hash)
return base64.b64encode(signature).decode()

key = "xxxx" # AES Signing key
iv = "yyy" # AES Signing iv
data = {
"content_id": "cf6c30dd50c1492e82344ea3e139da1d"
}
data = json.dumps(data, separators=(',', ':'))
signature = generate_signature(data, key, iv)
result = base64.urlsafe_b64encode(data.encode()).decode()

post_data = {
"request": result,
"signature": signature
}