FlixTube开发与测试深度解析
1. FlixTube开发测试概述
在开发过程中,测试是至关重要的环节。虽然手动测试是可行且必要的,但自动化测试在效率、可靠性和可重复性方面具有明显优势。我们将使用Jest和Cypress对FlixTube应用进行测试。
1.1 使用Jest测试微服务
FlixTube中的元数据微服务包含了Jest单元测试。在运行测试之前,需要安装依赖:
cd chapter-9/example-1/metadata
npm install
使用标准的npm测试脚本运行测试:
npm test
也可以使用实时重新加载模式运行测试,这样在编辑代码时,测试会自动重启:
npm run test:watch
1.2 使用Cypress测试应用
我们还可以使用Cypress对FlixTube应用进行端到端测试。运行此测试前,需要安装FlixTube项目的依赖:
cd chapter-9/example-1
npm install
确保应用已经启动:
docker-compose up --build
运行常规的npm测试脚本,该脚本配置为调用Cypress:
npm test
在开发过程中,可以使用
test:watch
脚本启动Cypress UI:
npm run test:watch
2. FlixTube深入剖析
在将FlixTube部署到生产环境之前,我们需要深入了解其一些细节,包括数据库固定装置、模拟存储微服务、网关、用户界面、视频流和视频上传等方面。
2.1 数据库固定装置
数据库固定装置可用于在运行自动化测试之前,向数据库加载逼真的数据集。在不同的测试场景中,对数据的处理方式不同:
-
Jest单元测试
:不需要任何数据,因为我们模拟了MongoDB数据库库,用模拟版本提供的假数据替换了真实数据。
-
Jest集成测试
:可以通过直接使用MongoDB库在测试代码中与MongoDB数据库进行交互,测试数据可以内联在测试代码中。
-
Cypress端到端测试
:由于Cypress测试在浏览器中运行,无法访问MongoDB库,因此创建了数据库固定装置REST API来解决这个问题。
数据库固定装置的示例代码如下:
const mongodb = require("mongodb");
module.exports = [
{
_id:
➥ mongodb.ObjectId("5ea234a1c34230004592eb32"),
name: "SampleVideo_1280x720_1mb.mp4"
},
{
_id:
➥ mongodb.ObjectId("5ea234a5c34230004592eb33"),
name: "Another video.mp4"
}
];
数据库固定装置可以使用JSON格式或JavaScript,JSON适用于静态数据,JavaScript则适合生成动态数据。
2.2 模拟存储
为了方便开发,我们将视频存储微服务的Azure版本替换为模拟版本。模拟存储微服务仍然可以完成存储工作,但它将视频存储在本地文件系统中,而不是使用云存储。
模拟存储微服务在Docker Compose文件中的设置如下:
video-storage:
image: mock-storage
build:
context: ./mock-storage
dockerfile: Dockerfile-dev
container_name: video-storage
volumes:
- /tmp/mock-storage/npm-cache:/root/.npm:z
- ./mock-storage/src:/usr/src/app/src:z
- ./mock-storage/storage:
➥ /usr/src/app/storage:z
ports:
- "4005:80"
environment:
- PORT=80
restart: "no"
如果需要测试真实的存储微服务,可以在Docker Compose文件中交换模拟版本和真实版本的配置。
模拟存储微服务的代码如下:
const express = require("express");
const fs = require("fs");
const path = require("path");
const app = express();
const storagePath =
➥ path.join(__dirname, "../storage");
app.get("/video", (req, res) => {
const videoId = req.query.id;
const localFilePath = path.join(storagePath, videoId);
res.sendFile(localFilePath);
});
app.post("/upload", (req, res) => {
const videoId = req.headers.id;
const localFilePath = path.join(storagePath, videoId);
const fileWriteStream =
➥ fs.createWriteStream(localFilePath);
req.pipe(fileWriteStream)
.on("error", err => {
console.error("Upload failed.");
console.error(err && err.stack || err);
})
.on("finish", () => {
res.sendStatus(200);
});
});
const port = process.env.PORT && parseInt(process.env.PORT) || 3000;
app.listen(port, () => {
console.log(`Microservice online`);
});
2.3 网关
FlixTube有一个单一的网关微服务,它是用户进入应用的入口。网关提供前端用户界面,允许用户在浏览器中与FlixTube交互,同时还提供REST API,使前端能够与后端进行交互。
网关的一个重要功能是将HTTP请求转发到集群中。更高级的网关可能会有REST API路由,向多个内部微服务发出请求,并将多个响应集成到一个响应中返回给前端。
2.4 用户界面(UI)
FlixTube的用户界面是一个传统的服务器渲染网页,而不是现代的单页应用(SPA)。它使用Express和Handlebars模板引擎进行服务器端渲染,前端使用普通的HTML、CSS和JavaScript,没有使用复杂的现代框架。
渲染视频列表网页的网关代码如下:
app.get("/", (req, res) => {
http.request(
{
host: `metadata`,
path: `/videos`,
method: `GET`,
},
(response) => {
let data = "";
response.on("data", chunk => {
data += chunk;
});
response.on("end", () => {
res.render("video-list", {
➥ videos: JSON.parse(data).videos });
});
response.on("error", err => {
console.error("Failed to get video list.");
console.error(err || `Status code:
➥ {response.statusCode}`);
res.sendStatus(500);
});
}
).end();
});
视频列表网页的Handlebars模板如下:
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>FlixTube: Home</title>
<link rel="stylesheet"
➥ href="css/tailwind.min.css">
<link rel="stylesheet" href="css/app.css">
</head>
<body>
<div class="flex flex-col">
<div class="border-b-2 bg-gray-100">
<div class="nav flex flex-row items-center mt-1 p-2">
<div class="text-xl font-bold">
FlixTube
</div>
<div class="ml-16 border-b-2 border-blue-600">
<a href="/">Videos</a>
</div>
<div class="ml-4">
<a href="/upload">Upload</a>
</div>
<div class="ml-4">
<a href="/history">History</a>
</div>
</div>
</div>
<div class="m-4">
<h1>Videos</h1>
<div id="video-list" class="m-4">
{{#if videos}}
{{#each videos}}
总结
通过对FlixTube的测试和深入剖析,我们了解了其在开发过程中的测试方法、数据库固定装置的使用、模拟存储微服务的配置、网关的功能以及用户界面的实现。这些知识有助于我们更好地开发和维护FlixTube应用。
以下是一个简单的流程图,展示了FlixTube的测试和部署流程:
graph TD
A[开发FlixTube] --> B[使用Jest和Cypress进行测试]
B --> C{测试是否通过}
C -- 是 --> D[深入剖析FlixTube细节]
D --> E[部署到生产环境]
C -- 否 --> A
表格展示不同测试场景下的数据处理方式:
| 测试场景 | 数据处理方式 |
| ---- | ---- |
| Jest单元测试 | 模拟数据库库,使用假数据 |
| Jest集成测试 | 直接使用MongoDB库与数据库交互,测试数据内联 |
| Cypress端到端测试 | 使用数据库固定装置REST API |
2.5 视频流
视频流功能是FlixTube的重要组成部分,它允许用户在应用中流畅地观看视频。在模拟存储微服务中,我们已经看到了处理视频流的代码示例。当用户请求视频时,模拟存储微服务会从本地文件系统中读取视频文件并将其发送给用户。
以下是模拟存储微服务中处理视频流的关键代码:
app.get("/video", (req, res) => {
const videoId = req.query.id;
const localFilePath = path.join(storagePath, videoId);
res.sendFile(localFilePath);
});
在这个代码中,当接收到
/video
的GET请求时,会根据请求中的
id
参数找到对应的本地视频文件,并使用
res.sendFile
方法将文件发送给客户端。
2.6 视频上传
视频上传功能允许用户将自己的视频上传到FlixTube应用中。模拟存储微服务同样处理了视频上传的逻辑。当用户上传视频时,请求会被发送到模拟存储微服务的
/upload
端点。
以下是模拟存储微服务中处理视频上传的代码:
app.post("/upload", (req, res) => {
const videoId = req.headers.id;
const localFilePath = path.join(storagePath, videoId);
const fileWriteStream =
➥ fs.createWriteStream(localFilePath);
req.pipe(fileWriteStream)
.on("error", err => {
console.error("Upload failed.");
console.error(err && err.stack || err);
})
.on("finish", () => {
res.sendStatus(200);
});
});
在这个代码中,当接收到
/upload
的POST请求时,会根据请求头中的
id
参数确定视频文件的存储路径,然后使用
fs.createWriteStream
创建一个写入流,将请求体中的视频数据写入到本地文件中。如果上传成功,会返回状态码200。
不同功能的操作步骤总结
| 功能 | 操作步骤 |
|---|---|
| 使用Jest测试微服务 |
1. 进入元数据微服务目录:
cd chapter-9/example-1/metadata
;2. 安装依赖:
npm install
;3. 运行测试:
npm test
;4. 若需实时重新加载模式:
npm run test:watch
|
| 使用Cypress测试应用 |
1. 进入项目目录:
cd chapter-9/example-1
;2. 安装依赖:
npm install
;3. 启动应用:
docker-compose up --build
;4. 运行测试:
npm test
;5. 若需启动Cypress UI:
npm run test:watch
|
| 切换存储微服务 | 1. 打开Docker Compose文件;2. 注释掉模拟存储微服务的配置;3. 取消注释真实存储微服务的配置;4. 重新构建并重启应用 |
未来展望
虽然目前FlixTube只有一个单一的网关,但随着应用的发展,可能会需要多个网关来满足不同前端的需求,例如为网页浏览器、移动应用和管理门户分别设置网关。这就是所谓的“后端为前端服务”(Backends for Front Ends)模式。
如果采用多个网关,我们可以使用不同的主机名或子域名来访问它们,例如
flixtube.com
用于网页浏览器,
mobile.flixtube.com
用于移动应用,
admin.flixtube.com
用于管理门户。
以下是一个流程图,展示了FlixTube未来可能的架构:
graph LR
A[用户] --> B[网页浏览器]
A --> C[移动应用]
A --> D[管理门户]
B --> E[网页网关]
C --> F[移动网关]
D --> G[管理网关]
E --> H[内部微服务]
F --> H
G --> H
总结
本文对FlixTube应用进行了全面的分析,包括开发过程中的测试方法、数据库固定装置的使用、模拟存储微服务的配置、网关的功能、用户界面的实现、视频流和视频上传功能。同时,我们还探讨了FlixTube未来可能的发展方向,如采用多个网关的架构。通过深入了解这些内容,我们可以更好地开发、维护和扩展FlixTube应用,为用户提供更好的视频服务体验。
希望这些信息对您在开发类似的视频应用时有所帮助,您可以根据实际需求对FlixTube的架构和功能进行调整和优化。如果您在实践过程中有任何问题或想法,欢迎在评论区留言讨论。
超级会员免费看

被折叠的 条评论
为什么被折叠?



