问题描述
我正在处理一个需要播放 HLS 加密视频 (.m3u8) 文件的项目。我正在使用 CloudFront 和签名 cookie 来保护内容。我可以在没有签名 cookie 的情况下播放 .m3u8 文件,但是当我使用签名 cookie 时,cookie 不会发送请求。
我正在使用 CloudFront 分配的备用域,并且我确认除了 .m3u8 文件之外,我可以使用签名的 cookie 访问所有其他文件。
经过研究,我发现如果我像下面的代码那样将 withCredentials
设置为 true,那么签名的 cookie 将在请求中发送:
player.ready(function() {
player.src({
src: 'https://protected.example.com/output-plain/art.m3u8',type: 'application/x-mpegURL',withCredentials: true
});
});
此代码有效并且签名的 cookie 正在请求中发送,但是我开始收到一个新错误:
Access to XMLHttpRequest at 'https://protected.example.com/output-plain/art.m3u8undefined' from origin 'https://example.com' has been blocked by CORS policy: The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'. The credentials mode of requests initiated by the XMLHttpRequest is controlled by the withCredentials attribute.
然后我发现我必须将 Access-Control-Allow-Credentials
设置为 true。但是,这对我不起作用。
我正在使用 video.js 库,我也尝试过 hls.js 并得到相同的错误并卡在同一个地方。
我在过去 7 天一直被困在这个问题上,我认为 AWS 文档真的太多了,我已经提到了很多关于 SO 的问题和 Github 上的问题,但仍然没有运气。希望有人能在这里帮助我。
以下是 CloudFront 分发行为的屏幕截图:
这是我的 php 和 js 代码; index.php:
<?php
header("Access-Control-Allow-Origin: https://protected.example.com");
header("Access-Control-Allow-Credentials: true");
header("Access-Control-Max-Age: 1000");
header("Access-Control-Allow-Headers: X-Requested-With,Content-Type,Origin,Cache-Control,Pragma,Authorization,Accept,Accept-Encoding");
header("Access-Control-Allow-Methods: PUT,POST,GET,OPTIONS,DELETE");
?>
<!DOCTYPE html>
<html>
<head>
<link href="https://vjs.zencdn.net/7.10.2/video-js.css" rel="stylesheet" />
</head>
<body>
<video
id="video_player"
class="video-js"
controls
preload="auto"
poster="//vjs.zencdn.net/v/oceans.png"
data-setup='{}'
width=600 height=300>
</video>
<script src="https://vjs.zencdn.net/7.10.2/video.js"></script>
<script>
var player = videojs('video_player')
player.responsive(true);
player.ready(function() {
player.src({
src: 'https://protected.example.com/output-plain/art.m3u8',withCredentials: true
});
});
</script>
</body>
</html>
这是 S3 反抗 CORS 政策:
[
{
"AllowedHeaders": [
""
],"AllowedMethods": [
"POST","GET","PUT","HEAD"
],"AllowedOrigins": [
"*"
],"ExposeHeaders": []
}
]
提前致谢。
解决方法
答案在浏览器的错误消息中,“当请求的凭据模式为‘包含’时,响应中‘Access-Control-Allow-Origin’标头的值不能是通配符‘*’。”您的 S3 存储桶的 CORS 策略不能对 AllowedOrigins 值使用通配符。
此外,您的空 AllowedHeaders 值可能会从预检请求检查中删除 Host 值,因此为了安全起见,让我们将其设置为通配符。
如果您将 S3 存储桶的 CORS 策略更新为此,它应该可以解决问题:
[
{
"AllowedHeaders": [
"*"
],"AllowedMethods": [
"POST","GET","PUT","HEAD"
],"AllowedOrigins": [
"https://example.com","https://protected.example.com"
],"ExposeHeaders": []
}
]