Android 端播放 HLS 加密视频

最近更新时间:2024-09-19 18:01:57

我的收藏
本文主要介绍如何在 Android 端播放 HLS 私有加密视频。

前置步骤

创建加密视频搭建 token 服务,详情请参见 HLS 视频加密播实践

Android 端播放指引

Android 端使用 ci-assistor.aar 中封装好的 CIPlayerAssistor 和 CIMediaInfo 对象来播放 m3u8 文件,用户按照如下规则传入参数,即可实现播放功能。
1. 集成 CIPlayerAssistor SDK。
集成 SDK:ci-assistor.aar
依赖 nanohttpd
implementation 'org.nanohttpd:nanohttpd:2.3.1'
2. 构造 CIMediaInfo 对象,参数说明如下。
参数名
说明
是否必填
类型
默认值
mediaUrl
请求m3u8接口的文件地址
string
setToken
设置token
function
setAuthorization
设置授权签名信息
function
3. 使用 CIPlayerAssistor 获取最终的播放 url。
// 1. 初始化万象播放协助器,例如可以在APP启动时
CIPlayerAssistor.getInstance().init(context);

// 2. 获取最终的播放url
String playerUrl = CIPlayerAssistor.getInstance().buildPlayerUrl(ciMediaInfo);

// 3. 注意:不再使用播放器助手后,请释放CIPlayerAssistor资源,例如APP退出时
CIPlayerAssistor.getInstance().destroy();
完整的 Android 端示例请参考如下代码。
// 初始化万象播放协助器,例如可以在APP启动时
CIPlayerAssistor.getInstance().init(context);

// 原始的媒体url,请替换成您业务的url,此处url仅为示例
String mediaUrl = "https://ci-h5-bj-1258125638.cos.ap-beijing.myqcloud.com/hls/BigBuckBunny.m3u8?ci-process=pm3u8";

// CIMediaInfo实例,可用于请求token
CIMediaInfo ciMediaInfo = new CIMediaInfo(mediaUrl);

// 从业务服务器获取token和授权信息: 自行实现getTokenAndAuthoriz方法(可参考下一块代码示例)
Pair<String, String> pair = getTokenAndAuthorization(ciMediaInfo.getMediaUrl(), ciMediaInfo.getPublicKey());
// 获取到token
String token = pair.first;
// 获取到授权信息,例如 q-sign-algorithm=sha1&q-ak=XXXXXXX&q-sign-time=1706098529;1706102129&q-key-time=1706098529;1706102129&q-header-list=&q-url-param-list=ci-process&q-signature=XXXXXXX
String authorization = pair.second;

// 给ciMediaInfo设置获取到的token
ciMediaInfo.setToken(token);
// 设置授权信息,会在url上通过&拼接传入的authorization
// 如果原始url是cdn的话,不用传cos的authorization
ciMediaInfo.setAuthorization(authorization);

// 获取最终的播放url(此链接只能播放一次,请不要重复使用,buildPlayerUrl非耗时方法,可以多次调用)
String playerUrl = CIPlayerAssistor.getInstance().buildPlayerUrl(ciMediaInfo);

// 将playerUrl设置给播放器即可,demo中演示了exoplayer和腾讯云播放器

// 以下以exoplayer作为代码示例
PlayerView playerView = view.findViewById(R.id.video_view);
ExoPlayer player = new ExoPlayer.Builder(getActivity()).build();
playerView.setPlayer(player);
MediaItem mediaItem = MediaItem.fromUri(playerUrl);
HlsMediaSource mediaSource = new HlsMediaSource.Factory(dataType ->
new DefaultHttpDataSource.Factory().createDataSource()createMediaSource(mediaItem);
player.prepare(mediaSource);
player.play();

// 注意:不再使用播放器助手后,请释放CIPlayerAssistor资源,例如APP退出时
CIPlayerAssistor.getInstance().destroy();
从业务服务器获取 token 和签名的示例代码如下。
/** * 从业务服务器获取token和授权 */ private Pair<String, String> getTokenAndAuthorization(String mediaUrl, String publicKey) { HttpURLConnection urlConnection = null; try { // 该url仅为示例,请替换成您业务的url,具体实现请参考 “业务后端示例代码” URL url = new URL("https://cos.cloud.tencent.com/samples/hls/token"); urlConnection = (HttpURLConnection) url.openConnection(); urlConnection.setRequestMethod("POST"); urlConnection.setDoOutput(true); urlConnection.setRequestProperty("Content-Type", "application/json"); JSONObject jsonObject = new JSONObject(); // 添加键值对到JSONObject jsonObject.put("src", mediaUrl); jsonObject.put("protectContentKey", 1); jsonObject.put("publicKey", publicKey); // 将JSONObject转换为字符串 String jsonInputString = jsonObject.toString(); byte[] input = jsonInputString.getBytes("utf-8"); urlConnection.getOutputStream().write(input, 0, input.length); int status = urlConnection.getResponseCode(); if (status != 200) { throw new RuntimeException("HttpResponseCode: " + status); } else { BufferedReader br = new BufferedReader(new InputStreamReader(urlConnection.getInputStream(), "utf-8")); StringBuilder response = new StringBuilder(); String responseLine; while ((responseLine = br.readLine()) != null) { response.append(responseLine.trim()); } String responseString = response.toString(); Log.d("getToKen:", responseString); JSONObject json = new JSONObject(responseString); String token = json.getString("token"); String authorization = json.getString("authorization"); // 在这里你可以使用token和authorization return new Pair<>(token, authorization); } } catch (Exception e) { e.printStackTrace(); throw new RuntimeException(e); } finally { if (urlConnection != null) { urlConnection.disconnect(); } } }

Demo 体验

我们提供了终端播放 HLS 私有加密视频的示例,请参见 CIPlayerAssistor Demo