电子发烧友App

硬声App

0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示
电子发烧友网>电子资料下载>电子资料>tinyserver C++编写的轻量服务器框架

tinyserver C++编写的轻量服务器框架

2022-06-22 | zip | 4.66 MB | 次下载 | 免费

资料介绍

授权协议 未知
开发语言 C/C++
操作系统 跨平台
软件类型 开源软件
所属分类 Web应用开发Web框架

软件简介

该库为C++编写的轻量服务器框架,服务器核心采用单进程单线程select实现,后续增加更多的实现方式如libevent,epoll,多线程,多进程。旨在学习服务端编程的方法。内部对http请求从封装到处理主要参考django的处理方式。

编译

这里bin目录下为我在windows/linux下编译好的简单服务器,可以直接运行使用,运行后在127.0.0.1:8000可以直接访问。

编译流程

cd build
cmake ..
make
./MyWebServer.exe  (或者是./MyWebServer)

使用流程

#include "tinyserver.h"
#include "ejson.h"

using namespace WebServer;
using namespace EasyJson;

void render_string(HttpRequest &request, HttpResponse &response) {
	// 显示html字符串,可以任意设置response_code
    response.set_header_attribute("key1", "value1") // 自定义header
            .set_header_attribute("key2", "value2")
            .set_response_code(404) // 自定义reponse code
            .set_data(R"(
this is a test
)"); } int main() { IHttpServer *server = new BaseHttpServer(8000); // 如果没有参数的话默认端口8888 server->enrol("/", render_string); server->run(); }
  • 包含头文件和名称空间。
  • 编写响应函数(该函数作为框架的回调函数)
  • 初始化HttpServer对象
  • 将响应函数注册到server中
  • 进行server事件循环

浏览器访问可以看到如下。

poYBAGKn6RyAWPvTAAANSpIZpn0790.png

按F12重新刷新可以看到响应Http报文的头部如下

pYYBAGKn6R2AO_JHAAAW4rczW1M438.png

example

example1: 文件下载

void download_file(HttpRequest &request, HttpResponse &response) {
	// 文件下载
    response.set_file("myfile")
            .set_content_type(STREAM);  
}

int main() {
    IHttpServer *server = new BaseHttpServer(8000);
    server->enrol("/download", download_file);
    server->run();
}    

对response对象调用set_file方法和set_content_type方法,浏览器访问url后会下载对应的文件。

访问127.0.0.1/download 会自动下载文件然后保存到本地中。如果文件不存在则返回404

example2: 纯文本显示在浏览器上

有一些文本我们想让浏览器显示,而不被当前是html文件(即使你文件中含有html标签也不会被浏览器渲染出来)

void render_plain_text(HttpRequest &request, HttpResponse &response) {
	// 将纯文本展示在浏览器上
    FILE *f = fopen("myfile", "rb"); 
    char buf[2048];
    size_t r = fread(buf, sizeof(char), 2048, f);
    response.set_data(buf, r)
            .set_content_type(PLAIN);
}

int main() {
    IHttpServer *server = new BaseHttpServer(8000);
    server->enrol("/text", render_plain_text);
    server->run();
}

编译后访问页面可以得到如下

poYBAGKn6R6ARawyAAAOtNvypDI332.png

example3: 返回json

这里需要依赖我编写的json库ejson 。 可以用来做rest服务

void render_json(HttpRequest &request, HttpResponse &response) {
    // 返回json,可以做rest服务
    JSONObject obj = {
            {"test obj", {"key", "value"}},
            {"int number", 2},
            {"float number", 34.3},
            {"my string", "fsdfsdg"},
            {"nullptr", nullptr},
            {"emptylist", {}},
            {"列表嵌套列表", {1,2.3, "sdf", {1,2.242, "float"}}}, // 列表嵌套
            {"列表嵌套对象和列表", {
                {{"key1", 1234}}, // 被认为是对象
                {"key1", 1234}, // 被认为是列表
                1.23,
                234325
            }},
            {"对象", { // 所有的值都是{key, value}对则认为是嵌套对象
                {"a obj", 1234566},
                {"b obj", "b obj value"},
            }}
    };
    response.set_data(obj.toString(2)) // 将json格式化
            .set_content_type(JSON);
}

int main() {
    IHttpServer *server = new BaseHttpServer(8000);
    server->enrol("/json", render_json);
    server->run();
}

访问127.0.0.1:8000/json 可以得到一下页面,这里我将json以2空格缩进打印在浏览器页面上。

pYYBAGKn6SCACs0QAAAlAxS-Mdk407.png

example4: url正则表达式匹配

void re_url_test(HttpRequest &request, HttpResponse &response) {
	// 捕抓url正则表达式匹配到的内容。
    auto match = request.get_url_parm(); // 返回一个smatch对象,可以用[]操作符索引匹配结果
    stringstream ss;
    ss << R"()";
    ss << R"(

匹配到的数字为: )" << match[0]; ss << R"(

)"; ss << ""; response.set_data(ss.str()); } int main() { IHttpServer *server = new BaseHttpServer(8000); server->enrol("/re/(\\d+)", re_url_test); server->run(); }

访问浏览器得到的结果如下

poYBAGKn6SGAUFfLAAANIQ_VGCs493.png

example5: 静态html文件

void render_html(HttpRequest &request, HttpResponse &response) {
    // 根据不同的请求方法返回不同的内容。
    response.set_file("my.html");
}

int main() {
    IHttpServer *server = new BaseHttpServer(8000);
    server->enrol("/hmpl", render_hmpl);
    server->run();
}

只需要调用set_file函数就可以将你的html显示在浏览器上。(可以依此使用正则表达式匹配对应的文件,来做静态文件服务器)

example6: html模版文件渲染

web开发中经常会用到模版,这是为了响应动态的数据。这里我使用到自己编写的一个轻量html模板渲染库cjinja

void render_tmpl(HttpRequest &request, HttpResponse &response) {
	// 将html模版显示在屏幕上。
    JSONObject context = OBJECT(
            KEYVALUE("username", "hhk"),
            KEYVALUE("obj", OBJECT(
                    KEYVALUE("abcd", LIST(1,2.3, "hahahaha")),
                    KEYVALUE("obj", OBJECT(
                            KEYVALUE("key", "this is obj.obj.key' s value")
                    ))
            )),
            KEYVALUE("null", nullptr),
            KEYVALUE("list", LIST(1, "qwerty", 2.34, OBJECT(
                            KEYVALUE("key", "this is a key"),
                            KEYVALUE("key2", "this is a key2"),
                    ))),
            KEYVALUE("list1", LIST(1,2,3,4,5)),
            KEYVALUE("list2", LIST(1,2,3)),
            KEYVALUE("obj2", OBJECT(
                    KEYVALUE("key1", "value1"),
                    KEYVALUE("key2", 222),
                    KEYVALUE("key3", 333),
            )),
            KEYVALUE("a", "111"),
            KEYVALUE("b", "222"),
            KEYVALUE("c", "333"),
    );
    context.add("parm", request.get_request_parm());
    render(response, "tmpl.html", context);
}

int main() {
    IHttpServer *server = new BaseHttpServer(8000);
    server->enrol("/tmpl", render_tmpl);
    server->run();
}

传入了一个JSONObject作为模版渲染的数据,在浏览器端显示如下,模版文件为tmpl.html(位于bin目录下)

浏览器渲染的部分结果如下图所示。

poYBAGKn6SKAdYaNAAA8bQnEOLE061.png

example6: 根据请求的方法做不同的处理

这里使用request.get_method 获取请求的请求的方法,然后根据不同的请求做不同的处理。

void render_html(HttpRequest &request, HttpResponse &response) {
    // 根据不同的请求方法返回不同的内容。
    if(request.get_method() == GET ) {
        response.set_file("my.html");
    } else if(request.get_method() == POST) {
        response.set_file("my2.html");
    }
}

int main() {
    IHttpServer *server = new BaseHttpServer();
    server->enrol("/html", render_html);
    server->run();
}

TODO

  • epoll libevent 版本
  • 多进程 多线程版本
  • session的处理
  • 缓存
  • 大文件下载,断点续传
 

下载该资料的人也在下载 下载该资料的人还在阅读
更多 >

评论

查看更多

下载排行

本周

  1. 1山景DSP芯片AP8248A2数据手册
  2. 1.06 MB  |  532次下载  |  免费
  3. 2RK3399完整板原理图(支持平板,盒子VR)
  4. 3.28 MB  |  339次下载  |  免费
  5. 3TC358743XBG评估板参考手册
  6. 1.36 MB  |  330次下载  |  免费
  7. 4DFM软件使用教程
  8. 0.84 MB  |  295次下载  |  免费
  9. 5元宇宙深度解析—未来的未来-风口还是泡沫
  10. 6.40 MB  |  227次下载  |  免费
  11. 6迪文DGUS开发指南
  12. 31.67 MB  |  194次下载  |  免费
  13. 7元宇宙底层硬件系列报告
  14. 13.42 MB  |  182次下载  |  免费
  15. 8FP5207XR-G1中文应用手册
  16. 1.09 MB  |  178次下载  |  免费

本月

  1. 1OrCAD10.5下载OrCAD10.5中文版软件
  2. 0.00 MB  |  234315次下载  |  免费
  3. 2555集成电路应用800例(新编版)
  4. 0.00 MB  |  33566次下载  |  免费
  5. 3接口电路图大全
  6. 未知  |  30323次下载  |  免费
  7. 4开关电源设计实例指南
  8. 未知  |  21549次下载  |  免费
  9. 5电气工程师手册免费下载(新编第二版pdf电子书)
  10. 0.00 MB  |  15349次下载  |  免费
  11. 6数字电路基础pdf(下载)
  12. 未知  |  13750次下载  |  免费
  13. 7电子制作实例集锦 下载
  14. 未知  |  8113次下载  |  免费
  15. 8《LED驱动电路设计》 温德尔著
  16. 0.00 MB  |  6656次下载  |  免费

总榜

  1. 1matlab软件下载入口
  2. 未知  |  935054次下载  |  免费
  3. 2protel99se软件下载(可英文版转中文版)
  4. 78.1 MB  |  537798次下载  |  免费
  5. 3MATLAB 7.1 下载 (含软件介绍)
  6. 未知  |  420027次下载  |  免费
  7. 4OrCAD10.5下载OrCAD10.5中文版软件
  8. 0.00 MB  |  234315次下载  |  免费
  9. 5Altium DXP2002下载入口
  10. 未知  |  233046次下载  |  免费
  11. 6电路仿真软件multisim 10.0免费下载
  12. 340992  |  191187次下载  |  免费
  13. 7十天学会AVR单片机与C语言视频教程 下载
  14. 158M  |  183279次下载  |  免费
  15. 8proe5.0野火版下载(中文版免费下载)
  16. 未知  |  138040次下载  |  免费