Win10 DokerDesktop 构建 PHP 环境

1,815 阅读7分钟

项目背景

Tester : 你看, 你这有 Bug 了!

Coder : 在我这里能跑啊, 我这里没问题啊!

Tester : 那我这里咋这样啊?

Coder : 我看下...凑, 是环境问题 (内心万马奔腾)

由于开发环境和线上环境存在微小的差异, 会导致一些不易发现的 Bug, 并且环境问题解决起来会很棘手... 为了避免这个情况出现, 开发环境与线上环境都使用 Docker 搭建;

Docker 安装

开发环境 Win10, 这里只介绍 Win10 对应的操作

下载地址

下载完成直接傻瓜式安装, 安装完重启电脑, 启动 docker-desktop

主页会显示 docker desktop starting, 忘记截图了

查资料有说是 Hyper-V 的问题 (可能是这个问题, 没做研究)

新版本的 Win10 系统, 采用的是 WSL2 Vmmem 进程

解决方案

对 WSL 旧版本进行升级, 选择适合自己的版本, 就可以解决问题

下载 Linux 内核更新包

image.png

下载完成, 双击打开, 等待完成

完成之后重启 docker-desktop, 成功启动!

更换镜像存储位置

由于 Windows 版本的 docker-desktop 默认安装路径是 C 盘, 这就会导致 C 盘空间越来越小, 所以需要我们手动更换下存储路径

原路径 C:\Users\用户名\AppData\Local\Docker

新版 Win10 使用的 wsl2 的版本, 所以docker-desktop 在安装的时候创建两个 wsl 子系统. 使用管理员打开Windows powershell 输入命令查看 wsl -l -v --all image.png

docker-desktop 是存放程序的 docker-desktop-data 是存放镜像的

  • 停止 wsl

    wsl --shutdown
    

    再次查看

    image.png

  • 导出 wsl 子系统镜像

    wsl --export docker-desktop docker-desktop.tar
    wsl --export docker-desktop-data docker-desktop-data.tar
    

    不报错即为正常 image.png

  • 删除现有的 wsl 子系统

    wsl --unregister docker-desktop
    wsl --unregister docker-desktop-data
    

    成功

    image.png

  • 重新创建 wsl 子系统

    wsl --import docker-desktop E:\Env\Docker\docker-desktop docker-desktop.tar --version 2
    wsl --import docker-desktop-data E:\Env\Docker\docker-desktop-data docker-desktop-data.tar --version 2
    

    成功, E:\Env\Docker\ 这个目录可以替换成自己的目录 image.png

  • 重启 docker-desktop, 然后拉取一个镜像, 就会发现新制定的路径下的文件修改时间做出改变, 表明路径更换成功

搭建环境

Nginx + PHP + MySQL + Redis

下载 MySQL 镜像
docker pull mysql:5.7.28
  1. 启动一个 mysql 容器

    docker run -d -p 3306:3306 -e MYSQL_ROOT_PASSWORD=123456 --name mysql mysql:5.7.28
    
  2. 进入 mysql 容器, 找到对应的配置文件位置和日志文件位置

    docker exec -it mysql /bin/sh
    

    配置文件

    image.png

    日志

    image.png

  3. 将容器内的文件拷贝出来, 目的是要一个MySQL的目录结构

    # 拷贝 log
    docker cp mysql:/var/log/mysql E:\Project\mysql-log
    # 拷贝 conf
    docker cp mysql:/etc/mysql E:\Project\mysql-conf
    

    命令解释 : docker cp 容器名:容器内路径 宿主机路径(Win10路径)

    因为复制的是整个目录,所以复制出来的地址有点小问题. 需要在Win10中调整下. 调整如下: 将mysql-log中的mysql目录里的所有文件复制到mysql-log目录中. 也就是所将日志文件的目录深度退一层; 同理 mysql-conf 文件的目录深度退一层.

  4. 删除 mysql 容器

    # 容器 停止 --> 删除
    docker stop mysql
    docker rm mysql
    
  5. 采用容器挂载卷的方式生成 mysql 容器

    docker run -d -v E:\Project\mysql-log:/var/log/mysql/ -v E:\Project\mysql-conf:/etc/mysql/ -p 3306:3306 -e MYSQL_ROOT_PASSWORD=123456 --name mysql mysql:5.7.28
    
    • -p 开放端口, 宿主机端口:容器端口

    • -name 给容器创建名称

    • -v volumes 挂载卷, 宿主机目录在前, 容器目录在后

    • -d 后台运行

    -v 挂载卷目录, 也可以说是将容器内部的文件映射到宿主机上; 使用这种方式生成的容器, 我们修改一些配置文件不必再进入容器内修改, 直接在宿主机映射目录内修改配置文件即可.

  6. Navicat 连接测试

