** 背景介绍**

HLS视频加密是一种基于HTTP Live Streaming(HLS)协议的加密技术。它的核心思想是将视频切片进行加密处理,在客户端播放时需要先获取解密密钥才能正常偶发。通过这种方式,HLS加密可以有效防止未经授权的第三方窃取视频内容,从而保障了视频内容的版权和安全。数据万象媒体处理服务提供了一套HLS视频加密方案,方便用户各个场景的需求。

** HLS加密方案**

整体加密方案如下图所示:

** 痛点**

在我们日常的工作生活中,如果没有HLS加密,会带来以下问题:

视频内容被非法下载和分享:没有加密的视频内容容易被非法下载和分享,导致付费业务受到威胁。

影响用户体验:为了提高视频的安全性,可能需要采用更复杂的验证和授权机制。这可能会增加用户的操作复杂度,降低用户体验。

增加服务器的负担:如果采用客户端解密的技术,服务器需要处理更多的请求和计算量,可能会对延迟和性能造成一定的不良影响。

** 使用场景**

直播赛事:体育赛事、音乐会等大型活动需要进行直播,HLS加密可以有效防止盗版和非法传播。

在线教育:在线教育平台需要保护课程内容的版权,HLS加密可以确保课程内容不被非法窃取。

付费视频:电影、电视剧等付费视频内容需要进行版权保护,HLS加密可以有效防止盗版行为。

企业会议:企业的重要会议、内部培训等内容需要进行保密处理,HLS加密可以确保这些内容不被泄露。

** 操作指南**

生成加密视频

一、模版设置

  1. 开通媒体处理

    进入存储桶界面,点击数据处理中的媒体处理,点击开通。

  2. 创建HLS转码模版

    点击任务与工作流里的模版配置,点击创建转码模版

    2.1 输入模版名称,封装格式选择HLS。

2.2 打开视频加密开关

视频参数和音频参数根据需要填写,在高级设置里打开视频加密开关

二、创建转码任务

在当前存储桶上传任意视频文件,点击任务管理里的创建任务。

  1. 生成m3u8加密文件

    源文件路径选择刚刚上传的视频文件,模版类型选择自定义模版,选择第二步创建的hls转码模版,记住目标路径和目标文件名,产出文件就是我们需要的加密视频文件。

  2. 确定产物文件

    找到创建任务时填的产物路径,可看到生成后的加密文件

播放加密视频

控制台媒体处理,视频加密配置模块,展示播放密钥(playKey,部署后端服务的时候会用到)

拿到生成的m3u8视频文件和播放秘钥(playKey)后,就可以开始搭建服务,播放刚刚加密的m3u8视频文件。

本文前端部分以js代码为例,服务端以nodejs为例,来说明整个使用过程。

