展示我们如何使用Spring WebFlux实现视频流。这将比您想象的要简单得多,因为 Spring 为我们完成了所有繁重的工作。这是一个简单有趣的项目,用于演示 Spring WebFlux 的工作原理。
需求用例
您通过Netflix观看电影 或通过YouTube 观看视频教程时,浏览器客户端不会下载整个视频内容。它首先获取一些内容。在播放内容时,它还会以流式传输方式获取接下来的几个块。这样我们就可以让用户在点击某个视频时立即与视频互动,而不是让用户等待下载整个内容。
很多时候,用户也会通过点击/拖动搜索栏来尝试在中间的某个地方观看视频,如上图所示。在这种情况下,不需要从一开始就获取视频块。相反,客户端将请求服务器从特定字节索引提供视频内容。服务器将接受字节范围请求并相应地提供内容。
我们将开发一个简单的应用程序来提供视频内容。我们将有一个 HTML UI。当用户点击播放按钮时,服务器会收到请求并播放内容。
用户可以随时调整搜索栏以观看视频。
开发过程
当我们点击播放按钮时,它会向服务器发送一个请求到一个端点(http://localhost:8080/video/tom-jerry)
<video src="video/tom-jerry" width="720px" height="480px" controls preload="none"> |
服务类非常简单。只需获取Resource对象并返回即可。
@Service |
下面是控制器——我们在这里获取视频标题名称并加载相应的视频资源。
- Range 请求标头包含客户端可能发送的字节范围请求。
- 我没有使用 Range 请求标头,只是在控制台上打印它。但是 Spring 为我们使用了它。我们可以在演示中看到。
- 不要忘记添加内容类型“ video/mp4 ”。
@RestController |
就是这样。这很简单。运行应用程序。
curl http://localhost:8080/video/tom-jerry -i -H "Range: bytes=0-500"
- 我们可以在服务器端看到如下所示的输出。
- 它表明它已收到请求头中的字节范围。
2021-08-22 16:02:08.845 INFO 25964 --- [ main] o.s.b.web.embedded.netty.NettyWebServer : Netty started on port 8080 |
- curl 客户端响应可能是这样的。
- 注意HTTP – 206状态代码,因为它是部分内容。
- 视频总长度为21589849字节。
- 我们收到了0-500个字节,即501 个字节。
- 在标头之后,以字节为单位的响应不是可读格式。让我们不用担心。
HTTP/1.1 206 Partial Content |
- 我们可以调整字节范围并相应地接收视频响应。
- 现在让我们访问 HTML 页面并单击播放按钮。
- 我们可以看到许多请求(按顺序)到服务器以获取视频内容。
- 检查状态代码为 206 的服务器响应,说它是部分内容。
- 您可以调整搜索栏,我们将看到为部分字节内容发送了一个新请求。
Spring WebFlux 还支持功能端点。除了 RestController,我们还可以使用功能端点提供内容,如下所示。
@Configuration |
- 在这种情况下,视频标签 src 应如下所示。
<video src="fun-ep/video/tom-jerry" width="720px" height="480px" controls preload="none"> |
我们能够使用 Spring WebFlux成功演示视频流。我们还了解到,我们没有做任何特殊的事情来处理 HTTP Range 请求,因为 Spring 会处理它。
源代码可在此处获得。