在开发中使用Docker-续

本文内容承接上一篇:在开发中使用Docker

运行多个容器

下面我们用一个稍微复杂点儿的服务来演示如何搭配使用多个容器。演示使用的计数器服务由web服务,保存计数用的Redis实例,以及保存业务数据的Mysql实例组成,共运行三个容器。

使用Docker运行mysql和redis

1
2
3
4
5
6
7
8
9
10
11
12
13
14
# 创建一个自定义bridge network,后续所有的容器都连接到这个网络上以便相互访问
docker network create counter-net
# 运行mysql 5,该命令会自动从Docker Hub拉取镜像
docker run --rm \
--network counter-net \
--name mysql \
-e MYSQL_ROOT_PASSWORD=12345678 \
-d mysql:5

# 运行redis,该命令会自动从Docker Hub拉去镜像redis
docker run --rm \
--name redis \
--network counter-net \
-d redis

构建simple-counter

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# 从samples仓库中签出simple-counter
git init simple-counter
cd simple-counter
git remote add origin git@github.com:hadix-lin/samples.git
git config core.sparsecheckout true
echo "simple-counter/" > .git/info/sparse-checkout
git pull origin master
# 构建simple-counter
mvn package
cp target/simple-counter-1.0-SNAPSHOT.jar docker-image/
cd docker-image
# 在docker-image文件夹中有Dockerfile文件
docker build -t simple-counter .
docker run -p 8080:8080 \
--rm \
--name simple-counter \
--network counter-net \
-d simple-counter

simple-counter/docker-image/Dockerfile内容如下:

1
2
3
4
FROM openjdk:8
COPY simple-counter-1.0-SNAPSHOT.jar app.jar
EXPOSE 8080/TCP
CMD ["java","-jar","app.jar"]

然后浏览器访问http://127.0.0.1:8080/可以得到如下响应

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
{
"hostSummary": { //数据库主机信息
"statement_avg_latency": "175.19 us",
"current_connections": "12",
"total_connections": "24",
"unique_users": "1",
"current_memory": "0 bytes",
"file_ios": "1393",
"host": "172.17.0.1",
"total_memory_allocated": "0 bytes",
"statements": "3407",
"file_io_latency": "3.85 ms",
"statement_latency": "596.86 ms",
"table_scans": "217"
},
"counter": 24 //每次访问计数器+1
}

要关闭服务使用如下命令:

1
2
3
4
5
6
7
8
docker stop <container id or name>
# 本文启动了三个容器,故需要下面三条指令来关闭容器
docker stop mysql
docker stop redis
docker stop simple-counter

#获取container id or name
docker container ls

默认情况下,同一个主机上运行的docker容器会加入一个默认的bridge网络,可以通过容器的ip地址互相访问。但是镜像构建时是无法知道依赖容器的ip地址的,在上面的示例中是通过”mysql”,”redis”这样的hostname进行访问的,所以在此需要使用docker network create \ 来创建自定义网络,自定义网络会为加入该网络的容器提供自动DNS解析,容器可以通过名称互相访问。

在上面的示例中,simple-counter中有如下配置来控制redis和mysql连接:

1
2
3
> spring.datasource.url=jdbc:mysql://mysql:3306/sys
> spring.redis.host=redis
>

由于以上配置的存在,要让simple-counter正常运行,redis和mysql的容器名称必须与配置中使用的主机名称一致。

使用docker-compose

上面的命令比较繁琐,可以提前准备一个docker-compose.yml文件来进行管理。

simple-counter/docker-image/docker-compose.yml内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
version: "3"
services:
redis: # 服务名
image: redis # 要部署的镜像
networks:
- counter-net
mysql:
image: mysql:5 # 要部署的镜像
environment:
- MYSQL_ROOT_PASSWORD=12345678
networks:
- counter-net
web:
build: . # 构建镜像使用的context
ports:
- "8080:8080"
networks:
- counter-net
networks: # 定义网络,相当于docker network create <net-name>
counter-net:

该文件定义了三个服务redis、mysql、web。其中web是通过simple-counter/docker-image/Dockerfile构建的。

有了这个文件后,运行simple-counter服务仅需要如下命令即可:

1
2
3
4
5
6
7
8
9
10
11
12
13
# 从samples仓库中签出simple-counter
git init simple-counter
cd simple-counter
git remote add origin git@github.com:hadix-lin/samples.git
git config core.sparsecheckout true
echo "simple-counter/" > .git/info/sparse-checkout
git pull origin master
# 构建simple-counter
mvn package
cp target/simple-counter-1.0-SNAPSHOT.jar docker-image/
## 如果之前已经构建过simple-counter前面都可以跳过
cd docker-image
docker-compose up

关闭服务使用

1
2
cd docker-image
docker-compose down

命令总结

1
2
3
4
5
6
7
8
9
# 创建自定义网络
docker network create <net_name>
# 运行容器并加入网络
docker run --network <net_name> [other_params] <image:tag>
# 列出所有运行的容器
docker container ls
# 使用编排文件管理多个容器
docker-compose up
docker-compose down