三、前端部分

  1. 首先下载hls加密代码包(https://bjtest-10008930.cos.ap-shanghai.myqcloud.com/hlsCode/hls加密代码包.zip)
  2. 在页面中引入压缩包中cos_hls.js、jsencrypt.js 和 hls.js。
  3. 根据播放器种类,在页面中引入压缩包中文件,目前支持三种类型(hls.js/tcplayer/video.js)。

hls.js:

<script src="./cos_hls.js"></script>
<script src="./hls.js"></script>
<script src="./jsencrypt.js"></script>

tcplayer:

<link href="https://web.sdk.qcloud.com/player/tcplayer/release/v4.2.2/tcplayer.min.css" rel="stylesheet"/>
<script src="https://web.sdk.qcloud.com/player/tcplayer/release/v4.2.2/libs/hls.min.0.13.2m.js"></script>
<script src="https://web.sdk.qcloud.com/player/tcplayer/release/v4.2.2/tcplayer.v4.2.2.min.js"></script>
<script src="./cos_hls.js"></script>
<script src="./jsencrypt.js"></script>

video.js:

<link href="https://vjs.zencdn.net/8.11.8/video-js.css" rel="stylesheet" />
<script src="https://vjs.zencdn.net/8.11.8/video.js"></script>
<script src="./cos_hls.js"></script>
<script src="./jsencrypt.js"></script>
  1. 前端使用cos_hls.js文件中封装好的cosHls对象来播放m3u8文件,用户按照如下规则传入参数,即可实现播放功能。
<script>
// cosHLs为cos_hls.js封装的对象,使用play方法播放视频文件
cosHls.play({
// video标签的id
container: 'video',
// 支持的播放器种类(hls.js/tcplayer/video.js)
playerType: 'hls.js',
// 请求m3u8接口的文件地址
src: 'https://examplebucket-1250000000.cos.ap-beijing.myqcloud.com/hls/video.m3u8?ci-process=pm3u8',
// 标记src里的域名是不是CDN域名(false/true)
// useCdn: false,
// 请求token和签名的函数
getToken(opt, callback) {
// 加密公钥,不需要用户填写,sdk会自动生成
var publicKey = opt.publicKey;
// 请求m3u8接口的文件地址,不需要用户填写,sdk会自动生成
var src = opt.src;
// 是否返回加密内容,与cosHls对象的ProtectContentKey参数保持一致,不需要用户填写,sdk会自动生成
var protectContentKey = opt.ProtectContentKey;
// 新建xhr对象,进行请求
var xhr = new XMLHttpRequest();
xhr.withCredentials = true;
// /samples/hls/token为自定义请求地址,用户可自自定义
xhr.open('POST', `/hls/token`, true);
xhr.setRequestHeader('Content-Type', 'application/json')
// 请求成功返回authorization 和 token
xhr.onload = function () {
var r = JSON.parse(xhr.responseText);
var authorization = r.authorization
var token = r.token
callback(null, {authorization, token});
};
xhr.onerror = function () {
callback('get token error');
};
// node服务所需要的参数,已从sdk获取,不需要用户填写
var data = {
src: src,
publicKey: window.btoa(publicKey),
protectContentKey: protectContentKey
};
xhr.send(JSON.stringify(data));
}
})
</script>

四、服务端部分

服务端,以 Nodejs 为例,主要代码如下:

const COS = require('cos-nodejs-sdk-v5');
const base64Url = require('base64-url');
const express = require('express');
const crypto = require('crypto'); // 配置参数
const config = {
// 获取腾讯云密钥,建议使用限定权限的子用户的密钥 https://console.cloud.tencent.com/cam/capi
secretId: process.env.SecretId,
secretKey: process.env.SecretKey,
// 播放秘钥,可在媒体处理模块获取 https://console.cloud.tencent.com/cos/bucket?bucket=xxxx-100000&region=ap-xxx&type=ci&anchorType=video
playKey: process.env.playKey,
// 目标存储桶名称,可在存储桶列表页获取 https://console.cloud.tencent.com/cos/bucket
bucket: 'xxx',
// 目标存储桶地域,可在存储桶列表页获取 https://console.cloud.tencent.com/cos/bucket
region: 'xxx'
}; // 创建临时密钥服务和用于调试的静态服务
const app = express(); app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true })); router.post('/hls/token', (req, res, next) => {
// 从接口拿到文件地址,加密公钥,是否返回加密内容
const body = req.body;
const src = body.src;
const publicKey = body.publicKey;
const protectContentKey = body.protectContentKey; // 如在某些特殊场景需要用HLS标准加密(例如小程序里播放/iOSWebview),可以去掉下面的限制判断并做好来源限制只允许小程序来源。
// 代码示例只允许 protectContentKey 传 1,原因:如果允许传入 0 播放流程会走 HLS 标准加密会有风险。
const userAgent = req.headers['user-agent'] || '';
const uaWhiteList = ['Safari', 'wechatdevtools', 'MiniProgramEnv'];
const isUaAllow = uaWhiteList.some(item => userAgent.includes(item));
// 只有白名单的浏览器,才能走标准加密
if (!protectContentKey && !isUaAllow) {
res.status(400);
return res.send({code: -1, message: 'protectContentKey=0 not allowed'});
} // src 链接校验
if (!src || !srcReg.test(src)) return res.send({code: -1, message: 'src format error'});
if (!publicKey) return res.send({code: -1, message: 'publicKey empty'}); // 解析 url
const { bucket, region } = config;
const { token, authorization } = getToken({publicKey, protectContentKey, bucket, region, src}, res)
res.send({code: 0, message: 'ok', token, authorization});
}); const srcReg = /^https?:\/\/([^/]+)\/([^?]+)/;
const ciHostReg = /^[^.]+\.ci\.[^.]+\.myqcloud\.com$/; function getToken({publicKey, protectContentKey, bucket, region, src}) {
const m = src.match(srcReg);
const srcHost = m[1];
const pathKey = m[2];
const query = {};
const isCiHost = ciHostReg.test(srcHost);
src.replace(/^([^?]+)(\?([^#]+))?(#.*)?$/, '$3').split('&').forEach(item => {
const index = item.indexOf('=');
const key = index > -1 ? item.slice(0, index) : item;
let val = index > -1 ? item.slice(index + 1) : '';
query[key] = decodeURIComponent(val);
});
let objectKey = isCiHost ? query.object : pathKey;
const header = {
"alg": "HS256",
"typ": "JWT"
}
const appId = bucket.slice(bucket.lastIndexOf('-') + 1);
let payload = {
Type: "CosCiToken",
AppId: appId,
BucketId: bucket,
Issuer: "client",
IssuedTimeStamp: Math.floor((new Date().getTime() - 30 * 1000) / 1000),
ProtectSchema: "rsa1024",
PublicKey: publicKey,
ProtectContentKey: protectContentKey || 0,
UsageLimit: 50,
Object: objectKey,
};
let Header = base64Url.encode(JSON.stringify(header))
let PayLoad = base64Url.encode(JSON.stringify(payload))
let data = Header + "." + PayLoad
let hash = crypto.createHmac('sha256', config.playKey).update(data).digest();
let Signature = base64Url.encode(hash);
let token = Header + '.' + PayLoad + '.' + Signature
let authorization = COS.getAuthorization({
SecretId: config.secretId,
SecretKey: config.secretKey,
Method: 'get',
Pathname: `/${objectKey}`,
Query: {'ci-process': 'pm3u8'},
});
return {token, authorization};
}

五、效果体验

完成前后端的代码后,启动服务,即可开始播放加密视频。

在线体验地址:

https://cos.cloud.tencent.com/samples/hls/private-encrypt/

方案接入优势

接入简单:支持多个开源通用播放器,定制化能力强。

支持场景丰富:PC Web、Android WebView,Android/iOS移动端App

不兼容的场景自动降级:因为 iOS Webview 不兼容 Media Source Extensions,会自动降级为标准加密方案。减少开发兼容成本。

总结

数据万象媒体处理新增视频加密,旨在让用户能够更加方便地使用视频加密功能,提高用户体验。同时,我们也会继续关注用户的反馈,不断优化和改进数据万象媒体处理的用户体验,为用户提供更好的服务。

HLS视频加密,让您的视频内容更安全!的更多相关文章

  1. HLS 视频加密小记

    我是在ubuntu中,安装好了 ffmpeg 加密用的 key(生成一个encrypt2.key文件) openssl rand 16 > encrypt2.key 另一个是 iv(生成一段字符 ...

  2. day89:luffy:使用Celery完成我的订单超时取消&Polyv视频加密播放

    目录 1.我的订单超时取消 2.PoliV视频播放 1.我的订单超时取消 使用Celery完成超时取消功能 mycelery/order/tasks.py from mycelery.main imp ...

  3. html里的添加视频特效(美化,丰富内容)

    现在如果要在页面中使用video标签,需要考虑三种情况,支持Ogg Theora或者VP8(如果这玩意儿没出事的话)的(Opera.Mozilla.Chrome),支持H.264的(Safari.IE ...

  4. phpcms视频模块实现列表页打开内容页直接播放视频

    摘自phpcms论坛 原链接地址:http://bbs.phpcms.cn/thread-557691-1-1.html 之前下载研究过“化蝶自在飞”开发的视频模型,发现功能不错,但唯一的缺憾是,我想 ...

  5. 关于ckPlayer 视频加密那些事

    最近疫情期间,公司在做一个在线行业教育收费平台,所以不得不做视频转码/切片/加密. 现在只说视频加密如何实现,找遍了所有百度,几乎没有提供相应的源码和例子. 而ckPlayer官网有一个收费的案例:如 ...

  6. Java 使用blob对H5视频播放进行加密《java视频加密》

    1.创建一个H5 <video>标签 <video id="sound" type="video/mp4" controls="co ...

  7. Android开发之获取本地视频和获取自拍视频

    1.获取本地所有视频 public void getLoadMedia() { Cursor cursor = UILApplication.instance.getApplicationContex ...

  8. C#控制台程序取得INSOYA视频区的视频的真实URL,视频标题,发布时间集合。

    准备工作 起因是因为这个网站:http://i.youku.com/kmsfan 这个是一个叫做冒险岛的游戏的资讯论坛,以前我经常在里面传视频,现在我不玩这个游戏了,但是很多玩家还是经常到我的网站里面 ...

  9. Android 音视频开发(七): 音视频录制流程总结

    在前面我们学习和使用了AudioRecord.AudioTrack.Camera.MediaExtractor.MediaMuxer API.MediaCodec. 学习和使用了上述的API之后,相信 ...

  10. 短视频如何制作?如何下载短视频?常用的短视频录制和剪辑App有哪些?

    当下,娱乐圈最火的是什么?当然是短视频了. 那么,短视频如何制作?短视频如何挣钱?如何下载免费短视频呢?这篇文章就收录了一些相关的短视频文章,加入收藏哦,小编会持续更新本文. 1. iPhone手机上 ...

随机推荐

  1. Task2 - IDA学习【进度 - 第二课】

    学习目标: - 无名侠的课,看二进制培训(第二集和第三集)(https://space.bilibili.com/7761039/video) - 会反汇编 - 会字符串搜索(f12) - 会简单异或 ...

  2. windows 下搭php环境

    windows 下搭php环境(php7.2+mysql5.7+apache2.4) 1. 先下载需要的软件 1) 先去微软官网下载vc,我下载的是2017版中文简体的.网址为https://www. ...

  3. 5.6 函数y=Asin(ωx+φ)的图像和性质

    \({\color{Red}{欢迎到学科网下载资料学习 }}\) [基础过关系列]2022-2023学年高一数学上学期同步知识点剖析精品讲义(人教A版2019) \({\color{Red}{ 跟贵哥 ...

  4. 巅峰对话在线研讨 Q&A:Oracle Database 21c vs openGauss 2.0新特性解读和架构演进

    2021年11月11日,墨天轮<巅峰对话>栏目邀请到了两位数据库领域的巅峰人物:云和恩墨创始人盖国强老师,和来自清华大学计算机与技术系的李国良教授,为大家带来了在线研讨<Oracle ...

  5. Solon 3.0 新特性:SqlUtils

    Solon 3.0 引入了新的 SqlUtils 用于数据库基础操作,SqlUtils 是对 JDBC 较为原始的封装,采用了 Utils API 的风格,极为反普归真. 特性有: 支持事务管理 支持 ...

  6. C#扩展方法 Where Any Count Signal SignalOrDefault First 等方法的使用

    using System; using System.Collections.Generic; using System.Linq; using System.Net.Http; using Syst ...

  7. 08 ELMo模型(双向LSTM模型解决词向量多义问题)

    博客配套视频链接: https://space.bilibili.com/383551518?spm_id_from=333.1007.0.0 b 站直接看 配套 github 链接:https:// ...

  8. 五款扩展组件齐发 —— Volcano、Keda、Crane-scheduler 等,邀你体验

    今年 3 月,KubeSphere 启动了首届扩展组件开发者训练营,吸引了 60 名开发者报名.经过一个半月的密集培训和实战演练,这些开发者成功打造了五款创新的扩展组件,现已全部上架至 KubeSph ...

  9. 下一代云电脑技术来临,为什么PC Farm才是未来,以ToDesk为例

    近年来飞速发展的云电脑技术,正在挤压传统电脑的生存空间.由于用户对电脑计算能力的要求日益增高,而传统电脑往往会受限于硬件性能无法更新,更换花费较高等因素,难以满足用户对高性能电脑的期待. 与此同时,下 ...

  10. WebStorm 和 Rider 现在对非商业用途免费

    JetBrains 在程序员节这一天在官方博客上发布了一篇文章:<WebStorm 和 Rider 现在对非商业用途免费>宣布了JetBrains将WebStorm和Rider IDE对非 ...