乐趣区

关于后端:PHP7内核实现原理基本架构

发展史

PHP 最早是由 Lerdorf 于 1995 年,应用 Perl 语言,以 Personal Home Page Tools (PHP Tools) 的模式创立的,目标是为了不便记录集体网站的访客记录和反对留言本等性能,此时称为 PHP 1

起初越来越多的网站开始应用 PHP 并心愿能提供更多的性能,之后 Lerdorf 将 PHP 开源 ,此时称为 PHP 2

1997 年两个以色列程序员 Zeev Suraski 和 Andi Gutmans 重写了 PHP 的解析器,并于 1998 年正公布,此为 PHP 3,并从此开始 PHP 改为 Hypertext Preprocessor,新版的解析器命名为 Zend Engine。Zend 的命名来自于两位作者的名字。

2000 年,以 Zend 1.0 为根底的 PHP 4 公布。2004 年,以 Zend 2.0 为根底的 PHP 5 公布,至此 PHP 反对了面向对象、PDO、命名空间等个性,性能方面也大幅晋升。

2015 年 12 月 3 日 PHP 7 公布,重构了 PHP 中很多重要且罕用的数据结构,内存占用失去显著优化,性能也失去了大幅晋升。

PHP 的组成

  • SAPI:

    PHP 自身能够了解为一组库函数,而 SAPI 则是其接入层,应用程序通过调用 SAPI 来间接调用 PHP 的函数,相似于 Shell 与 Linux 内核的关系。严格来讲 SAPI 不算是 PHP 内核的一部分。

  • Zend 引擎:

    Zend 引擎是 PHP 和外围,是 PHP 最最根底的局部。Zend 分为两局部:

    • 编译器:将应用层的 PHP 代码编译为形象语法树 AST,进一步编译为可执行的 opcodes。
    • 执行器:负责执行 opcodes

示意图:

SAPI 介绍

SAPI 即 Server Application Programming Interface,是应用程序与 PHP 内核交互的一套 API 标准。常见的 SAPI 实现有:

  • Apache mod_php 模块:

    该模块实现 SAPI 标准,使得让 Apache 与 PHP 做交互。

  • FastCGI/FPM:

    个别配合 Nginx 服务器解决 web 申请。

  • cli:

    命令行中执行 PHP。

下层利用与实现了 SAPI 的模块做交互,高低两层都遵循 SAPI 标准:

FPM(FastCGI Process Manager) 介绍

要理解 FPM,首先要理解 CGI,CGI(Common Gateway Interface)定义了 Web 服务器和应用程序交互的标准,FastCGI 是在其之上优化改良的后果,减少了 worker 常驻等个性,不必每次都 fork 新的过程来解决申请。

FastCGI 采纳多过程模型,与 web 服务器配合解决 web 申请。服务器负责解决解析网络申请,之后交给 FastCGI,FastCGI 将申请交给其治理的 worker pool,由具体一个 worker 来解决申请。

FastCGI 中的 master 过程通过共享内存的形式获取 worker 过程的状态,通过发送信号的形式治理 worker。

FastCGI 也是一种协定,而 FPM 则是实现了这种协定的过程管理器。

FPM 能够同时监听多个端口,一个端口对应一个 worker pool

FPM 配置,监听在 unix sock 上

; worker pool 名称
[www]
user = www
group = www

; 配置 worker pool 接管 FastCGI 申请的地址
; 能够是 ip:port 也能够是 unix sock
; The address on which to accept FastCGI requests.
; Valid syntaxes are:
;   'ip.add.re.ss:port'    - to listen on a TCP socket to a specific IPv4 address on
;                            a specific port;
;   '[ip:6:addr:ess]:port' - to listen on a TCP socket to a specific IPv6 address on
;                            a specific port;
;   'port'                 - to listen on a TCP socket to all addresses
;                            (IPv6 and IPv4-mapped) on a specific port;
;   '/path/to/unix/socket' - to listen on a unix socket.
; Note: This value is mandatory.
listen = /run/php7-cgi.sock

listen.owner = www
listen.group = www
listen.mode = 0660
pm = dynamic
pm.max_children = 20
pm.start_servers = 10
pm.min_spare_servers = 10
pm.max_spare_servers = 20

Nginx 与 FPM 通过 unix sock 交互配置

server
{
    listen 80;
    server_name xxx.xxx.com;
    index index.html index.php;
    root  /home/xxx/public;

    location / {if (!-e $request_filename){rewrite ^/(.*) /index.php last;
        }
    }
    location ~ [^/]\.php(/|$)
    {
        try_files $uri =404;
                # Nginx 转发申请给 PHP
        fastcgi_pass  unix:/run/php7-cgi.sock;
        fastcgi_index index.php;
        include fastcgi.conf;
    }
}

FPM master 治理 worker 的几种形式:

  • static:初始化就固定 worker 数不变
  • dynamic:动静调整 worker 数量
  • ondemand:相当于懒加载,一开始不创立 worker,之后申请到来在创立。

本文由 mdnice 多平台公布

退出移动版