docker与docker-compose的安装就不在此过多说明了,需要的自行百度,做为一个小白,刚接触时就有以下几个疑惑?

  • 能否使用docker代替linux的lnmp环境或者同时共存?
  • 怎么使用docker搭建lnmp环境呢?能不能搞php多版本共存?
  • 容器重启后,对容器修改就会丢失!那么如何处理lnmp的配置?数据库呢?代码又怎么保证是最新的?

代替与共存:是可以的,docker使用端口映射,指定容器的端口连接到主机的特定端口(不冲突主机当前使用的端口),就能在主机访问容器了,共存或替换都可以。

怎么搭建环境:可以在一个容器里面安装好lnmp,也可以一个环境一个容器(如:php/nginx/mysql各弄一个docker容器)推荐lnmp各装一个容器,配置一下就能切换不同的php版本,再加上docker-compose实现多个容器同步启动方便管理

保存数据与配置:用docker的volume数据卷就行,容器使用卷之后,就会将硬盘目录挂载到容器的指定目录,实现数据长久保存、容器之间共享数据,因为文件是保存在电脑硬盘里面而不是容器里面,重启docker也能正常,所以我们将《数据库文件、nginx/php配置文件、lnmp日志、代码文件目录》都使用卷挂载到容器,很灵活。

解决了疑惑之后,就开始着手使用docker实现lnmp环境,先分享一个docker-compose配置https://github.com/zhousmq/docker_lnmp.git,再说说构建环境以及配置遇到的问题。

一、lnmp配置文件应该怎么写呢?php/nginx的配置每个版本都不一样,总不能顺便写一个配置,跟docker环境的不一致是不是有问题呢?

解决这个问题也简单,docker构建完成,先run起来,使用sudo docker ps -a获取容器id,使用sudo docker exec -it 容器id /bin/bash,进入容器找到配置文件,使用docker cp复制配置文件到主机目录(最后放入到docker-compose的配置目录下)

ubuntu@ip-172-31-109-240:~$ sudo docker ps -a
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                               NAMES
c55a3c306255        files_nginx         "nginx -g 'daemon of…"   8 days ago          Up 3 days           0.0.0.0:80->80/tcp                  files_nginx_1

ubuntu@ip-172-31-109-240:~$ sudo docker exec -it c55a3c306255 /bin/bash

ubuntu@ip-172-31-109-240:~$ sudo docker cp c55a3c306255:/etc/nginx/conf conf
示例操作
二、配置文件解决,容器正常启动了,网站却报502 Bad Gateway错误,不能访问

这个问题主要是容器通信问题,在linux环境下,我们都是习惯使用127.0.0.1指定为本机路径,使用容器后,lnmp配置文件挂载到容器后,127.0.0.1访问的是容器,而不是主机,我们可以使用容器ip,在主机执行ifconfig获取容器通信ip,一般为172.17.0.1,然后修改nginx的配置,将php的指向的ip换成docker0网卡ip就行。

test@Inspiron-3650:~$ sudo ifconfig
docker0: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500
        inet 172.17.0.1  netmask 255.255.0.0  broadcast 172.17.255.255
        inet6 fe80::42:38ff:fe77:959c  prefixlen 64  scopeid 0x20<link>
        ether 02:42:38:77:95:9c  txqueuelen 0  (Ethernet)
        RX packets 3638  bytes 258043 (251.9 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 2834  bytes 1096401 (1.0 MiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
server {
			location ~ \.php$ {
            #ip换成docker网卡的
            fastcgi_pass   172.17.0.1:9000;
            #fastcgi_pass   127.0.0.1:9000;
            fastcgi_index  index.php;
            
            #文件路径要对应上容器内的路径
            fastcgi_param  SCRIPT_FILENAME  /usr/local/apache2/htdocs/$fastcgi_script_name;
            include        fastcgi_params;
        }
}        
nginx配置示例
三、站点无法连接mysql,站点访问不了

这个问题原因同上,在代码的数据库连接配置文件将host换成docker网卡ip就行,可能还需要配置一下docker环境的mysql完成开放(允许所有的ip)

           <connection>
                    <host><![CDATA[172.17.0.1]]></host>
                    <username><![CDATA[root]]></username>
                    <password><![CDATA[root]]></password>
                    <dbname><![CDATA[database_name]]></dbname>
           </connection>
代码数据库连接示例
四、页面显示空白,浏览器标签一直都在转圈,php报了not found错误,无法正常访问站点

多容器时候会有这个问题,php与nginx的docker-compose.yml配置文件里面,把代码路径都配置到两个容器,挂载上卷就行,php获取代码路径会在本容器上查找代码文件。

五、docker-compose.yml的nginx容器增加到volume,却不能在容器里面查看到新增卷的文件路径

这个问题也真坑,在刚开始构建环境的时候,只把php容器做了代码路径卷挂载,后面想明白了两个容器的问题后,在docker-compose.yml的nginx容器也增加了代码路径卷挂载,发现还是不行,最后终于发现nginx容器没有挂载到代码路径,最终处理办法是删除nginx容器卷,再重新创建一次。

 test@Inspiron-3650:~$ sudo docker ps -a
 #获取容器id
 test@Inspiron-3650:~$ sudo docker-compose stop
 #停止容器
 test@Inspiron-3650:~$ sudo docker rm 容器id
 #删除容器
 test@Inspiron-3650:~$ sudo docker-compose up
 #重新up容器,up后,会一直是docker的界面,Ctrl+c停止后,再执行以下命令就行
 test@Inspiron-3650:~$ sudo docker-compose start
 
 
说明示例