簡介
阿裡雲視訊點播服務提供了試看的完整解決方案,您可自由設定試看時長(或觀看完整視訊),播放服務會根據設定提供含有試看限制的特定的播放位址,可借此來實作完整的試看功能。
使用前提
試看的基本原理是,播放的 CDN 加速位址帶有試看的指定時長資訊,雲端會對該資訊進行鑒權,鑒權通過會傳回指定的檔案内容,否則拒絕通路、傳回 403。
- 點播試看功能基于阿裡雲 CDN 加速實作,且必須在視訊點播 (VOD) 控制台配置 CDN 加速域名。
- 此方案必須開啟 A 鑒權,同時,為了防止試看參數被篡改,試看參數也作為 auth_key 計算的一部分。
- 域名必須開啟 range 回源和拖拽播放。具體可在域名管理 > 配置 (對應域名處)> 視訊相關處開啟。
使用步驟
-
首先将需要試看的域名開啟試看功能,具體可參見配置方式。
說明 如果域名沒有開啟試看,則請求點播時不能攜帶試看參數,否則傳回的位址不能通路。
- 請求點播的播放服務,在請求時帶試看參數,指定所需要試看的時間,具體可參見試看位址擷取。
- 點播傳回試看位址。
- 客戶根據此位址通路 CDN,此位址隻傳回試看所需要的時長資料。
流程示例

配置方式
登入點播控制台,【媒體處理配置】>【分發加速配置】>【域名管理】>【選擇域名 - 配置】>【通路控制】>【URL 鑒權】,開啟 A 方式鑒權,同時打開支援試看開關。
試看位址擷取
通過點播擷取
說明
- 隻有配置 CDN 加速域名的情況,才支援試看功能。
- 如果域名沒有開啟試看,則請求點播時不能攜帶試看參數,否則傳回的位址不能通路。
- 目前支援的檔案格式為 mp4、m3u8。
- 由于試看時間與關鍵幀存在依賴 (點播轉碼輸出檔案預設 10 秒一個關鍵幀,可在轉碼模闆修改),是以短視訊不建議使用試看,長視訊試看時間建議至少設定為 30 秒。
- m3u8 檔案試看精度為 ts 分段時長,具體可能存在誤差,采用最大化原則,即 10 秒一個 ts,試看 15 秒,實際傳回資料為 20 秒。
調用時,您可以設定
PlayConfig結構中的 PreviewTime 來擷取指定時長的播放試看位址。
示例代碼如下:
package com.ali.vod.test;
import com.alibaba.fastjson.JSONObject;
import com.aliyun.oss.ClientException;
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.profile.DefaultProfile;
import com.aliyuncs.vod.model.v20170321.GetPlayInfoRequest;
import com.aliyuncs.vod.model.v20170321.GetPlayInfoResponse;
/**
* @author wb-zzb
* @date 2020/6/3
*/
public class VodPreviewTest {
public static void main(String[] args) {
//請根據點播服務接入區域填寫,詳情參見點播服務接入區域(https://help.aliyun.com/document_detail/98194.html?spm=a2c4g.11186623.6.612.51c6534bqLs9Wd)
String regionId = "cn-shanghai";
String accessKeyId = "<your accessKeyId>";
String accessKeySecret = "<your accessKeySecret>";
String videoId = "595d020bad3*****f37433451720";
DefaultAcsClient client = InitVodClient(regionId, accessKeyId, accessKeySecret);
GetPlayInfoResponse response = null;
try {
response = getPlayInfo(client, videoId);
} catch (Exception e) {
e.printStackTrace();
}
System.out.println("response = " + JSONObject.toJSONString(response));
}
/**
* 初始化Client
*
* @param regionId
* @param accessKeyId
* @param accessKeySecret
* @return
* @throws ClientException
*/
public static DefaultAcsClient InitVodClient(String regionId, String accessKeyId, String accessKeySecret) throws ClientException {
DefaultProfile profile = DefaultProfile.getProfile(regionId, accessKeyId, accessKeySecret);
DefaultAcsClient client = new DefaultAcsClient(profile);
return client;
}
/**
* 擷取視訊播放位址
*
* @param client
* @param videoId
* @return
* @throws Exception
*/
public static GetPlayInfoResponse getPlayInfo(DefaultAcsClient client, String videoId) throws Exception {
GetPlayInfoRequest request = new GetPlayInfoRequest();
request.setVideoId(videoId);
//設定過期時間,機關秒,不設定,預設3600s
request.setAuthTimeout(3600L);
request.setFormats("mp4");
JSONObject playConfig = new JSONObject();
//視訊點播試看時長,機關為秒。最小值1
playConfig.put("PreviewTime", "30");
request.setPlayConfig(playConfig.toJSONString());
return client.getAcsResponse(request);
}
}
自行計算
- 在生成 authkey 時如果有試看參數,計算 md5hash 時要帶上試看時長參數,即在原來 URL 鑒權 md5hash 計算方式的基礎上,加入試看時長的計算。試看 md5hash 的計算方法為 MD5 (uri-timestamp-rand-uid-auth_key-preview_time)。
- 在最後加上 & end={試看時長},如果需要看完整視訊,試看參數不設定即可,并且不參與進行 auth_key 計算。
private String generateRand() {
return UUID.randomUUID().toString().replaceAll("-", "");
}
public String genAuthKey(String object, String privateKey, Long expireTime, Long previewTime) {
String rand = "0";
String uid = "0";
if (StringUtils.isBlank(privateKey)) {
return "";
}
rand = generateRand();
long timestamp = System.currentTimeMillis() / 1000 + (expireTime == null ? 0 : expireTime);
String authStr = timestamp + "-" + rand + "-" + uid;
String md5Str = object + "-" + authStr + "-" + privateKey;
if(previewTime!=0)
md5Str = md5Str + "-" + previewTime;
String auth_key = authStr + "-" + MD5Util.md5( md5Str);
return auth_key;
}
public void previewTest() throws Exception {
try {
String key = "your cdn auth key";
String fileUrl = "http://test.yourdomain.com/test/bee21427ca3346848835c1bd786054c5-19bd8528c1d51576cd726cf86471ca0****.mp4";
URL url = new URL(fileUrl);
String file = url.getFile();
Long previewtime = 120L;
Long expireTime = 1800L;
String auth_key =genAuthKey(file, key, expireTime, previewtime);
fileUrl = fileUrl + "?auth_key=" + auth_key;
if(previewtime != 0)
fileUrl = fileUrl + "&end=" + previewtime;
System.out.println(fileUrl);
} catch (Exception e) {
e.printStackTrace();
}
}
「視訊雲技術」你最值得關注的音視訊技術公衆号,每周推送來自阿裡雲一線的實踐技術文章,在這裡與音視訊領域一流工程師交流切磋。