Docker容器化从零开始搭建Spring Cloud微服务系统:docker-compose
前言
在没有docker-compose
之前,我们创建和启动一个容器方式如下:
1.通过类似下面两种方式的命令来构建或者拉取一个docker
镜像。
方式1:创建Dockerfile
文件来构建镜像(命令最后的点别漏了~):
docker build -t registry.cn-beijing.aliyuncs.com/wangjihong/nacos-server:1.0.0 .
方式2: 直接从Docker Hub
或者阿里云
或者网易云
等等平台拉取镜像。
docker pull registry.cn-beijing.aliyuncs.com/wangjihong/nacos-server:1.0.0
2.使用命令docker run ...
来来依赖镜像创建并运行一个容器,中间还要加一些复杂的参数。
docker run --restart always --privileged=true -e MODE=standalone -e SPRING_DATASOURCE_PLATFORM="mysql" -e MYSQL_MASTER_SERVICE_HOST="www.wangjihong.com.cn" -e MYSQL_MASTER_SERVICE_PORT="3300" -e MYSQL_MASTER_SERVICE_DB_NAME="nacos" -e MYSQL_MASTER_SERVICE_USER="root" -e MYSQL_MASTER_SERVICE_PASSWORD="123456" -e MYSQL_SLAVE_SERVICE_HOST="www.wangjihong.com.cn" -e MYSQL_SLAVE_SERVICE_PORT="3301" -v=/usr/local/dockerfiles/nacos/data:/home/nacos/data -v=/usr/local/dockerfiles/nacos/logs:/home/nacos/logs --name docker-nacos-server1.0.0 -d -p 8848:8848 registry.cn-beijing.aliyuncs.com/wangjihong/nacos-server:1.0.0
3.使用命令docker exec ...
进入容器操作。
docker exec -it docker-nacos-server1.0.0 bash
4.查看容器启动日志。
docker logs -f docker-nacos-server1.0.0
综上我们可以看出,运行单个docker
容器我们要用命众多命令来管理容器,这种情况下若是只运行一个容器还好,但如果我们有一堆容器(如: mysql
、kibana
、 elasticsearch
等等...)需要执行的话,这样管理是极其麻烦的,利器docker-compose
的出现便解决了此类问题。
What-什么是docker-compose
- Docker Compose 将所管理的容器分为三层,分别是工程(project)、服务(service)、容器(container)。
- Docker Compose 运行目录下的所有文件(docker-compose.yml)组成一个工程,一个工程包含多个服务,每个服务中定义了容器运行的镜像、参数、依赖,一个服务可包括多个容器实例。
- Docker Compose 是一个批处理工具,我们可以通过配置一个
docker-compose.yml
文件去定义多个容器的应用,通过一条命令就可以根据docker-compose.yml
文件创建出指定的容器,文件格式如下(使用docker-compose.yml
部署微服务调用链监控组件skywalking
):
version: '2' services: elasticsearch: image: elasticsearch:5.6 container_name: elasticsearch ports: - 9200:9200 volumes: - ./es/data:/usr/share/elasticsearch/data - ./es/config/elasticsearch.yml:/usr/share/elasticsearch/config/elasticsearch.yml kibana: image: kibana:5.6 container_name: kibana ports: - 5601:5601 links: - elasticsearch:elasticsearch depends_on: - elasticsearch environment: ELASTICSEARCH_URL: http://elasticsearch:9200 skywalking: image: weihanli/skywalking:5.0.0-GA container_name: skywalking ports: - 10800:10800 - 11800:11800 - 12800:12800 - 8090:8080 volumes: - ./skywalking/application.yml:/app/skywalking/config/application.yml links: - elasticsearch:elasticsearch depends_on: - elasticsearch
Why-为什么要用docker-compose
可参考前言介绍。
How-如何使用docker-compose
安装docker-compose
从github上下载docker-compose二进制文件 https://github.com/docker/com... 并按描述安装。
1.下载最新版的docker-compose文件。
sudo curl -L https://github.com/docker/compose/releases/download/1.16.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
2.添加可执行权限。
sudo chmod +x /usr/local/bin/docker-compose
3.测试安装结果。
docker-compose --version
4.安装pip。
sudo pip install docker-compose
运行docker-compose
1.在centos
上创建一个docker-compose.yml
文件,里面写上自己的多容器内容,如上述skywalking
对应的文件内容。
2.最后在centos
上打开docker-compose.yml
所在的文件夹路径下执行docker-compopse up
就可以启动了,如果需要后台启动则为docker-compopse up -d
。
docker-compose配置文件参数使用详解
通过上述描述我们可以看到一份标准配置文件应该包含 version、services、networks 三大部分,其中最关键的就是 services 和 networks 两个部分,下面先来看 services 的书写规则。
version
指定 docker-compose.yml 文件的写法格式,如:
version: '3'
services
定义多个容器服务集合,如定义docker-mysql5.7-master-service和elasticsearch-service两个容器服务写法:
services: docker-mysql5.7-master-sevice: image: registry.cn-beijing.aliyuncs.com/wangjihong/mysql:5.7 container_name: docker-mysql5.7-master ports: - 3300:3306 elasticsearch-sevice: image: elasticsearch:5.6 container_name: elasticsearch ports: - 9200:9200
image
标明image的ID,这个image的ID可以是本地也可以是远程的,如果本地不存在,Compose会尝试去pull下来,如在services标签下的第二级标签是docker-mysql5.7-master-service,它表示服务名称,用户可自定义名称,image则是指定服务的镜像名称或镜像ID,如果镜像在本地不存在,Compose将会尝试拉取这个镜像。
services: docker-mysql5.7-master-sevice: image: registry.cn-beijing.aliyuncs.com/wangjihong/mysql:5.7 container_name: docker-mysql5.7-master ports: - 3300:3306
build
配置构建时,Compose会利用它自动构建镜像,该值可以是一个路径,也可以是一个对象,用于指定Dockerfile参数。该参数指定Dockerfile文件的路径,Compose将会以一个已存在的名称进行构建并标记,并随后使用这个image。
示例:
services: docker-mysql5.7-master-sevice: image: mysql:5.7 container_name: docker-mysql5.7-master ports: - 3300:3306 build: context: /usr/local/dockerfiles/mysql dockerfile: Dockerfile args: - buildno=1 - password=secre
示例说明:
docker-mysql5.7-master-sevice容器服务会根据/usr/local/dockerfiles/mysql路径下的Dockerfile文件以buildno=1,password=secre为环境变量来构建出一个image ID为mysql:5.7的镜像。其中:
context
:是一个目录路径,也可以是一个git repository url。 当所提供的值是相对路径的时候,它被解释为compose文件位置的相对路径。目录里的信息会被当做构建内容发送到Docker daemon, context只支持version2+, version1只能使用build。
Dockerfile
:Compose将会使用指定的该Dockerfile文件去构建,但必须指定路径,如与context搭配使用。
args
:仅支持Version2+,用于添加构建环境变量参数,但是仅构建过程期间可以使用,如:
ARG buildno ARG password RUN echo "Build number: $buildno" RUN script-requiring-password.sh "$password"
depends_on
表示服务之间的依赖关系,作用如下:
1.docker-compose up
将会根据依赖关系的顺序开启所有服务,下面的例子中, kibana会早于elasticsearch服务先启动。
2.docker-compose up
SERVICE会自动包含 SERVICE的依赖,下面的例子中, 执行docker-compose up命令时kibana将会创建,同时也会启动elasticsearch服务。
version: '2' services: elasticsearch: image: elasticsearch:5.6 container_name: elasticsearch ports: - 9200:9200 volumes: - ./es/data:/usr/share/elasticsearch/data - ./es/config/elasticsearch.yml:/usr/share/elasticsearch/config/elasticsearch.yml kibana: image: kibana:5.6 container_name: kibana ports: - 5601:5601 links: - elasticsearch:elasticsearch depends_on: - elasticsearch environment: ELASTICSEARCH_URL: http://elasticsearch:9200
注意:kibana服务启动前并不会等待elasticsearch服务到ready状态才启动。如果需要等待其他服务到ready状态,可以参考https://docs.docker.com/compo...。
environment
环境变量配置,可以用数组或字典两种方式。
格式如:
environment: RACK_ENV: development SHOW: 'ture' ------------------------- environment: - RACK_ENV=development - SHOW=ture
示例如:
version: '2' services: kibana: image: kibana:5.6 container_name: kibana ports: - 5601:5601 links: - elasticsearch:elasticsearch depends_on: - elasticsearch environment: ELASTICSEARCH_URL: http://elasticsearch:9200
env_file
从文件中获取环境变量,可以指定一个文件路径或路径列表,其优先级低于 environment指定的环境变量。
env_file: .env --------------- env_file: - ./common.env
links
将指定容器连接到当前连接,可以设置别名,避免ip方式导致的容器重启动态改变的无法连接情况,达到服务之间可以使用服务名称相互访问,links 允许定义一个别名,从而使用该别名访问其它服务,类似于微服务中的根据服务名查找主机服务的场景。
version: '2' services: kibana: image: kibana:5.6 container_name: kibana ports: - 5601:5601 links: # 指定服务名称:别名 - elasticsearch:elasticsearch-server
备注:示例中kibana服务就可以使用elasticsearch或elasticsearch-server作为hostname访问elasticsearch:elasticsearch服务了。
volumes
挂载指定的路径或者named volumes, 可以在主机上指定一个路径 HOST:CONTAINER, 或者一个只读的HOST:CONTAINER:ro。
volumes: # Just specify a path and let the Engine create a volume - /var/lib/mysql # Specify an absolute path mapping - /opt/data:/var/lib/mysql # Path on the host, relative to the Compose file - ./cache:/tmp/cache # User-relative path - ~/configs:/etc/configs/:ro # Named volume
示例
将容器的/usr/share/elasticsearch/data挂载到宿主机的./es/data文件下。目的是可以不进入容器内部直接通过宿主机的./es/data目录就可以看到容器的数据内容,避免容器删除销毁后造成把数据也销毁了的严重问题。
version: '2' services: elasticsearch: image: elasticsearch:5.6 container_name: elasticsearch ports: - 9200:9200 volumes: - ./es/data:/usr/share/elasticsearch/data - ./es/config/elasticsearch.yml:/usr/share/elasticsearch/config/elasticsearch.yml
expose
对外暴露端口,只将端口暴露给连接的服务(已经linked的service可访问),而不暴露给主机。
expose: - "6666" - "8888"
ports
对外暴露的端口定义,和expose对应。
格式:- "宿主机端口:容器暴露端口"
ports: # 暴露端口信息 - "3300:3306" - "8080:8080"
注意:
当以 HOST:CONTAINER的形式映射端口的时候,当容器的端口低于60的时候可能会遇到错误,因为YAML会解析xx:yy数字为60。基于这个原因,我们推荐明确指定端口映射用字符串的形式。
ports: - "3000" - "3000-3005" - "8000:8000" - "9090-9091:8080-8081" - "49100:22" - "127.0.0.1:8001:8001" - "127.0.0.1:5000-5010:5000-5010
command
覆盖容器启动后默认执行的命令。
command: bundle exec thin -p 3000 ---------------------------------- command: [bundle,exec,thin,-p,3000]
dns
配置 dns 服务器,可以是一个值或列表。
dns: 8.8.8.8 ------------ dns: - 8.8.8.8 - 9.9.9.9
dns_search
配置 DNS 搜索域,可以是一个值或列表。
dns_search: example.com ------------------------ dns_search: - dc1.example.com - dc2.example.com
network_mode
network_mode: "bridge" network_mode: "host" network_mode: "none" network_mode: "service:[service name]" network_mode: "container:[container name/id]"
logs
--no-color 单色输出,不显示其他颜. -f, --follow 跟踪日志输出,就是可以实时查看日志 -t, --timestamps 显示时间戳 --tail 从日志的结尾显示,--tail=200
labels
添加 metadata 到容器中。可以使用数组或字典。
labels: app-description: "website for wangjihong" app-website: "www.wangjihong.com.cn" app-memo: "一个不太神奇的网站" labels: - "app-description=website for wangjihong" - "app-website=www.wangjihong.com.cn" - "app-memo=一个不太神奇的网站"
pid
将当前的PID设置为主机的PID,从而打开容器和host操作系统之间的PID地址共享。带有PID启动的容器可以访问和操纵其他真实机器空间容器。
pid:"host"
docker-compose命令使用详解
Docker Compose 常用命令与配置如下(与docker命令基本一致)。
ps
列出所有运行容器。
docker-compose ps
logs
查看服务日志输出。
docker-compose logs
port
打印绑定的公共端口,下面命令可以输出 elasticsearch 服务 9002 端口所绑定的公共端口。
docker-compose port elasticsearch 9002
build
构建或者重新构建服务。
docker-compose build
start
启动指定服务已存在的容器。
docker-compose start elasticsearch
stop
停止已运行的服务的容器。
docker-compose stop elasticsearch
rm
删除指定服务的容器。
docker-compose rm elasticsearch
up
构建、启动容器。
----前台启动--- docker-compose up ----后台启动--- docker-compose up -d ----指定文件后台启动--- docker-compose -f docker-compose-nacos.yml up -d
kill
通过发送 SIGKILL 信号来停止指定服务的容器。
docker-compose kill elasticsearch
pull
下载服务镜像。
docker-compose pull elasticsearch
scale
设置指定服务运行容器的个数,以 service=num 形式指定。
docker-compose scale user=3 movie=3
run
在一个服务上执行一个命令。
docker-compose run elasticsearch bash
总结
本文只是介绍了docker-compose基本内容,想深入了解可以自行查资料,嘿嘿。