下载 PHP 镜像
docker pull php:7.4-fpm
  1. 启动一个 PHP 容器

    docker run -d -p 9000:9000 --name php74 php:7.4-fpm
    
  2. 进入 php74 容器, 找到对应的配置文件位置和日志文件位置

    docker exec -it php74 /bin/sh
    
  3. 将容器内的文件拷贝出来, 目的是要一个 PHP 配置文件的目录结构

    • 配置文件 /usr/local/etc
    • 日志文件 /usr/local/var/log
    • 项目文件 /var/www/html
    # 拷贝 log
    docker cp php74:/usr/local/var/log E:\Project\php74-log
    # 拷贝 conf
    docker cp php74:/usr/local/etc E:\Project\php74-conf
    # 拷贝 www
    docker cp php74:/var/www/html E:\Project\www
    

    命令解释 : docker cp 容器名:容器内路径 宿主机路径(Win10路径)

    因为复制的是整个目录,所以复制出来的地址有点小问题. 需要在Win10中调整下. 调整和 MySQL 一样

  4. 删除 php74 容器

    # 容器 停止 --> 删除
    docker stop php74
    docker rm php74
    
  5. 采用容器挂载卷的方式生成 php74 容器

    docker run -d -v E:\Project\php74-log:/usr/local/var/log -v E:\Project\php74-conf:/usr/local/etc -v E:\Project\www:/var/www/html -p 9000:9000 --link mysql:mysql --name php74 php:7.4-fpm
    
    • -p 开放端口, 宿主机端口:容器端口
    • -name 给容器创建名称
    • -v volumes 挂载卷, 宿主机目录在前, 容器目录在后
    • -d 后台运行
    • --link 容器1 和 容器2 连通

    -v 挂载卷目录, 也可以说是将容器内部的文件映射到宿主机上; 使用这种方式生成的容器, 我们修改一些配置文件不必再进入容器内修改, 直接在宿主机映射目录内修改配置文件即可.

  6. 进入容器, 安装 php 扩展

    #进入容器
    docker exec -it php74 /bin/sh
    
    # 扩展1
    docker-php-ext-install pdo_mysql
    # 扩展2
    docker-php-ext-install mysqli
    
  7. 查看扩展是否安装

    php -m 
    
下载 Nginx 镜像
docker pull nginx:1.21.4
  1. 启动一个 nginx 容器

    docker run -d -p 80:80 --name nginx nginx:1.21.4
    
  2. 进入 nginx 容器, 找到对应的配置文件位置和日志文件位置

    docker exec -it nginx /bin/sh
    
  3. 将容器内的文件拷贝出来, 目的是要一个 nginx 配置文件的目录结构

    • 配置文件 /etc/nginx/
    • 日志文件 /var/log/nginx/
    # log
    宿主机目录手动创建 access.log, error.log 两个文件
    # 拷贝 conf
    docker cp nginx:/etc/nginx E:\Project\nginx-conf
    

    命令解释 : docker cp 容器名:容器内路径 宿主机路径(Win10路径) 因为复制的是整个目录,所以复制出来的地址有点小问题. 需要在Win10中调整下. 调整和 MySQL 一样

  4. 删除 nginx 容器

    # 容器 停止 --> 删除
    docker stop nginx
    docker rm nginx
    
  5. 采用容器挂载卷的方式生成 nginx 容器

    docker run -d -p 80:80 -v E:\Project\www:/var/www/html -v E:\Project\nginx-log:/usr/local/var/log -v E:\Project\nginx-conf:/etc/nginx --link php74:php7.4-fpm --name nginx nginx:1.21.4 
    
    • -p 开放端口, 宿主机端口:容器端口
    • -name 给容器创建名称
    • -v volumes 挂载卷, 宿主机目录在前, 容器目录在后
    • -d 后台运行
    • --link 容器1 和 容器2 连通
  6. 修改配置文件

    采用文件挂载的方式启动的容器, 我们不必再进入容器中修改了, 直接在宿主机目录下修改件就可以了.

    编辑 E:\Project\nginx-conf\conf.d\default.conf(这是我的目录, 自行替换)

    image.png

  7. 重启 nginx

    • 进入 nginx 容器, 执行 nginx -s reload
    • 直接重启 nginx 容器, 执行 docker restart nginx (线上服务器, 不建议这样操作, 建议使用第一种方式!)
  8. 测试

    E:\Project\www 创建一个 index.php

    <?php
    echo phpinfo();
    
    

    浏览器中打开 http://localhost/

    image.png

    看到这个页面, OK, 成功!

下载 Redis 镜像
docker pull redis:5.0.3-alpine
  1. 准备 redis 配置文件

    官方下载

    选择合适的版本下载, 放置在目录下, 方便作为挂载卷启动容器

  2. redis 配置文件的目录结构

    • 配置文件 /etc/redis.conf

    • 数据文件 /data/

  3. 采用容器挂载卷的方式生成 redis 容器

     docker run --restart=always -p 6379:6379 --name redis -v D:\Project\redis-conf\redis.conf:/etc/redis/redis.conf -v D:\Project\data\redis:/data -d redis:5.0.3-alpine redis-server /etc/redis/redis.conf  --appendonly yes  --requirepass 123456
    
    • --restart=always 表示自动重启
    • -p 开放端口, 宿主机端口:容器端口
    • -name 给容器创建名称
    • -v volumes 挂载卷, 宿主机目录在前, 容器目录在后
    • -d 后台运行
  4. 测试

    使用工具 Redis Desktop Manager 连接测试!

    image.png

  5. 设置密码

    上面生成容器的时候, 指定了密码. 也可以手动修改 redis.conf 配置文件设置密码

    找到刚才下载的 redis.conf 文件打开,找到 requirepass 取消注释, 设置成自己想要的

    image.png

参考文献