文章目录
简要:
cpp-httplib是一个c++封装的http库,使用这个库可以在windows平台下完成http客户端、http服务端的搭建。
在p2p点对点下载器的项目中,我们只需用到cpp-httplib中的 httplib.h这个头文件,所以我们在这里只讲一下httplib搭建tcp客户端与服务器的原理。
httplib.h头文件的处理流程:
1. 最简单的http客户端搭建的步骤
- 组织http协议格式的请求数据
- 搭建tcp客户端
- 发送组织好的http请求数据
- 等待服务端响应,接收响应数据
- 对响应数据的解析
2. 最简单的http服务端搭建的步骤
- 搭建tcp服务端
- 等待接收客户端发送的数据
- 按照http协议格式,对数据进行解析(格式按照: 请求方法 URL 协议版本\r\n 头部\r\n 正文)
- 根据请求的资源路径以及查询字符串以及正文,进行业务处理
- 组织http协议格式的响应,返回给客户端(协议版本 状态码 描述\r\n 头部)
httplib.h头文件的组成
httplib.h头文件的组成主要包含有以下四个类
| 类 | 类名 |
|---|---|
| class Request | 请求数据类 |
| class Response | 回复数据类 |
| cass Server | 服务端类 |
| class Client | 客户端类 |
发送请求类的组成
class Request
{
std::string method; // 请求方法
std::string path; // 请求路径
map<std::string, std::string> param; // 查询字符串(查询字符串中)
map<std::string, std::string> headers;// 键值对头部
std::string body; //正文
};
回复数据类的组成
class Response
{
int status; //返回的状态码
map<std::string,std::string> headers; //返回的价值对头部
std::string body; //正文
};
服务端类的组成
class Server()
{
Get(); // 请求方法 Get
Post(); // 请求方法 Post
Put(); // 请求方法 Put
....
listen(host,port); // 监听(传入某个主机,端口)
};
客户端类的组成
class Client
{
//创建client
Client(host,port);
Get()
Post()
Put()
...
};
httplib.h头文件搭建服务端与客户端的原理
main.cpp中使用httplib搭建了一个http服务器
#include "cpp-httplib"
void helloworld(Request& req, Response& rsp)
{
}
int main()
{
Server srv; // 创建服务端对象
srv.Get("/",helloworld);
srv.listen("0.0.0.0",9000); // 0.0.0.0 本机的任意一块网卡地址, 9000端口
}
Get接口
Get表达式: Get( 请求资源路径path, 回调函数指针)
Server对象中 :Get接口的作用就是将资源路径以及请求方法还有回调函数,在srv对象中的map表中存储起来。
srv对象中有一张map表,在这里的就是对应的是"/" , GET, hello
| 资源路径 | 请求方法 | 回调函数地址 |
|---|---|---|
| “/” | GET | hello |
注意:
服务端首先Get(),先注册对应关系,先告诉自己的服务器,当我们遇到什么请求方法,请求什么资源,在回调什么函数。将浙西全部都记录在map中。当listen监听的时候,才建立起服务端。
若服务端收到了http请求,解析之后。若请求中的path,对应了Get接口传入的path(也就是能在map中找到对应关系),则服务端会创建一个线程回调这个传入的函数helloworld()对这次的请求进行业务处理。
服务器Server的

listen(0.0.0.0,9000)接口
listen(0.0.0.0,9000)接口功能: 搭建tcp服务器,监听本机所有网卡9000端口,等待客户端传来数据。若接收到了客户端的请求数据,则服务端创建一个线程去处理这个请求。
- 按照http协议格式解析请求数据,将解析的结果放入到一个实例化的Request对象中(包含请求方法,资源路径,查询字符串,头部信息,正文…)-- 得到了req
- 去srv对象中的那张map表中查找
根据req中的请求方法,以及资源路径,判断map中是否有对应的处理函数。
若请求方法与资源路径都对应成功,则将req对象传入这个回调函数,去处理这次请求。
在这个用户自定义的回调函数中,处理完毕之后,会填充一个rsq对象。到此,回调函数运行完毕 - 回调函数运行完毕,则得到了一个已经填充了各种响应信息的rsq对象
- 通过这个rsq对象,组织http响应发送给客户端。
httplib.h头文件建立服务端与客户端的例子:
#include "httplib.h"
void helloword(const httplib::Request &req, httplib::Response &rsp)
{
printf("httplib server recv a req: %s\n ", req.path.c_str() );
rsp.set_content("<html><h1> 武汉, 加油!</h1></html>", "text/html");//最后一个参数是正文类型
rsp.status = 200;
}
int main()
{
httplib::Server srv;
srv.Get("/",helloword);
srv.listen("0.0.0.0", 9000);
system("pause");
}
向网址中输入127.0.0.1:9000 我们就可以看见结果了。
(127.0.0.1 本机的回环网卡地址, 9000端口)
结果:

httplib.h头文件的网盘链接:
链接: https://pan.baidu.com/s/1ikxlF9vccR_A-UPs794Fqw
提取码:1x8w