TimelineServer: 概述
使用 C++实现的 Web 服务器,代码规范参考的是Google 命名约定
功能
主体框架参照了WebServer项目,同时增加了以下功能:
- 基于注册的静态请求跳转(如”/“跳转到”/index.html”)
- 基于回调函数的动态请求处理(登录/数据库增删改查)
- POST 请求解析(原项目做了”urlencoded”格式请求体的解析,改成了”json”格式的解析)
- 基于”MySQL Connector/C++”的数据库系统(原项目使用的是 C 的数据库函数)
- 利用”gtest”为每一个模块都写了模块测试
代码仓库 | Github
前端代码仓库 | Github
相关笔记 | 遗世の私语
环境安装与测试
配置 mysql
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21安装 mysql 数据库(服务器+客户端)
并配置用户账号密码和代码中对应
参考链接: http://yishiyu.world/2023/02/08/TimelineServer-总结-数据库/
默认为 root explosion
创建数据库
CREATE DATABASE timelineserver;
CREATE TABLE IF NOT EXISTS users(
user_id BIGINT(20) UNSIGNED AUTO_INCREMENT,
user_name VARCHAR(40) NOT NULL,
user_passwd VARCHAR(40) NOT NULL,
PRIMARY KEY (user_id)
);
CREATE TABLE IF NOT EXISTS tasks(
task_id BIGINT(20) UNSIGNED AUTO_INCREMENT,
user_id BIGINT(20) UNSIGNED NOT NULL,
time DATE NOT NULL,
task VARCHAR(300) NOT NULL,
priority INT DEFAULT 0 NOT NULL,
PRIMARY KEY (task_id)
);安装依赖库
1
2
3
4
5
6
7sudo apt update
安装 mysql connector
sudo apt install libmysqlcppconn-dev
安装 json11
sudo apt install libjson11-1-dev编译
1
2git clone https://github.com/yishiyu/TimelineServer.git
bash ./build.sh启动
1
2cd 到 build 目录
./TimelineServer项目结构
1 | . |
前后端交互逻辑
事件描述:
1
2
3
4
5
6
7{
"task_id": "xxx",
"user_id": "xxx",
"time": "时间戳",
"task": "xxx",
"priority": "0-10(越大越重要)"
}服务器交互
- 登陆之后,服务器回复浏览器一个
action_token
作为浏览器的身份凭证 - 浏览器断开链接/主动退出登录后
action_token
销毁 (action_token 其实就是 cookie)
浏览器发送内容
登录
Post 信息
1
2
3
4
5
6
7{
"action": "login",
"action_info": {
"user": "xxx",
"passwd": "xxx"
}
}服务器返回内容
1
2
3
4
5
6
7
8
9{
"action_result": "true/false",
"result_info": {
"action_token": "xxx",
// 发生错误时
"error_message": "xxx"
}
}
退出登录
Post 信息
1
2
3
4
5
6{
"action": "logout",
"action_info": {
"action_token": "xxx"
}
}服务器返回内容
1
2
3
4
5
6
7{
"action_result": "true/false",
"result_info": {
// 发生错误时
"error_message": "xxx"
}
}
查询数据
Post 信息
1
2
3
4
5
6
7{
"action": "query",
"action_info": {
// query:
"action_token": "xxx"
}
}服务器返回内容
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15{
"action_result": "true/false",
"result_info": {
"tasks": [
{
"task_id": "xxx",
"time": "时间戳",
"task": "xxx",
"priority": "0-10(越大越重要)"
}
],
// 发生错误时
"error_message": "xxx"
}
}
添加数据
Post 信息
1
2
3
4
5
6
7
8
9{
"action": "add",
"action_info": {
"action_token": "xxx",
"time": "时间戳",
"task": "xxx",
"priority": "0-10(越大越重要)"
}
}服务器返回内容
1
2
3
4
5
6
7
8
9{
"action_result": "true/false",
"result_info": {
"task_id": "xxx",
// 发生错误时
"error_message": "xxx"
}
}
更新数据
Post 信息
1
2
3
4
5
6
7
8
9
10{
"action": "update",
"action_info": {
"action_token": "xxx",
"task_id": "xxx",
"time": "时间戳",
"task": "xxx",
"priority": "0-10(越大越重要)"
}
}服务器返回内容
1
2
3
4
5
6
7{
"action_result": "true/false",
"result_info": {
// 发生错误时
"error_message": "xxx"
}
}
删除数据
- 登陆之后,服务器回复浏览器一个
login 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/login", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"login", "action_info": {"user":"user", "passwd": "passwd"}}',
})
).then((resp) => {
console.log(resp);
});logout 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/logout", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"logout", "action_info": {"action_token":"PKdhtXMmr29n3L0K99eM"}}',
})
).then((resp) => {
console.log(resp);
});query 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/query", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"query", "action_info": {"action_token":"PKdhtXMmr29n3L0K99eM"}}',
})
).then((resp) => {
console.log(resp);
});add 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/add", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"add", "action_info": {"action_token":"PKdhtXMmr29n3L0K99eM","time":"2024-01-01","task":"test task","priority": 3}}',
})
).then((resp) => {
console.log(resp);
});update 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/update", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"update", "action_info": {"action_token":"PKdhtXMmr29n3L0K99eM","task_id": 4, "time":"2099-01-01","task":"test task","priority": 3}}',
})
).then((resp) => {
console.log(resp);
});delete 动态路由
1
2
3
4
5
6
7
8
9fetch(
new Request("action/delete", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: '{"action":"delete", "action_info": {"action_token":"PKdhtXMmr29n3L0K99eM","task_id": 9}}',
})
).then((resp) => {
console.log(resp);
});
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 遗世の私语!