分类 Docker & K8S 下的文章

我们来继续利用 Docker 搭建 PHP,目前主流的 PHP 运行模式还是基于 FPM,那么在这节中,我们来使用 Dcoker 搭建 PHP-FPM。

首先是下载镜像。

$ docker pull php:7.2.0-fpm-alpine3.6

$ php docker image ls | grep php
php           7.2-cli               dfdb1713d26a   23 months ago   365MB
php           7.2-cli-alpine3.6     27bfb4b1f223   4 years ago     74.1MB
php           7.2.0-fpm-alpine3.6   da8c99d32f95   4 years ago     75.4MB

其体积只有 76M,我们在运行容器时候可以使用 -d 让容器在后台运行。

$ docker run -d --rm -p 9000:9000 --name fpm-7.2 php:7.2.0-fpm-alpine3.6
0ea75f025c557b9cd4878a38219e5fa581ae66478ec321b91eec879ecf144fed
$ php docker ps | grep php
0ea75f025c55   php:7.2.0-fpm-alpine3.6   "docker-php-entrypoi…"   6 seconds ago   Up 6 seconds   0.0.0.0:9000->9000/tcp              fpm-7.2

接下来,我们安装 apache

# 拉取镜像
$ docker pull httpd:2.4-alpine

# 运行容器
docker run -d -p 80:80 --rm --name httpd-2.4 -v /home/maksim/src/php/:/usr/local/apache2/htdocs/ httpd:2.4-alpine

我们还是利用上一次我们编写的 Hello Docker! 脚本来进行演示,-v 可以将我们的本地目录挂在到 apache 容器中,

接下来,我们将 apache 的配置文件拷贝出来。

# . 代表当前目录,你可以设置成自己想要的目录
# 我的当前目录是 /home/maksim/src/conf/
$ docker cp httpd-2.4:/usr/local/apache2/conf/httpd.conf .
$ ls
httpd.conf

我们可以看到 httpd.conf 这样就被复制出来了,然后我们对其进行修改,支持 fpm。

# 将这三个模块加载放开

LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_http_module modules/mod_proxy_http.so
LoadModule proxy_fcgi_module modules/mod_proxy_fcgi.so

然后就是 docker 之间的通讯,如果没有指定 docker 容器的网络,默认情况下两个容器之间是在一个虚拟网络下,我们可以在两个容器之间通过虚拟 IP 进行通讯。

$ docker inspect fpm-7.2
...
"IPAddress": "172.17.0.3",
...

通过 inspect 命令我们可以查看 docker 容器的详细信息,我们将 apache 的代理设置为 172.17.0.3。

<VirtualHost *:80>
    ServerAdmin [email protected]
    DocumentRoot "/usr/local/apache2/htdocs"
    ServerName localhost
    <Directory "/usr/local/apache2/htdocs">
        Options None
        Require all granted
    </Directory>
    ProxyRequests Off
    ProxyPassMatch ^/(.*\.php)$ fcgi://172.17.0.4:9000/php/$1
</VirtualHost>

现在准备工作都已经结束了,我们开始重新开启容器。

# 停止当前容器
$ docker stop fpm-7.2 && docker stop httpd-2.4

# 启动 apache
docker run -d -p 80:80 --name httpd-2.4  -v /home/maksim/src/php/:/usr/local/apache2/htdocs/ -v /home/maksim/src/conf/httpd.conf:/usr/local/apache2/conf/httpd.conf httpd:2.4-alpine

# 启动 fpm
docker run -d -p 9000:9000 --name fpm-2.4 -v /home/maksim/src/php/:/php php:7.2.0-fpm-alpine3.6

至此我们就可以访问我们的应用程序了,如果启动后无法解析 php 文件,那么极有可能是 IP 发生了变更,我们可以再次查看 IP。

$ curl localhost/index.php
Hello Docker!

目前 Docker 部署算是比较流行的方式,在传统方式搭建生产环境时候我们需要人工进行编译,我们可以利用 Docker 来简化这一步操作,直接拉取官方镜像。

$ docker pull php:7.2-cli
$ docker image list | grep php
php   7.2-cli   dfdb1713d26a   23 months ago   365MB

这个镜像对于值运行 cli 程序来说镜像镜像有些太大了,镜像大就涉及到了拉取时间慢,而且占用磁盘资源,我们也可以选择 alpine 的版本,这是一个专门面向 docker 封装的精简版 Linux,其镜像要更小一些。

$ docker pull php:7.2-cli-alpine3.6

$ docker image list | grep php
php     7.2-cli             dfdb1713d26a   23 months ago   365MB
php     7.2-cli-alpine3.6   27bfb4b1f223   4 years ago     74.1MB

alpine 版本的 php-cli 总大小才 74.1MB。

接下来,我们来看一下该镜像中为我们打包好的 PHP 是否足以运行我们的 PHP 程序,最主要的就是看都安装了那些扩展。

$ docker run -it --rm php:7.2-cli-alpine3.6 php -m

该命令的意义如下:

[PHP Modules]
...
Core
ctype
curl
date
dom
fileinfo
....
[Zend Modules]

如果其扩展不足以支持我们的应用运行,我们可以选择基于官方的 Dockerfile 进行定制,同时如果将要基于当前镜像进行定制的话也可以编写自己的 Dockerfile。

接下来,利用该进行来执行我们的第一个应用程序。

$ cat /home/maksim/index.php
<?php

echo "Hello Docker!";

$ docker run -it --rm --name runphp -v /home/maksim/index.php:/usr/src/index.php php:7.2-cli-alpine3.6 php /usr/src/index.php
Hello Docker!%

这样 PHP 的 Cli 程序就可以运行了。