前言

时隔一个差不多月,终于又出工夫来更新自己之服务器了,这次更新主要实现转 CGI
协议。

先放上GitHub链接
tinyServer-GitHub-枕边书

用作一个服务器,基本要求凡能够受理请求,提取信息并将信息分发给 CGI
解释器,再以解释器响应的音讯包装后赶回客户端。在这个历程遭到,除了和客户端
socket 之间的互相,还要拉到第三独实体 – 请求解释器。

图片 1

倘齐图所示,客户端负责打包请求和分析响应,服务器的主要职责是管理总是、数据易、传输和散发客户端请求,而实在进展数据文档处理和数据库操作的即是伸手解释器,这个解释器,在
PHP 中一般是 PHP-FPM,JAVA 中是 Servlet。

我们事先进行的处理多以客户端和服务器之间的通信,以及服务器的其中调整,这次更新的情节要是背后两独实体之间的过程之中通信。

进程中通信牵涉到三只地方,即方式形式内容

艺术凭的是过程中通信的传导媒介,如 Nginx 中实现之 TCP 方式跟 Unix Domain
Socket,它们分别发出跨机器和高效率的助益,还有我实现的服务器用了特别 low
popen方式。

万一花样就是数据格式了,我看其并无定式,只要服务器容易组织数据,解释器能便于地收并分析,最好与否能省掉传输资源,提高传输效率。目前之化解方案有经的
xml,轻巧易掌握的 json 和谷歌高效率的 protobuf。它们每起独到之处,我选了
json,主要是坐来CJson库的有,数据以 C
中好组织,而以PHP中,一个json_decode()措施就是完了了数据解析。

关于该传哪些内容为?CGI 描述了平等仿商:

CGI

通用网关接口(Common Gateway
Interface/CGI)是同等栽重要之互联网技术,可以叫一个客户端,从网页浏览器为实施于网络服务器上的顺序要数据。CGI描述了服务器和伸手处理程序之间传输数据的如出一辙种标准。

CGI
是服务器和解释器交互的接口,服务器负责受理请求,并将请信息说啊一条条基本的求信息(在文档中给称为“元数据”),传送给解释器来诠释施行,而解释器响应文档和数据库操作信息。

前看了瞬间 CGI 的 RFC
文档,总结了几乎单重要点,有趣味的可以看下底部参考文献。常见规范(信息最多,只考虑
MUST 的动静)如下:

CGI请求

  • 服务器根据 以 / 分隔的不二法门选择解释器;
  • 如果有 AUTH 字段,需要先实行 AUTH,再实施解释器;
  • 服务器确认 CONTENT-LENGTH
    表示的凡数量解析出的长,如果附带信息体,则要将长字段传送到解释器;
  • 如果有 CONTENT-TYPE
    字段,服务器必须用那个传为解释器;若任由夫字段,但发生信息体,则服务器判断此类型或丢弃信息体;
  • 服务器必须设置 QUERY_STRING
    字段,如果客户端从未装,服务端要招一个空字符串“”
  • 服务器必须设置 REMOTE_ADDR,即客户端请求IP;
  • REQUEST_METHOD 字段必须安装, GET POST 等,大小写敏感;
  • SCRIPT_NAME 表示执行的解释器脚本名,必须装;
  • SERVER_NAMESERVER_PORT
    代表着大大小小写敏感的服务器名和服务器受理时之TCP/IP端口;
  • SERVER_PROTOCOL
    字段指示在服务器和解释器协商的磋商项目,不肯定和客户端请求的SCHEMA
    相同,如’https://'可能为HTTP;
  • CONTENT-LENGTH 不也 NULL
    时,服务器如果供信息体,此信息体要严厉和长相符,即使有重多之而读信息为无可知多传;
  • 服务器必须以数据压缩等编码解析出;

CGI响应

  • CGI解释器必须响应 至少一行头 + 换行 + 响应内容;
  • 解释器在响应文档时,必须使出 CONTENT-TYPE 头;
  • 以客户端重定向时,解释器除了
    client-redir-response=绝对url地址,不能够更起外返回,然后服务器返回一个
    302 状态码;
  • 解释器响应 三号数字状态码,具体部署可自动检索;
  • 服务器必须将所有解释器返回的数目应给客户端,除非需要减小等编码,服务器不克改响应数据;

Nginx和PHP的CGI实现

介绍完了 CGI,我们来参考一下当下服务器 CGI
协议落实的秋方案,这里挑选我熟悉的 Nginx 和 PHP。

以 Nginx 和 PHP 的相当着,Nginx 自然是服务器,而解释器是 PHP 的 SAPI。

SAPI

