一个简单的 Web 服务器 [未完成]

时间:2023-03-08 16:33:07

最近学习C++,linux和网络编程,想做个小(mini)项目.  就去搜索引擎, 开源中国, Sourceforge上找http server的项目.

好吧,也去了知乎.    知乎上程序员氛围好, 有不少经验可以借鉴.

终极目标:自己实现(implement)一个WEB SERVER.

感想: 算法和数据结构还是很重要的...(一切的基础啊...悔不当初为什么不好好学,去acm也好...)

指导:Build a simple HTTP server in C  (有不会的就问*, 所以说如果有一天这网站挂了,网站管理员都不会修了,因为没有可以问啊)

资料:

0.RFC1945:Hypertext Transfer Protocol -- HTTP/1.0  (http协议版本1.0)

1.RFC2616: rfc2616 Hypertext Transfer Protocol -- HTTP/1.1   (讲HTTP协议,版本1.1,114页大小)

2.A Practical Guide to Writing Clients and Servers   (15页打印纸的内容,略长略长,慢慢看)

  比RFC容易看,快速过一遍.

3.RFC2396:

4.RFC2732:

5.RFC822: Standard for ARPA Internet Text Messages

6.RFC1521:MIME part I

前导知识 prerequisites:

  0.网络知识 (看TCP/IP Illustrated)

  1.网络编程  (可以看UNP, Unix Network Programming)

        (或者更好入门的Beej's Guide to Network Programming)

  2.系统API   (看APUE, Advanced Programming in the UNIX Environment Third Edition)

(书厚不是问题,反正以后都要看,早点看得了)

找到几个轻量级的小项目:

1.nweb Tiny Webserver (谷歌搜出来的, 200行,静态网页,C,安全检查)

  比较简单,如果有点网络编程的基础的话,就是刚学完网络编程就能写出来的程度.

  用fork(),不用select().   看完后可以用select做一次. 代码中用了signal(),inet_addr()这些不推荐的函数. 可以自己替代为sigaction()和inet_aton()  

  如何写一个daemon :Linux Daemon Writing HOWTO

  我犯过的错误:  

  1. if(a=b)

  2.accept()调用时没有初始化socklen_t addrlen = sizeof client_addr;

  3.发送图片时没有写头部 Content-Type: image/jpg

  4. 使用sprintf时没有使格式和参数一一对应,导致未定义的结果.

  5. 调用select()时没有注意nfds要加1

  6.如果要用ipv6,似乎不能用sa->ai_family = AF_UNSPEC;而只能用AF_INET6;不然问题提示"Connection refused"

  7.getaddrinfo()返回0是成功. 非0为失败(而还是-1!!!!!!)

2.Tiny HTTPd (*上有人推荐,500 行,C,支持CGI)

  (CSDN上有人解析源码: 【源码剖析】tinyhttpd —— C 语言实现最简单的 HTTP 服务器)

3.mongoose  (知乎上一个问题下说到了)

4.lighthttpd  (轻量级,高性能网站,安全、快速、兼容性好并且灵活的web server环境)

  (ChinaUNIX 的 lighttpd-1.4.20源码分析  )

5.Zaver如何写一个Web服务器 github:zyearn/zaver  (知乎上看到的, 高性能, http/1.1, 基本架构 : 非阻塞, event loop, 线程池)

6.Nginx (生产环境.  不知道为什么我会把这个放在这里,装饰下页面......应该不会去看的)

测试:

1. 压力测试

  http_load

  webbench

  ab

还有一个问题,阅读别人的代码:

  1.书:Code Reading

  2.网页:Tips For Reading Code

Further Study:

the c10k problem (10,000 connection)