zoukankan      html  css  js  c++  java
  • docker compose 的使用

    github 地址:https://github.com/docker/compose

    官方文档:https://docs.docker.com/compose/

    docker compose是什么?

    这里引用github上的一句话

    Docker Compose is a tool for running multi-container applications on Docker defined using the Compose file format. A Compose file is used to define how the one or more containers that make up your application are configured. Once you have a Compose file, you can create and start your application with a single command: docker-compose up.

    上面的翻译过来,简单来说就是管理容器的。

    还没懂?嗯,不光你没懂,我也没懂[/手动憨笑]

    举个例子[/手动思考]

    一个web项目可能有nginx,mysql,php-fpm等等,很多很多容器,当容器数量达到一定数量比如10个,这时候要扩展,需要先关掉容器 ,你需要一个个关掉,扩展,然后一个个启动,多麻烦,这时候docker compose出现了。它就是为了解决这个问题的。

    简单明白了是干嘛的,我们来看看官方文档上的介绍

    Compose is a tool for defining and running multi-container Docker applications. With Compose, you use a YAML file to configure your application’s services. Then, with a single command, you create and start all the services from your configuration. To learn more about all the features of Compose, see the list of features.

    Compose works in all environments: production, staging, development, testing, as well as CI workflows. You can learn more about each case in Common Use Cases.

    Using Compose is basically a three-step process:

    1. Define your app’s environment with a Dockerfile so it can be reproduced anywhere.
    2. Define the services that make up your app in docker-compose.yml so they can be run together in an isolated environment.
    3. Run docker-compose up and Compose starts and runs your entire app.

    大概意思:

    Compose是一个用于定义和运行多容器Docker应用程序的工具。使用Compose,您可以使用YAML文件来配置应用程序的服务。然后,只需要一个命令,就可以从配置中创建并启动所有服务。要了解关于Compose的所有特性的更多信息,请参见特性列表

    组合工作在所有环境中:生产、阶段、开发、测试以及CI工作流。您可以在常见用例中了解有关每个案例的更多信息。

    使用Compose基本上有三个步骤:

    1. 用Dockerfile定义你的应用环境,这样它就可以在任何地方复制。

    2. 在docker-compose中定义组成应用程序的服务。这样它们就可以在一个孤立的环境中一起运行。

    3. 运行docker-compose up,然后Compose启动并运行你的整个应用。

    docker compose ,docker swarm和k8s的区别

    你会发现你搜索docker compose的资料经常会出现,,docker swarm,k8s,那这些是干嘛的,有什么区别?

    Docker-Compose

    Docker-Compose 是用来管理你的容器的,有点像一个容器的管家,想象一下当你的Docker中有成百上千的容器需要启动,如果一个一个的启动那得多费时间。有了Docker-Compose你只需要编写一个文件,在这个文件里面声明好要启动的容器,配置一些参数,执行一下这个文件,Docker就会按照你声明的配置去把所有的容器启动起来,只需docker-compose up即可启动所有的容器,但是Docker-Compose只能管理当前主机上的Docker,也就是说不能去启动其他主机上的Docker容器

    Docker Swarm

    Docker Swarm 是一款用来管理多主机上的Docker容器的工具,可以负责帮你启动容器,监控容器状态,如果容器的状态不正常它会帮你重新帮你启动一个新的容器,来提供服务,同时也提供服务之间的负载均衡,而这些东西Docker-Compose 是做不到的

    k8s

    K8S,就是基于容器的集群管理平台,它的全称,是kubernetes。

    Kubernetes它本身的角色定位是和Docker Swarm 是一样的,也就是说他们负责的工作在容器领域来说是相同的部分,都是一个跨主机的容器管理平台,当然也有自己一些不一样的特点,k8s是谷歌公司根据自身的多年的运维经验研发的一款容器管理平台。而Docker Swarm则是由Docker 公司研发的。

    既然这两个东西是一样的,那就面临选择的问题,应该学习哪一个技术呢?实际上这两年Kubernetes已经成为了很多大公司的默认使用的容器管理技术,而Docker Swarm已经在这场与Kubernetes竞争中已经逐渐失势,如今容器管理领域已经开始已经逐渐被Kubernetes一统天下了。所以建议大家学习的时候,应该多考虑一下这门技术在行业里面是不是有很多人在使用。

    需要注意的是,虽然Docker Swarm在与Kubernetes的竞争中败下阵来,但是这个跟Docker这个容器引擎没有太大关系,它还是整个容器领域技术的基石,Kubernetes离开他什么也不是。

    总结

    Docker是容器技术的核心、基础,Docker Compose是一个基于Docker的单主机容器编排工具.而k8s/Docker Swarm是一个跨主机的集群部署工具

    Docker-Compose 安装

    参考:

    https://docs.docker.com/compose/install/

    下载

    Github源

    sudo curl -L "https://github.com/docker/compose/releases/download/1.27.4/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
    

    上面这个由于是github的,可能会比较慢

    可以使用这个地址

    Daocloud镜像

    curl -L https://get.daocloud.io/docker/compose/releases/download/1.27.4/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose
    

    可以看到上面的下载完毕之后应该是在/usr/local/bin/目录,我们进该目录看下

    image-20210111095537523

    可以看到已经下载成功

    授权

    给程序授予可执行权限

    sudo chmod +x /usr/local/bin/docker-compose
    

    测试是否安装成功

    docker-compose version
    

    image-20210111100515723

    快速体验

    参考:https://docs.docker.com/compose/gettingstarted/

    这是官方提供的一个入门例子

    就是python 使用falask框架,数据库使用redis的一个计数器

    前提条件要已经安装了docker和docker compose

    好,我们现在跑一下官方的测试,体验一下

    1.创建一个目录

    $ mkdir composetest
    $ cd composetest
    

    2.创建一个app.py的应用

    创建app.py文件,文件写入下面的内容

    import time
    
    import redis
    from flask import Flask
    
    app = Flask(__name__)
    cache = redis.Redis(host='redis', port=6379)
    
    def get_hit_count():
        retries = 5
        while True:
            try:
                return cache.incr('hits')
            except redis.exceptions.ConnectionError as exc:
                if retries == 0:
                    raise exc
                retries -= 1
                time.sleep(0.5)
    
    @app.route('/')
    def hello():
        count = get_hit_count()
        return 'Hello World! I have been seen {} times.
    '.format(count)
    

    注意保存退出

    在此示例中,redis是应用程序网络上的redis容器的主机名。我们为Redis使用默认端口6379

    处理瞬态错误

    注意get_hit_count函数的编写方式。如果redis服务不可用,这个基本的重试循环使我们可以多次尝试请求。当应用程序联机时,这在启动时很有用,但是如果需要在应用程序的生命周期内随时重新启动Redis服务,则还可以使我们的应用程序更具弹性。在群集中,这还有助于处理节点之间的瞬时连接断开。

    3.创建应用的依赖包文件

    创建一个requirements.txt文件,文件写入下面内容

    flask
    redis
    

    现在应用相关的基本已经准备好了,现在可以使用dockerfile构建应用了

    4.使用dockerfile将应用构建为镜像

    有关dockerfile使用,可以参考:

    https://www.cnblogs.com/makalochen/p/14247807.html

    创建一个Dockerfile文件,文件里面写入下面的内容

    FROM python:3.7-alpine
    WORKDIR /code
    ENV FLASK_APP=app.py
    ENV FLASK_RUN_HOST=0.0.0.0
    RUN apk add --no-cache gcc musl-dev linux-headers
    COPY requirements.txt requirements.txt
    RUN pip install -r requirements.txt
    EXPOSE 5000
    COPY . .
    CMD ["flask", "run"]
    

    这告诉Docker:

    • 从Python 3.7映像开始构建映像。
    • 将工作目录设置为/code
    • 设置flask命令使用的环境变量。
    • 安装gcc和其他依赖项
    • 复制requirements.txt并安装Python依赖项。
    • 向图像添加元数据以描述容器正在侦听端口5000
    • .项目中的当前目录复制到.映像中的工作目录。
    • 将容器的默认命令设置为flask run

    5.创建docker compose服务配置文件

    创建docker-compose.yml文件,文件写入下面内容

    version: "3.9"
    services:
      web:
        build: .
        ports:
          - "5000:5000"
      redis:
        image: "redis:alpine"
    

    该Compose文件定义了两个服务:webredis

    网络服务

    web服务使用从Dockerfile当前目录中构建的映像。然后,它将容器和主机绑定到暴露的端口5000。此示例服务使用Flask Web服务器的默认端口5000

    Redis服务

    redis服务使用 从Docker Hub注册表中提取的公共Redis映像。

    6.启动服务

    在项目目录中,运行

    docker-compose up
    

    启动完成

    image-20210111141409332

    关于版本的问题

    这一步按照官网粘贴,有可能会出现版本不一致的情况,如:

    ERROR: Version in "./docker-compose.yml" is unsupported. You might be seeing this error because you're using the wrong Compose file version. Either specify a supported version (e.g "2.2" or "3.3") and place your service definitions under the services key, or omit the version key and place your service definitions at the root of the file to use version 1.

    image-20210111103531451

    解决办法

    重新下载docker-compose

    #删除
    sudo rm /usr/local/bin/docker-compose
    #下载
    curl -L https://get.daocloud.io/docker/compose/releases/download/1.27.4/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose
    #授权
    sudo chmod +x /usr/local/bin/docker-compose
    #查看版本
    docker-compose version
    

    7.浏览器测试访问

    image-20210111141548262

    到此体验项目运行完毕,你会发现我们没有用任何拉取镜像,构建镜像,启动容器的命令,一个命令就把项目跑起来了,这就是docker compose的作用。

    docker compoe常用命令

    #构建建启动nignx容器
    docker-compose up -d nginx                     
    
    # 登录到nginx容器中
    docker-compose exec nginx bash           
    
    #删除所有nginx容器,镜像
    docker-compose down                              
    
    #显示所有容器
    docker-compose ps                                   
    
    #重新启动nginx容器
    docker-compose restart nginx                   
    
    #在php-fpm中不启动关联容器,并容器执行php -v 执行完成后删除容器
    docker-compose run --no-deps --rm php-fpm php -v  
    
    #构建镜像 。
    docker-compose build nginx                             
    
    #不带缓存的构建。
    docker-compose build --no-cache nginx   
    
    #查看nginx的日志 
    docker-compose logs  nginx                     
    
    # 查看nginx的实时日志
    docker-compose logs -f nginx                  
     
    # 验证(docker-compose.yml)文件配置,当配置正确时,不输出任何内容,当文件配置错误,输出错误信息。 
    docker-compose config  -q                       
    
    #以json的形式输出nginx的docker日志
    docker-compose events --json nginx       
    
    # 暂停nignx容器
    docker-compose pause nginx                
    
    #恢复ningx容器
    docker-compose unpause nginx             
    
    #删除容器(删除前必须关闭容器)
    docker-compose rm nginx                       
    
    #停止nignx容器
    docker-compose stop nginx                    
    
    #启动nignx容器
    docker-compose start nginx                    
    

    yaml 文件编写规则

    参考:

    https://docs.docker.com/compose/compose-file/compose-file-v3/

    yaml命令特别多,但是我们一般只要关注三层即可

    #三层!
    
    # 版本
    version: "3.9" 
    # 服务
    services:
    	服务1:web
    		#服务配置
    		images
    		build
    		network
    		原来docker的配置
    		....
    	服务2:redis
    	...
    #其他配置 网络/卷、全局规则
    volumes:
    networks:
    configs:
    

    yaml语法规则

    • 大小写敏感
    • 使用缩进表示层级关系
    • 缩进不允许使用tab,只允许空格
    • 缩进的空格数不重要,只要相同层级的元素左对齐即可
    • '#'表示注释

    结构介绍

    docker-compose.yaml 文件结构主要由

    version # docker compose版本
    networks # 网络,用于docker容器内部通讯
    x-{name} # 模版命名规则 以x-开头 用于复用
    volumes # 挂载卷
    services # 服务模块,内部定义容器信息 其内部参数相当于docker run时的参数
    

    模块介绍

    Docker Compose官方文档

    version

    设定docker-compose.yaml的版本
    需要升级的话,参看文档 版本升级参考文档

    Compose file 版本 Docker Engine 版本
    3.8 19.03.0+
    3.7 18.06.0+
    3.6 18.02.0+
    3.5 17.12.0+
    3.4 17.09.0+
    3.3 17.06.0+
    3.2 17.04.0+
    3.1 1.13.1+
    3.0 1.13.0+
    2.4 17.12.0+
    2.3 17.06.0+
    2.2 1.13.0+
    2.1 1.12.0+
    2.0 1.10.0+
    1.0 1.9.1.+

    network_mode

    使用与--network参数相同的值,以及特殊形式service:[service name]一般配合 networks使用

    network_mode: "bridge"
    network_mode: "host"
    network_mode: "none"
    network_mode: "service:[service name]"
    network_mode: "container:[container name/id]"
    

    networks

    为当前docker-compose.yaml文件创建的容器设定网络

    不一定存在于和version同级,也可以在各个其他模块中,例如services中

    可以参考:https://www.jianshu.com/p/3004fbce4d37

    • 内部网络
    services:
      some-service:
        networks:
         - some-network
         - other-network
    
    • 公用网络
    version: "3"
    networks:
      default-network:
    

    aliases(待补充)

    网络的别名

    version: "3.8"
    
    services:
      web:
        image: "nginx:alpine"
        networks:
          - new
    
      worker:
        image: "my-worker-image:latest"
        networks:
          - legacy
    
      db:
        image: mysql
        networks:
          new:
            aliases:
              - database
          legacy:
            aliases:
              - mysql
    
    networks:
      new:
      legacy:
    

    ipv4_address , ipv6_address(待补充)

    version: "3.8"
    
    services:
      app:
        image: nginx:alpine
        networks:
          app_net:
            ipv4_address: 172.16.238.10
            ipv6_address: 2001:3984:3989::10
    
    networks:
      app_net:
        ipam:
          driver: default
          config:
            - subnet: "172.16.238.0/24"
            - subnet: "2001:3984:3989::/64"
    

    services

    最主要的部分,用来配置各个服务

    build

    用于构建镜像,当build和image字段都存在时,使用image指定的镜像名和tag作为build镜像的name和tag

    version: "3.8" # docker compose版本
    services:
      webapp: # docker-compose定义的服务(容器)名,主要是针对docker-compose命令的参数,与docker ps看到的容器名不一定一致
        build: # 使用Dockerfile构建镜像
          context: ./dir 上下文路径,相对路径则是相对于compose文件路径
          dockerfile: Dockerfile-alternate # 指定Dockerfile文件名
          args: # 指定Dockerfile的参数 环境变量
            buildno: 1 # directory写法和list写法均可
    
    context

    可以使用相对路径或者git仓库的url

    build:
      context: ./dir
    
    Dockerfile

    指定Dockerfile文件名,必须指定context

    build:
      context: .
      dockerfile: Dockerfile-alternate
    
    args

    Dockerfile中的ARG字段,用于指定docker build时的环境变量

    ARG buildno
    ARG gitcommithash
    
    RUN echo "Build number: $buildno" # bash-like风格的写法
    RUN echo "Based on commit: $gitcommithash"
    

    可以使用list或者map来设定args

    build:
      context: .
      args: # map
        buildno: 1
        gitcommithash: cdc3b19
    build:
      context: .
      args: # list
        - buildno=1
        - gitcommithash=cdc3b19
    

    tips
    如果需要使用boolean值,需要使用双引号("true", "false", "yes", "no", "on", "off"),以便解析器将他们解析为字符串。

    cache_from

    为build过程指定cache

    build:
      context: .
      cache_from:
        - alpine:latest
        - corp/web_app:3.14
    
    labels

    同Dockerfile中的LABEL指令,为镜像设定metadata

    build:
      context: .
      labels: # map
        com.example.description: "Accounting webapp"
        com.example.department: "Finance"
        com.example.label-with-empty-value: ""
    build:
      context: .
      labels: # list
        - "com.example.description=Accounting webapp"
        - "com.example.department=Finance"
        - "com.example.label-with-empty-value"
    
    network

    docker --network指令,为容器指定网络,个人理解为设定局域网
    桥接可以将两个物理局域网连接起来
    三种模式

    build:
      context: .
      network: host # host模式,网络延迟最低,性能与宿主机一致
    build:
      context: .
      network: custom_network_1 # 自创network 
    build:
      context: .
      network: none # 无网络
    
    shm_size

    设置容器内/dev/shm目录的大小

    /dev/shm目录非常重要,此目录并不在硬盘上,而是在内存中,默认大小为内存的一半大小,存入其中的文件不会被清空,容器内划分此目录可以一定程度上指定容器的性能。

    build:
      context: .
      shm_size: '2gb' # 使用字符串设置大小
    build:
      context: .
      shm_size: 10000000 # 设置字节大小
    

    command

    相当于Dockerfile中的CMD命令

    command: bundle exec thin -p 3000 # shell-like
    command: ["bundle", "exec", "thin", "-p", "3000"] # json-like
    

    container_name

    相当于docker run --name

    container_name: my-web-container
    

    depends_on

    用于表述服务之间的依赖关系

    docker-compose up时,会根据depends_on来决定启动顺序

    version: "3.8"
    services:
      web:
        build: .
        depends_on: # 先启动 db 和 redis
          - db
          - redis
      redis:
        image: redis
      db:
        image: postgres
    

    tips:
    docker-compose 不会等待depends_on中的容器的状态时‘ready’时才启动,所以需要在启动完成后检查容器状态。官方给出了解决办法,使用shell脚本来曲线救国,不做赘述。

    depends_on does not wait for db and redis to be “ready” before starting web - only until they have been started. If you need to wait for a service to be ready, see Controlling startup order for more on this problem and strategies for solving it.
    ----form https://docs.docker.com/compo...

    devices

    挂载的外接设备,与--devices功能相同

    devices:
      - "/dev/ttyUSB0:/dev/ttyUSB0"
    

    dns

    自定义dns地址

    dns: 8.8.8.8 # 单个string值
    dns: # list 
      - 8.8.8.8
      - 9.9.9.9
    

    自定义dns搜索域名

    dns_search: example.com # 单个string值
    dns_search:
      - dc1.example.com
      - dc2.example.com
    

    entrypoint

    覆盖重写默认的 entrypoint

    entrypoint: /code/entrypoint.sh
    

    同Dockerfile中的写法

    entrypoint: ["php", "-d", "memory_limit=-1", "vendor/bin/phpunit"]
    

    tips:
    docker-compose.yaml 中的 entrypoint 清空Dockerfile中的CMD命令,并覆盖所有的Dockerfile中的ENTRYPOINT指令。

    env_file

    docker-compose.yaml添加环境变量文件。如果在docker-compose -f FILE中设置了 compose 文件,则env_file中的文件路径是相对于FILE的相对路径

    env_file: .env # single value
    env_file: # list
      - ./common.env
      - ./apps/web.env
      - /opt/runtime_opts.env
    

    tips:
    .env 文件格式:

    # Set Rails/Rack environment # '#'为注释,
    # 空行会被忽略
    RACK_ENV=development # 格式为 VAR=VAL
    

    .env 文件中的环境变量无法在build过程中被显示读取,只会被docker-compose.yaml文件读取,如果需要在build时使用该环境变量,请在build后加args子参数。

    对于指定多个.env文件的情况,官网的这句话贼复杂

    Keep in mind that the order of files in the list is significant in determining the value assigned to a variable that shows up more than once.
    ---from https://docs.docker.com/compo...

    直译过来是

    请记住,列表中文件的顺序对于确定分配给多次显示的变量的值很重要。

    因为对环境参数文件的处理是自上而下的,所以翻译成人话就是,多个参数文件中包含同一个环境变量,以最后一个为准。

    environment

    添加环境变量

    environment: # map
      RACK_ENV: development
      SHOW: 'true'
      SESSION_SECRET:
    environment: # list
      - RACK_ENV=development
      - SHOW=true
      - SESSION_SECRET
    

    tips:
    .env 文件中的环境变量无法在build过程中被显示读取,只会被docker-compose.yaml文件读取,如果需要在build时使用该环境变量,请在build后加args子参数。
    次环境变量在构建镜像时,可以被我们自身的代码读取到,例如:

    func getEnvInfo() string {
    rackEnv := os.Getenv("RACK_ENV")
    fmt.Println(rackEnv)
    }
    
    output:
    development
    

    expose

    暴露端口,但是仅限于服务之间的通信,暴露的是内部端口,类似Dockerfile的EXPOSE指令

    expose:
      - "3000"
      - "8000"
    

    连接服务

    external_links:
      - redis_1
      - project_db_1:mysql
      - project_db_1:postgresql
    

    tips:
    官方推荐使用network

    extra_hosts

    添加自定义域名,同--add-host

    extra_hosts:
      - "somehost:162.242.195.82"
      - "otherhost:50.31.209.229"
    

    也可以在容器内的/etc/hosts文件内写入

    162.242.195.82  somehost
    50.31.209.229   otherhost
    

    healthcheck

    同Dockerfile中的HEALTHCHECK指令

    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost"]
      interval: 1m30s
      timeout: 10s
      retries: 3
      start_period: 40s
    

    使用disabel: true,相当于test: ["NONE"]

    healthcheck:
      disable: true
    

    image

    指定需要拉取或使用的镜像,也可以使用仓库/标签或部分镜像ID

    image: redis # 默认标签 latest
    image: ubuntu:18.04
    image: tutum/influxdb
    image: example-registry.com:4000/postgresql
    image: a4bc65fd
    

    init

    在容器内运行一个初始化程序,以转发信号开获取进程。

    version: "3.8"
    services:
      web:
        image: alpine:latest
        init: true
    

    tips:
    使用的默认初始化二进制文件是Tini,并安装在/usr/libexec/docker-init守护程序主机上。您可以通过init-path配置选项将守护程序配置为使用自定义init二进制文件 。

    isolation

    指定容器隔离技术,Linux只支持default,windows支持default``process hyperv三个值,具体参考 Docker Engine Docs

    labels

    同Dockerfile中的LABEL指令,为容器设定metadata

    build:
      context: .
      labels: # map
        com.example.description: "Accounting webapp"
        com.example.department: "Finance"
        com.example.label-with-empty-value: ""
    build:
      context: .
      labels: # list
        - "com.example.description=Accounting webapp"
        - "com.example.department=Finance"
        - "com.example.label-with-empty-value"
    

    旧版的功能,不推荐使用

    logging

    为当前服务设置日至参数

    logging:
      driver: syslog
      options:
        syslog-address: "tcp://192.168.0.42:123"
    

    driver参数同--log-driver指令

    driver: "json-file"
    driver: "syslog"
    driver: "none"
    

    tips:
    只有使用json-filejournald时,docker-compose updocker-compose logs才能看到日志,其他任何的驱动都无法看到日志打印。

    指定日志设置,同docker run --log-opt.格式为k-v结构

    driver: "syslog"
    options:
      syslog-address: "tcp://192.168.0.42:123"
    

    默认的日志驱动是json-file,可以设置存储限制

    options:
      max-size: "200k" # 单文件最大存储
      max-file: "10" # 文件最大数量
    

    tips:
    上述的option参数仅为json-file日志驱动支持的参数,不同驱动支持的参数各不相同,具体参照下表。

    支持的驱动列表

    Driver Description
    none 不输出日志。
    local 日志以自定义格式存储,旨在最大程度地减少开销。
    json-file 日志以自定义格式存储,旨在最大程度地减少开销。
    syslog 将日志消息写入syslog设施。该syslog守护程序必须在主机上运行。
    journald 将日志消息写入journald。该journald守护程序必须在主机上运行。
    gelf 将日志消息写入Graylog扩展日志格式(GELF)端点,例如Graylog或Logstash。
    fluentd 将日志消息写入fluentd(向前输入)。该fluentd守护程序必须在主机上运行。
    awslogs 将日志消息写入Amazon CloudWatch Logs。
    splunk 将日志消息写入到splunk使用HTTP Event Collector。
    etwlogs 将日志消息写为Windows事件跟踪(ETW)事件。仅在Windows平台上可用。
    gcplogs 将日志消息写入Google Cloud Platform(GCP)日志记录。
    logentries 将日志消息写入Rapid7 Logentries。

    tips:
    具体请参考 Configure logging drivers

    ports

    对外暴露端口

    short syntax:
    要么指定两个端口HOST:CONTAINER,要么仅指定容器端口(选择了临时主机端口)。

    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"
      - "6060:6060/udp"
      - "12400-12500:1240"
    

    tips:
    当以HOST:CONTAINER格式映射端口时,使用低于60的容器端口可能会报错,因为YAML会将格式xx:yy中的数字解析为以60进制的数(可以理解为时间)。因此建议始终将端口映射显式指定为字符串。

    long syntax

    长语法允许出现短语法不允许出现的字段

    • target:容器内的端口
    • published:公开暴露端口
    • protocol:端口协议(tcp或udp)
    • mode:host用于在每个节点上发布主机端口,ingress使群集模式端口达到负载平衡。
    ports:
      - target: 80
        published: 8080
        protocol: tcp
        mode: host
    

    restart

    容器重启策略

    restart: "no" # 失败不重启
    restart: always # 失败后总是重启
    restart: on-failure # 错误码为 on-failure 时才重启
    restart: unless-stopped # 手动停止后不重启
    

    secrets(待补充)

    volumes

    用来挂载数据卷

    short syntax
    短语法使用最简单的格式[SOURCE:]TARGET[:MODE]

    • SOURCE可以是宿主机地址,也可以是数据卷名。
    • TARGET是容器内路径。
    • MODE包括rofor read-onlyrw for read-write(默认)

    如果使用宿主机的相对路径,则以docker-compose.yaml为基础进行拓展。

    volumes:
      # 指定容器内路径,docker 自动创建路径
      - /var/lib/mysql
    
      # 挂载绝对路径
      - /opt/data:/var/lib/mysql
    
      # 挂载相对路径
      - ./cache:/tmp/cache
    
      # 用户目录相对路径
      - ~/configs:/etc/configs/:ro
    
      # 命名挂载
      - datavolume:/var/lib/mysql
    

    long syntax

    长语法允许使用短语法无法表达的字段

    • type: 安装类型, bind, tmpfs 或者 npipe
    • source: 挂载源,可以是宿主机路径,也可以是顶级挂载设置中设置好的卷名。tmpfs不适用于挂载
    • target: 容器内挂载路径
    • read_only: 设置挂载路径只读
    • bind: 配置额外的绑定设置
      • propagation: 用于设置绑定的传播模式
    • volume: 配置额外的挂载配置
      • nocopy: 创建卷时禁用从容器复制数据标识位
    • tmpfs: 配置额外的tmpfs配置
      • size: 设置挂载tmpfs的大小(字节)
    • consistency: 装载的一致性要求,consistent (主机和容器具有相同的视图),cached(读缓存,主机视图具有权威性)或delegated(读写缓存,容器的视图具有权威性)之一
    version: "3.8"
    services:
      web:
        image: nginx:alpine
        ports:
          - "80:80"
        volumes:
          - type: volume
            source: mydata
            target: /data
            volume:
              nocopy: true
          - type: bind
            source: ./static
            target: /opt/app/static
    
    networks:
      webnet:
    
    volumes:
      mydata:
    

    案例:使用docker-compose部署WordPress项目

    官方文档:https://docs.docker.com/compose/wordpress/

    创建一个项目目录

    如:命名目录my_wordpress

    #创建目录
    mkdir my_wordpress
    
    #进入目录
    cd my_wordpress/
    

    创建yaml文件

    创建一个docker-compose.yml文件来启动您的 WordPress博客,文件内容如下:

    #指定yaml版本
    version: '3.3'
    
    #配置服务
    services:
       #创建一个db服务
       db:
         #使用mysql:5.7的镜像创建
         image: mysql:5.7
         #容器卷
         #可以将主机路径安装为单个服务的定义的一部分,而无需在顶级volumes密钥中进行定义
         #但是,如果要在多个服务之间重用卷,请在顶级volumes定义
         volumes:
           - db_data:/var/lib/mysql
         #指定容器重启策略,当always指定时,容器总是重新启动
         restart: always
         #添加环境变量
         environment:
           MYSQL_ROOT_PASSWORD: somewordpress
           MYSQL_DATABASE: wordpress
           MYSQL_USER: wordpress
           MYSQL_PASSWORD: wordpress
    
       #创建一个wordpress服务
       wordpress:
         #指定依赖db服务,会先启动db
         depends_on:
           - db
         #使用wordpress:latest镜像构建
         image: wordpress:latest
         #指定暴露端口 宿主机端口:容器端口
         ports:
           - "8000:80"
         #指定容器重启策略,当always指定时,容器总是重新启动
         restart: always
         #添加环境变量
         environment:
           WORDPRESS_DB_HOST: db:3306
           WORDPRESS_DB_USER: wordpress
           WORDPRESS_DB_PASSWORD: wordpress
           WORDPRESS_DB_NAME: wordpress
    #容器卷配置
    volumes:
        #在第一次调用时docker-compose up,将创建该卷。在随后的服务调用中将重用相同的卷
        db_data: {}
    

    注意事项

    启动项目

    前台启动

    docker-compose up
    

    image-20210112111042684

    后台启动

    docker-compose up -d
    

    image-20210112111224374

    访问测试

    ip:8000

    image-20210112111151772

    关机和清理

    该命令docker-compose down将删除容器和默认网络,但会保留WordPress数据库。

    docker-compose down
    

    该命令docker-compose down --volumes将删除容器,默认网络和WordPress数据库。

    docker-compose down --volumes
    
  • 相关阅读:
    elk 分布式数据同步
    mget 同时获取
    Jzoj1460 无题noname
    Jzoj1460 无题noname
    Jzoj1322硬币
    Jzoj1322硬币
    Jzoj1321 灯
    Jzoj1321 灯
    Jzoj1310 生日礼物
    Jzoj1310 生日礼物
  • 原文地址:https://www.cnblogs.com/makalochen/p/14266075.html
Copyright © 2011-2022 走看看