SAPI: Server abstraction API,指的凡 PHP 具体以之编程接口,它叫
PHP 可以和其他应用进行交互数据。

PHP 脚论要执行好经杀多种计,通过 Web
服务器,或者直接在指令行下,也得放开在旁程序中。常见的 sapi
apache2handler、fpm-fcgi、cli、cgi-fcgi,可以经过 PHP
函数php_sapi_name()来查阅时 PHP 执行所利用的 sapi。

PHP5.3 之前用的与服务器交互的 sapi 是cgi,它实现基本的 CGI
协议,由于其每次处理要都设创一个历程、初始化进程、处理要、销毁过程,消耗过非常,使得系统性能大大降低。

此刻就起了 CGI 协议的升官版本 Fast-CGI。

PHP-FPM

迅猛通用网关接口(Fast Common Gateway
Interface/FastCGI)是平等栽为彼此程序和Web服务器通信的商。FastCGI是初通用网关接口(CGI)的增进版。

Fast-CGI 提升效率要靠将 CGI
解释器长驻内存重现,避免了经过反复加载的淘。PHP 的 sapi
cgi-fcgi心想事成了 Fast-CGI 协议,提升了 PHP 处理 Web 请求的频率。

这就是说我们普遍的 php-fpm 是呀吧?它是同等种植进程管理器(PHP-FastCGI Process
Manager),它负责管理实现 Fast-CGI
的那些经过(worker进程),它加载php.ini消息,初始化 worker
进程,并落实平滑重开和外高档功能。

Nginx 将请求都交由 php-fpm,fpm 选择一个空暇工作经过来拍卖要。

纠偏

此总结一下几单名字,以防混淆:

  • sapi,是 PHP 与外表进程并行的接口;
  • CGI/Fast-CGI(大写)是一律种协议;
  • 本节遭到出现的 cgi(小写),是凭 PHP 的 sapi,即实现 CGI
    协议的平栽接口。
  • php-fpm 是管理实现了Fast-CGI协议的进程的一个经过。

代码实现

介绍了了高端的Nginx服务器,说一样下自己的兑现:

服务器解析 http 报文,实现 CGI 协议,将数据包装成 json 格式,通过 PHP
cli sapi 发送至 PHP 进程,PHP 进程解析后应 json
格式数据,服务器解析响应数据后装进成 http 响应报文发送给客户端。

http_parser

首要任务是分析 http 报文,C
中没怪丰富字符串函数,我啊从来不包装了常用的函数库,所以只好临时自己实现了一个util_http.c,这里介绍几个处理
http 报文时好用的字符串函数。

strtok(char str[], const *delimeter),将 delimeter 设置为
"\n",分行处理 http 报文头正好适合。

sscanf(const *str, format, dest1[,dest...]),它从字符串中因一定格式读取字符串,读取时的隔符是空格,用她来处理
http 请求行十分方便。

至于解析 http 报文头的键值对应,没悟出好方法,只好利用字符遍历来判断。

cJSON

cJSON 是一个 C 实现之用来生成和分析 json 格式数据的函数库,在 GitHub
上足轻松搜到,只所以少独文件 cJSON.ccJSON.h即可。

待注意:C 作为强类型语言,往 json
内添加不同品种的数如果动不同的主意,cJSON 支持
string, bool, number, cJSON object等类型。

此大概地介绍一下变更和分析的形似法;

生成:

cJSON *root; // 声明cJSON格式数据
root = cJSON_CreateObject(); // 创建一个cJSON对象
cJSON_AddStringToObject(root, "key", "value") // 往cJSON对象内添加键值对
char *output = cJSON_PrintUnformatted(root); // 生成json字符串
cJSON_Delete(root); // 别忘记释放内存

解析:

cJSON *json = cJSON_Parse(response_json);
value = cJSON_GetObjectItem(cJSON, "key");

自,也足以声明 cJSON 类型的多寡开展嵌套;

总结

说实话,用极端中心的 C
写作业逻辑类的代码真的能赔磨坏人,仅一个字符串的操作就能为人口欲仙欲死了。常因此
C
开发之相应出各种函数库吧,就算没团结的仓库也使失去找寻开源库,自己过去不了有的轮。

感觉服务器又吃自己写残了,留了不少工作品种的坑也无知情啊时会填,希望会闹工夫写一个工业级的事物。。。

若你看本文对君来帮带,可以点击下面的 推荐
支持一下自家。博客一直于创新,欢迎 关注

参考: The Common Gateway Interface (CGI) Version
1.1

深切明PHP内核 »
生命周期和Zend引擎

搞不清FastCgi与PHP-fpm之间是单怎样的涉嫌

相关文章

网站地图xml地图