前言
本文视频版教程:一个视频说清docker及docker compose的应用和部署(https://cloud.tencent.com/developer/video/82177)
本期教程将介绍Docker和Docker compose的基础应用,通过实际应用来讲解具体使用方法和两者的区别。
假设现在服务器上需要部署三个项目,项目ABC,他们的web服务都是nginx,但是PHP版本不同,mysql数据库的版本也不相同,在传统模式下,尽管PHP可以多版本互存,但是数据库的多版本互存,相对来说就困难一些,在这种情况下,docker就是一种很好的解决方案。
docker主要由镜像和容器两部分组成,镜像可以理解成是一个模板,那么容器就是根据镜像,创建的不同的可执行的实例,那么这些实例之间是相互独立的。
一、Docker 的安装
docker_16">1.1 安装 docker
安装过程可能会因为网络的问题而造成中断,如果中断了,只需重新执行下该命令就可以继续安装,安装成功后可以查看对应的版本,显示版本信息就证明安装已经完成了。
# 安装 Docker 所需的依赖
yum install -y yum-utils device-mapper-persistent-data lvm2# 添加 Docker 的 yum 源
yum-config-manager --add-repo https://mirrors.cloud.tencent.com/docker-ce/linux/centos/docker-ce.repo# yum 安装 Docker
yum install -y docker-ce docker-ce-cli containerd.io# 查看 Docker 版本
docker version
docker_36">1.2 启动 docker
启动docker并将docker设置为开机自启动,查看运行状态,当出现active (running)
的时候就表示正在运行之中。
# 执行以下命令启动 Docker
systemctl start docker# 然后将 Docker 设置为开机启动
systemctl enable docker# 查看 Docker 运行状态
service docker status# 可能返回以下内容,看到 active (running) 表示正在运行中
Redirecting to /bin/systemctl status docker.service
● docker.service - Docker Application Container EngineLoaded: loaded (/usr/lib/systemd/system/docker.service; enabled; vendor preset: disabled)Active: active (running) since Fri 2023-12-22 10:00:56 CST; 11s agoDocs: https://docs.docker.com
docker__60">1.3 配置 docker 镜像加速
因为docker的镜像都是在海外,所以说访问会比较慢,这时候可以设置成国内的加速镜像,这里选择的是腾讯云的,完成之后重启相关服务。
方法一:
# 创建 Docker 配置目录
mkdir -p /etc/docker# 配置 Docker 镜像加速源
vim /etc/docker/daemon.json# 输入以下内容后保存退出
{"registry-mirrors": ["https://mirror.ccs.tencentyun.com"]
}# 重启守护进程并重启 Docker
systemctl daemon-reload && systemctl restart docker
方法二:
sudo su -
cat >> /etc/docker/daemon.json <<- EOF
{"registry-mirrors": ["https://mirror.ccs.tencentyun.com"]
}
EOFsystemctl daemon-reload && systemctl restart docker
docker_97">1.4 体验 docker
设置完成之后就可以进行体验,通过简单的命令,就可以完成镜像的拉取和容器的创建,这里是拉取了nginx镜像创建的容器,创建完成之后就可以直接运行,此时通过IP,就可以访问nginx的默认页面,说明nginx已经成功部署完毕。
# 拉取最新的 nginx 镜像
docker pull nginx# 运行容器
docker run -d --name nginx -p 80:80 nginx# 查看容器
docker ps -a# 显示结果
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
cc5b9ffeb31d nginx "/docker-entrypoint.…" 6 seconds ago Up 5 seconds 0.0.0.0:80->80/tcp, :::80->80/tcp nginx
二、Docker 的镜像与容器
Docker 镜像是只读的模板。
Docker 容器是基于镜像创的运行的实例。
镜像与容器是docker的核心概念,通过刚才的操作拉取了nginx的镜像,这是一个只读的模板,基于这个镜像,创建了一个可以运行的nginx的实例。
三、Docker 容器的独立性
项目 | web服务 | php版本 | mysql版本 |
---|---|---|---|
项目A | nginx | php7.4 | mysql5.7 |
项目B | nginx | php8.0 | mysql8.0 |
项目C | nginx | php7.4 | mysql8.0 |
由于docker的独立性,在面对表格这样的复杂的部署环境时,就可以通过拉取不同的镜像,比如说nginx、PHP的不同版本,和mysql数据库的不同版本,分别创建对应的容器。
四、操作示例
4.1 部署思路
部署思路:分别拉取nginx、php7.4、php8.0、mysql5.7、mysql8.0的镜像,再创建不同的容器。
LNMP_a:nginx + php7.4 + mysql5.7
LNMP_b:nginx + php8.0 + mysql8.0
4.2 拉取镜像
为了演示分别搭建两套环境,第一套环境是nginx+PHP 7.4+mysql 5.7,首先将所需要的镜像全部拉取下来,其次查看当前所有已拉取的镜像。
# 拉取镜像docker pull nginxdocker pull php:7.4-fpm
docker pull php:8.0-fpmdocker pull mysql:5.7
docker pull mysql:8.0# 查看镜像
docker images
4.3 部署LNMP_a
LNMP_a:nginx + php7.4 + mysql5.7的环境要求,按照命令逐次执行,会依次创建数据库,PHP以及nginx的容器,并完成相关的配置。
# 建立 lnma_a 项目的各功能目录
mkdir -p ~/lnmp_a/{www,nginx,mysql}# 建立网络
docker network create network_a# mysql 容器
docker run -d --name mysql57_a \-p 33061:3306 \-v ~/lnmp_a/mysql:/var/lib/mysql \-e MYSQL_ROOT_PASSWORD=root_password \--network network_a \mysql:5.7# php 容器
docker run -d --name php74_a \-v ~/lnmp_a/www:/var/www/html \--network network_a \php:7.4-fpm# nginx conf 配置文件
vim ~/lnmp_a/nginx/default.conf########## 将下方内容复制至配置文件内 ##########
server {listen 80;server_name localhost;root /var/www/html;location / {index index.php index.html;}location ~ \.php$ {fastcgi_pass php74_a:9000;include fastcgi_params;fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;}
}
########## 将上方内容复制至配置文件内 ########### nginx 容器
docker run -d --name nginx_a \-p 8081:80 \-v ~/lnmp_a/www:/var/www/html \-v ~/lnmp_a/nginx/default.conf:/etc/nginx/conf.d/default.conf \--network network_a \nginx:latest
4.3.1 镜像容器说明
输入docker ps -a
命令查看容器,第一个nginx是体验的时候创建的,而后面含有下划线杠_a的名字是创建的第一个项目所包含的三个容器。这三个容器的数据是独立的,并且这个nginx与最开始的nginx也是互不干扰的。
4.3.2 测试文件说明
创建一个静态的文件和一个动态的PHP文件,分别测试一下容器是否能够正常使用。
当访问静态文件的时候,会出现hello lnmp_a,这表明静态文件也能够正常解析。
当对PHP文件进行访问的时候,可以看到已经有一个phpinfo,它能够显示出当前PHP的信息,说明PHP的动态解析也能够实现了。
# 建立网站静态文件
vim ~/lnmp_a/www/index.html# 内容
hello lnmp_a# 建立网站 php 文件
vim ~/lnmp_a/www/index.php# 内容
<?php
phpinfo();
4.3.3 数据库测试说明
同时也对数据库进行测试,建立一个新的数据库,测试一下数据库能否正常建立,并且在文件夹中,能否显示对应的数据库文件。
# 创建数据库
docker exec -it mysql57_a mysql -uroot -proot_passwordCREATE DATABASE IF NOT EXISTS docker_mysql57_db;
SHOW DATABASES;
exit;# 查看数据库文件
ls ~/lnmp_a/mysql/
4.4 部署LNMP_b
LNMP_b:nginx + php8.0 + mysql8.0
# 建立 lnma_a 项目的各功能目录
mkdir -p ~/lnmp_b/{www,nginx,mysql}# 建立网络
docker network create network_b# mysql 容器
docker run -d --name mysql80_b \-p 33062:3306 \-v ~/lnmp_b/mysql:/var/lib/mysql \-e MYSQL_ROOT_PASSWORD=root_password \--network network_b \mysql:8.0# php 容器
docker run -d --name php80_b \-v ~/lnmp_b/www:/var/www/html \--network network_b \php:8.0-fpm# nginx conf 配置文件
vim ~/lnmp_b/nginx/default.conf########## 将下方内容复制至配置文件内 ##########
server {listen 80;server_name localhost;root /var/www/html;location / {index index.php index.html;}location ~ \.php$ {fastcgi_pass php80_b:9000;include fastcgi_params;fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;}
}
########## 将上方内容复制至配置文件内 ########### nginx 容器
docker run -d --name nginx_b \-p 8082:80 \-v ~/lnmp_b/www:/var/www/html \-v ~/lnmp_b/nginx/default.conf:/etc/nginx/conf.d/default.conf \--network network_b \nginx:latest# 建立网站静态文件
vim ~/lnmp_b/www/index.html# 内容
hello lnmp_b# 建立网站 php 文件
vim ~/lnmp_b/www/index.php# 内容
<?php
phpinfo();# 创建数据库
docker exec -it mysql80_b mysql -uroot -proot_passwordCREATE DATABASE IF NOT EXISTS docker_mysql80_db;
SHOW DATABASES;
exit;# 查看数据库文件
ls ~/lnmp_b/mysql/
4.4.1 创建过程及测试说明
以同样的方式,建立第二个项目所需要的各种环境的容器,并且对第二个项目也进行,静态文件和PHP动态文件的访问,以及数据库的测试。
4.4.2 镜像与容器说明
通过命令查看当前服务器已建立好的容器,会发现主要分为3组。
这些容器之间都是相互独立,互不干扰,使用8081的端口访问第一个项目的页面,使用8082的端口访问第二个项目的页面,这样在同一个服务器上,就可以创建很多个容器。
4.5 主要命令功能说明
4.5.1 建立功能模块目录
第一个命令,主要是建立各功能模块的目录,其中www是放置程序和网页文件的,nginx目录是放置nginx配置文件的,mysql目录则是放置数据库文件的。
# 建立 lnma_a 项目的各功能目录
mkdir -p ~/lnmp_b/{www,nginx,mysql}
4.5.2 建立网络
第二个命令主要是用来建立一个网络,用于容器内部进行互相连接。
# 建立网络
docker network create network_b
4.5.3 创建数据库容器
接下来创建数据库的容器,-d参数表示是后台运行,-name参数用于给容器起一个名字,-p参数是进行端口映射,是将宿主主机的端口映射到容器之中,也就是将33061映射到3306,-v参数则是用于挂载,将主机目录挂载到容器之中,-e参数用于设置环境变量,此处设计的是数据库root账号的密码。
# mysql 容器
docker run -d --name mysql80_b \-p 33062:3306 \-v ~/lnmp_b/mysql:/var/lib/mysql \-e MYSQL_ROOT_PASSWORD=root_password \--network network_b \mysql:8.0
4.5.4 创建PHP容器
接下来是创建PHP的容器,这里只需注意一个-v参数。
# php 容器
docker run -d --name php80_b \-v ~/lnmp_b/www:/var/www/html \--network network_b \php:8.0-fpm
4.5.5 创建nginx conf配置文件
然后创建nginx conf的配置文件,将内容复制至配置文件内,这里主要是实现nginx能够正常解析PHP文件,所以要将PHP容器的名称填写在这里。
# nginx conf 配置文件
vim ~/lnmp_b/nginx/default.conf########## 将下方内容复制至配置文件内 ##########
server {listen 80;server_name localhost;root /var/www/html;location / {index index.php index.html;}location ~ \.php$ {fastcgi_pass php80_b:9000;include fastcgi_params;fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;}
}
########## 将上方内容复制至配置文件内 ##########
4.5.6 创建nginx容器
接下来就是创建nginx容器,-p参数端口映射,将8081映射到80,也就是说,这个容器可以通过8081的方式进行访问,-v参数将网站的目录映射到主机内就是www,第二个-v参数则是conf文件的映射。
# nginx 容器
docker run -d --name nginx_b \-p 8082:80 \-v ~/lnmp_b/www:/var/www/html \-v ~/lnmp_b/nginx/default.conf:/etc/nginx/conf.d/default.conf \--network network_b \nginx:latest
4.5.7 创建静态和动态文件
接下来就是创建静态的html文件,和动态的PHP文件,进行测试,看能不能正常解析。
# 建立网站静态文件
vim ~/lnmp_b/www/index.html# 内容
hello lnmp_b# 建立网站 php 文件
vim ~/lnmp_b/www/index.php# 内容
<?php
phpinfo();
4.5.8 数据库容器测试
这里是通过新建终端的方式,连接到容器内部,该容器为数据库容器,通过命令行的方式创建一个数据库,然后进行测试,使用命令,查看刚才创建的数据库是否存在,以及在文件夹中是否存在。
# 创建数据库
docker exec -it mysql80_b mysql -uroot -proot_passwordCREATE DATABASE IF NOT EXISTS docker_mysql80_db;
SHOW DATABASES;
exit;# 查看数据库文件
ls ~/lnmp_b/mysql/
五、Docker Compose
通过上述方法确实能够创建很多互不干扰的容器,也能够搭建不同的项目使用不同的环境,但是命令过于繁琐,需要的配置太多,导致非常不利于维护,也不利于迁移。
在面对这种情况下通常使用另外一种解决方案docker compose。
5.1 安装Docker Compose
按照文档中的命令进行安装,安装完成后可以查看版本号信息,有正确的信息返回,说明安装成功。
# 安装编译 Python 包所需的基础工具和 bcrypt 的依赖:
sudo yum install -y gcc openssl-devel bzip2-devel libffi-devel python3-devel make# 升级 pip 和 setuptools
sudo pip3 install --upgrade pip setuptools wheel# 安装 docker-compos
sudo pip3 install docker-compose# 查看版本
docker-compose --version
5.2 建立目录及核心配置文件
# 建立 lnma_a 项目的各功能目录
mkdir -p ~/lnmp_c/{www,nginx,mysql}# 建立 docker-compose.yml 文件
vim ~/lnmp_c/docker-compose.yml
dockercomposeyml_530">5.3 编写docker-compose.yml
docker-compose.yml是核心配置文件,它可以将多个关联的容器,定义在一个文件之中,避免手动输入复杂的命令,确保开发、测试、生产环境的一致性,能够自动处理容器间的依赖关系,以及快速启动和销毁整个应用。
version: "3"services:nginx:image: nginxcontainer_name: nginx_crestart: alwaysports:- 8083:80- 4433:443 volumes:- ~/lnmp_c/nginx/default.conf:/etc/nginx/conf.d/default.conf- ~/lnmp_c/www:/var/www/htmlphp:image: php:7.4-fpmcontainer_name: php74_crestart: alwaysvolumes:- ~/lnmp_c/www:/var/www/htmlmysql:image: mysql:8.0container_name: mysql80_crestart: alwaysports:- 33063:3306volumes:- ~/lnmp_c/mysql:/var/lib/mysqlenvironment:- MYSQL_ROOT_PASSWORD=root_password- MYSQL_DATABASE=lnmp_c- MYSQL_USER=lnmp_c_user- MYSQL_PASSWORD=lnmp_c_password
5.4 编写nginx conf配置
# nginx conf 配置文件
vim ~/lnmp_c/nginx/default.conf########## 将下方内容复制至配置文件内 ##########
server {listen 80;server_name localhost;root /var/www/html;location / {index index.php index.html;}location ~ \.php$ {fastcgi_pass php74_c:9000;include fastcgi_params;fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;}
}
########## 将上方内容复制至配置文件内 ##########
5.5 启动服务
通过已经编写好的docker-compose.yml配置文件,使用命令自动创建相关容器。
# 进入目录
cd lnmp_c# 启动容器
docker-compose up -d# 建立网站静态文件
vim ~/lnmp_c/www/index.html# 内容
hello lnmp_c# 建立网站 php 文件
vim ~/lnmp_c/www/index.php# 内容
<?php
phpinfo();# 查看数据库文件
ls ~/lnmp_c/mysql/
5.6 建立静态及动态测试文件
建立静态的html文件和动态的PHP文件,看看创建好的容器能否正常的解析。
5.7 查看数据库文件
因为在配置文件之中已经创建好了一个数据库,通过命令在文件系统中,也确实能够查看对应的数据库,说明数据库的建立也是正确的。
dockercomposeyml_635">5.8 docker-compose.yml文件介绍
这里是配置文件三个核心部分的介绍,重点关注的就是类似于-v、-p、-e参数,也就是端口映射,文件映射和环境变量的设置。
dockercompose_639">5.9 docker-compose的启动与重启
通过这种方式建立的容器,也可以很方便地重启,重启可以分为相对路径重启,和绝对路径重启。
方法一:相对路径写法
# 停止并删除所有由 Compose 管理的容器
docker-compose down# 启动容器
docker-compose up -d
方法二:绝对路径写法
# 停止并删除所有由 Compose 管理的容器
docker-compose -f ~/lnmp_c/docker-compose.yml down# 启动容器
docker-compose -f ~/lnmp_c/docker-compose.yml up -d
六、迁移测试
6.1 迁移说明
只需将当前服务器上项目lnmp_c的目录复制到其他服务器,进入指定目录重新执行docker-compose up -d
,即可一键拉取、创建项目lnmp_c所需要的容器。
并且因为将目录也打包过去了,那么网站的文件和数据库的数据都依然存在。
6.1 迁移前数据库准备
为了能够更好的测试数据迁移的完整性,通过终端的方式,先给项目c的数据库创建一些表和添加一些记录,然后迁移过去来查看数据是否完整。
docker exec -it mysql80_c mysql -uroot -proot_passwordSHOW DATABASES;use lnmp_c;CREATE TABLE `test` (`id` int(11) NOT NULL,`title` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;INSERT INTO `test` (`id`, `title`) VALUES
(1, 'title'),
(2, 'test');ALTER TABLE `test`ADD PRIMARY KEY (`id`);ALTER TABLE `test`MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=3;SELECT * FROM `test`;exit;
6.3 迁移过程说明
打开的是一台新的测试服务器,通过命令可以查看到已经将项目c的文件复制过来了,并且当前服务器上,并没有安装任何的镜像和容器,通过命令启动docker compose文件,可以看到,服务器已经自动开始拉取所需的镜像,自动创建所需的容器。
在创建好之后,我们可以通过IP加端口的方式,访问静态页面和动态页面,然后通过终端的方式,进入到数据库容器中,也能够看到,数据库表和记录,都完整地保留了过来,通过这样的迁移方式,能够保证新旧服务器程序,数据库所运行和环境完全一致。
总结
本期教程到此结束,通过对比Docker的两种使用方法,可以看出Docker compose的使用更为灵活方便,在日常使用中,推荐使用Docker compose的方法来进行部署。