docker編排參數(shù)詳解(docker-compose.yml配置文件編寫)

作者:xcbeyond
瘋狂源自夢(mèng)想,技術(shù)成就輝煌!微信公眾號(hào):《程序猿技術(shù)大咖》號(hào)主,專注后端開發(fā)多年,擁有豐富的研發(fā)經(jīng)驗(yàn),樂于技術(shù)輸出、分享,現(xiàn)階段從事微服務(wù)架構(gòu)項(xiàng)目的研發(fā)工作,涉及架構(gòu)設(shè)計(jì)、技術(shù)選型、業(yè)務(wù)研發(fā)等工作。對(duì)于Java、微服務(wù)、數(shù)據(jù)庫、Docker有深入了解,并有大量的調(diào)優(yōu)經(jīng)驗(yàn)。

docker compose 在 Docker 容器運(yùn)用中具有很大的學(xué)習(xí)意義,docker compose 是一個(gè)整合發(fā)布應(yīng)用的利器。而使用 docker compose 時(shí),懂得如何編排 docker compose 配置文件是很重要的。

一. 前言
關(guān)于 docker compose 技術(shù)可以查看官方文檔 Docker Compose

以下的內(nèi)容是確立在已經(jīng)下載好 Docker 以及 Docker Compose,可參看 Docker Compose 的官方安裝教程 Install Docker Compose

二. Docker Compose 配置文件的構(gòu)建參數(shù)說明
首先,官方提供了一個(gè) docker-compose.yml 配置文件的標(biāo)準(zhǔn)例子

version: "3"
services:
 
  redis:
    image: redis:alpine
    ports:
      - "6379"
    networks:
      - frontend
    deploy:
      replicas: 2
      update_config:
        parallelism: 2
        delay: 10s
      restart_policy:
        condition: on-failure
 
  db:
    image: postgres:9.4
    volumes:
      - db-data:/var/lib/postgresql/data
    networks:
      - backend
    deploy:
      placement:
        constraints: [node.role == manager]
 
  vote:
    image: dockersamples/examplevotingapp_vote:before
    ports:
      - 5000:80
    networks:
      - frontend
    depends_on:
      - redis
    deploy:
      replicas: 2
      update_config:
        parallelism: 2
      restart_policy:
        condition: on-failure
 
  result:
    image: dockersamples/examplevotingapp_result:before
    ports:
      - 5001:80
    networks:
      - backend
    depends_on:
      - db
    deploy:
      replicas: 1
      update_config:
        parallelism: 2
        delay: 10s
      restart_policy:
        condition: on-failure
 
  worker:
    image: dockersamples/examplevotingapp_worker
    networks:
      - frontend
      - backend
    deploy:
      mode: replicated
      replicas: 1
      labels: [APP=VOTING]
      restart_policy:
        condition: on-failure
        delay: 10s
        max_attempts: 3
        window: 120s
      placement:
        constraints: [node.role == manager]
 
  visualizer:
    image: dockersamples/visualizer:stable
    ports:
      - "8080:8080"
    stop_grace_period: 1m30s
    volumes:
      - "/var/run/docker.sock:/var/run/docker.sock"
    deploy:
      placement:
        constraints: [node.role == manager]
 
networks:
  frontend:
  backend:
 
volumes:
  db-data:
此文件配置了多個(gè)服務(wù),關(guān)于此配置文件的各個(gè)語句含義就需要弄懂配置選項(xiàng)的含義了

文件配置
compose 文件是一個(gè)定義服務(wù)、 網(wǎng)絡(luò)和卷的 YAML 文件 。Compose 文件的默認(rèn)路徑是 ./docker-compose.yml

提示:可以是用 .yml 或 .yaml 作為文件擴(kuò)展名 

服務(wù)定義包含應(yīng)用于為該服務(wù)啟動(dòng)的每個(gè)容器的配置,就像傳遞命令行參數(shù)一樣 docker container create。同樣,網(wǎng)絡(luò)和卷的定義類似于 docker network create 和 docker volume create。

正如 docker container create 在 Dockerfile 指定選項(xiàng),如 CMD、 EXPOSE、VOLUME、ENV,在默認(rèn)情況下,你不需要再次指定它們docker-compose.yml。

可以使用 Bash 類 ${VARIABLE} 語法在配置值中使用環(huán)境變量。

配置選項(xiàng)
1.bulid
服務(wù)除了可以基于指定的鏡像,還可以基于一份 Dockerfile,在使用 up 啟動(dòng)之時(shí)執(zhí)行構(gòu)建任務(wù),這個(gè)構(gòu)建標(biāo)簽就是 build,它可以指定 Dockerfile 所在文件夾的路徑。Compose 將會(huì)利用它自動(dòng)構(gòu)建這個(gè)鏡像,然后使用這個(gè)鏡像啟動(dòng)服務(wù)容器

build: /path/to/build/dir1
也可以是相對(duì)路徑

build: ./dir1
設(shè)定上下文根目錄,然后以該目錄為準(zhǔn)指定 Dockerfile

build:
  context: ../
  dockerfile: path/of/Dockerfile123
例子

version: '3'
services:
  webapp:
    build: ./dir
如果 context 中有指定的路徑,并且可以選定 Dockerfile 和 args。那么 args 這個(gè)標(biāo)簽,就像 Dockerfile 中的 ARG 指令,它可以在構(gòu)建過程中指定環(huán)境變量,但是在構(gòu)建成功后取消,在 docker-compose.yml 文件中也支持這樣的寫法:

version: '3'
services:
  webapp:
    build:
      context: ./dir
      dockerfile: Dockerfile-alternate
      args:
        buildno: 1
與 ENV 不同的是,args值可以為空值

args:
  - buildno
  - password
如果要指定 image 以及 build ,選項(xiàng)格式為

build: ./dir
image: webapp:tag
這會(huì)在 ./dir 目錄生成一個(gè)名為 webaapp 和標(biāo)記為 tag 的鏡像

Note:當(dāng)用(Version 3) Compose 文件在群集模式下部署堆棧時(shí),該選項(xiàng)被忽略。因?yàn)?docker stack 命令只接受預(yù)先構(gòu)建的鏡像

2. context
context 選項(xiàng)可以是 Dockerfile 的文件路徑,也可以是到鏈接到 git 倉庫的 url.

當(dāng)提供的值是相對(duì)路徑時(shí),它被解析為相對(duì)于撰寫文件的路徑,此目錄也是發(fā)送到 Docker 守護(hù)進(jìn)程的 context

build:
  context: ./dir
3. dockerfile
使用此 dockerfile 文件來構(gòu)建,必須指定構(gòu)建路徑

build:
  context: .
  dockerfile: Dockerfile-alternate
4. args
添加構(gòu)建參數(shù),這些參數(shù)是僅在構(gòu)建過程中可訪問的環(huán)境變量

首先, 在Dockerfile中指定參數(shù):

ARG buildno
ARG password
 
RUN echo "Build number: $buildno"
RUN script-requiring-password.sh "$password"
然后指定 build 下的參數(shù),可以傳遞映射或列表

build:
  context: .
  args:
    buildno: 1
    password: secret


build:
  context: .
  args:
    - buildno=1
    - password=secret
指定構(gòu)建參數(shù)時(shí)可以省略該值,在這種情況下,構(gòu)建時(shí)的值默認(rèn)構(gòu)成運(yùn)行環(huán)境中的值

args:
  - buildno
  - password
  Note: YAML 布爾值(true,false,yes,no,on,off)必須使用引號(hào)括起來,以為了能夠正常被解析為字符串


5. cache_from
編寫緩存解析鏡像列表

build:
  context: .
  cache_from:
    - alpine:latest
    - corp/web_app:3.14
6. labels
使用 Docker標(biāo)簽 將元數(shù)據(jù)添加到生成的鏡像中,可以使用數(shù)組或字典。

建議使用反向 DNS 標(biāo)記來防止簽名與其他軟件所使用的簽名沖突

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


build:
  context: .
  labels:
    - "com.example.description=Accounting webapp"
    - "com.example.department=Finance"
    - "com.example.label-with-empty-value"
7.shm_size
設(shè)置容器 /dev/shm 分區(qū)的大小,值為表示字節(jié)的整數(shù)值或表示字符的字符串

build:
  context: .
  shm_size: '2gb'


build:
  context: .
  shm_size: 10000000
8. target
根據(jù)對(duì)應(yīng)的 Dockerfile 構(gòu)建指定 Stage

build:
    context: .
    target: prod
9. cap_add、cap_drop
添加或刪除容器功能,可查看 man 7 capabilities

cap_add:
  - ALL
 
cap_drop:
  - NET_ADMIN
  - SYS_ADMIN
Note:當(dāng)用(Version 3) Compose 文件在群集模式下部署堆棧時(shí),該選項(xiàng)被忽略。因?yàn)?docker stack 命令只接受預(yù)先構(gòu)建的鏡像

10. command
覆蓋容器啟動(dòng)后默認(rèn)執(zhí)行的命令

command: bundle exec thin -p 30001
該命令也可以是一個(gè)列表,方法類似于 dockerfile:

command: ["bundle", "exec", "thin", "-p", "3000"]
11. configs
使用服務(wù) configs 配置為每個(gè)服務(wù)賦予相應(yīng)的訪問權(quán)限,支持兩種不同的語法。

Note: 配置必須存在或在 configs 此堆棧文件的頂層中定義,否則堆棧部署失效 

SHORT 語法
SHORT 語法只能指定配置名稱,這允許容器訪問配置并將其安裝在 /<config_name> 容器內(nèi),源名稱和目標(biāo)裝入點(diǎn)都設(shè)為配置名稱。

version: "3.3"
services:
  redis:
    image: redis:latest
    deploy:
      replicas: 1
    configs:
      - my_config
      - my_other_config
configs:
  my_config:
    file: ./my_config.txt
  my_other_config:
    external: true
以上實(shí)例使用 SHORT 語法將 redis 服務(wù)訪問授予 my_config 和 my_other_config ,并被 my_other_config 定義為外部資源,這意味著它已經(jīng)在 Docker 中定義??梢酝ㄟ^ docker config create 命令或通過另一個(gè)堆棧部署。如果外部部署配置都不存在,則堆棧部署會(huì)失敗并出現(xiàn) config not found 錯(cuò)誤。

Note: config 定義僅在 3.3 版本或在更高版本的撰寫文件格式中受支持,YAML 的布爾值(true, false, yes, no, on, off)必須要使用引號(hào)引起來(單引號(hào)、雙引號(hào)均可),否則會(huì)當(dāng)成字符串解析。 

LONG 語法
LONG 語法提供了創(chuàng)建服務(wù)配置的更加詳細(xì)的信息

 

source:Docker 中存在的配置的名稱
target:要在服務(wù)的任務(wù)中裝載的文件的路徑或名稱。如果未指定則默認(rèn)為 /<source>
uid 和 gid:在服務(wù)的任務(wù)容器中擁有安裝的配置文件的數(shù)字 UID 或 GID。如果未指定,則默認(rèn)為在Linux上。Windows不支持。
mode:在服務(wù)的任務(wù)容器中安裝的文件的權(quán)限,以八進(jìn)制表示法。例如,0444 代表文件可讀的。默認(rèn)是 0444。如果配置文件無法寫入,是因?yàn)樗鼈儼惭b在臨時(shí)文件系統(tǒng)中,所以如果設(shè)置了可寫位,它將被忽略。可執(zhí)行位可以設(shè)置。如果您不熟悉 UNIX 文件權(quán)限模式,Unix Permissions Calculator

下面示例在容器中將 my_config 名稱設(shè)置為 redis_config,將模式設(shè)置為 0440(group-readable)并將用戶和組設(shè)置為 103。該?。鄏edis 服務(wù)無法訪問 my_other_config 配置。

version: "3.3"
services:
  redis:
    image: redis:latest
    deploy:
      replicas: 1
    configs:
      - source: my_config
        target: /redis_config
        uid: '103'
        gid: '103'
        mode: 0440
configs:
  my_config:
    file: ./my_config.txt
  my_other_config:
    external: true
可以同時(shí)授予多個(gè)配置的服務(wù)相應(yīng)的訪問權(quán)限,也可以混合使用 LONG 和 SHORT 語法。定義配置并不意味著授予服務(wù)訪問權(quán)限。

12. cgroup_parent
可以為容器選擇一個(gè)可選的父 cgroup_parent

cgroup_parent: m-executor-abcd
  注意:當(dāng) 使用(Version 3)Compose 文件在群集模式下部署堆棧時(shí),忽略此選項(xiàng)


13. container_name
為自定義的容器指定一個(gè)名稱,而不是使用默認(rèn)的名稱

container_name: my-web-container
因?yàn)?docker 容器名稱必須是唯一的,所以如果指定了一個(gè)自定義的名稱,不能擴(kuò)展一個(gè)服務(wù)超過 1 個(gè)容器

14. credential_spec
為托管服務(wù)賬戶配置憑據(jù)規(guī)范,此選項(xiàng)僅適用于 Windows 容器服務(wù)

在 credential_spec 上的配置列表格式為 file://<filename> 或 registry://<value-name>

使用 file: 應(yīng)該注意引用的文件必須存在于CredentialSpecs,docker 數(shù)據(jù)目錄的子目錄中。在 Windows 上,該目錄默認(rèn)為 C:\ProgramData\Docker\。以下示例從名為C:\ProgramData\Docker\CredentialSpecs\my-credential-spec.json 的文件加載憑證規(guī)范 :

credential_spec:
  file: my-credential-spec.json

使用 registry: 將從守護(hù)進(jìn)程主機(jī)上的 Windows 注冊(cè)表中讀取憑據(jù)規(guī)范。其注冊(cè)表值必須位于:

HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Virtualization\Containers\CredentialSpecs
下面的示例通過 my-credential-spec 注冊(cè)表中指定的值加載憑證規(guī)范:

credential_spec:
  registry: my-credential-spec
15. deploy
指定與部署和運(yùn)行服務(wù)相關(guān)的配置

version: '3'
services:
  redis:
    image: redis:alpine
    deploy:
      replicas: 6
      update_config:
        parallelism: 2
        delay: 10s
      restart_policy:
        condition: on-failure
這里有幾個(gè)子選項(xiàng)

endpoint_mode
指定連接到群組外部客戶端服務(wù)發(fā)現(xiàn)方法

endpoint_mode:vip :Docker 為該服務(wù)分配了一個(gè)虛擬 IP(VIP),作為客戶端的  “前端“ 部位用于訪問網(wǎng)絡(luò)上的服務(wù)。
endpoint_mode: dnsrr : DNS輪詢(DNSRR)服務(wù)發(fā)現(xiàn)不使用單個(gè)虛擬 IP。Docker為服務(wù)設(shè)置 DNS 條目,使得服務(wù)名稱的 DNS 查詢返回一個(gè) IP 地址列表,并且客戶端直接連接到其中的一個(gè)。如果想使用自己的負(fù)載平衡器,或者混合 Windows 和 Linux 應(yīng)用程序,則 DNS 輪詢調(diào)度(round-robin)功能就非常實(shí)用。





version: "3.3"
 
services:
  wordpress:
    image: wordpress
    ports:
      - 8080:80
    networks:
      - overlay
    deploy:
      mode: replicated
      replicas: 2
      endpoint_mode: vip
 
  mysql:
    image: mysql
    volumes:
       - db-data:/var/lib/mysql/data
    networks:
       - overlay
    deploy:
      mode: replicated
      replicas: 2
      endpoint_mode: dnsrr
 
volumes:
  db-data:
 
networks:
  overlay:

相關(guān)信息:Swarm 模式 CLI 命令 、Configure 服務(wù)發(fā)現(xiàn)

labels
指定服務(wù)的標(biāo)簽,這些標(biāo)簽僅在服務(wù)上設(shè)置。

version: "3"
services:
  web:
    image: web
    deploy:
      labels:
        com.example.description: "This label will appear on the web service"
通過將 deploy 外面的 labels 標(biāo)簽來設(shè)置容器上的 labels

version: "3"
services:
  web:
    image: web
    labels:
      com.example.description: "This label will appear on all containers for the web service"
mode
global:每個(gè)集節(jié)點(diǎn)只有一個(gè)容器

replicated:指定容器數(shù)量(默認(rèn))

version: '3'
services:
  worker:
    image: dockersamples/examplevotingapp_worker
    deploy:
      mode: global
placement
指定 constraints 和 preferences

version: '3'
services:
  db:
    image: postgres
    deploy:
      placement:
        constraints:
          - node.role == manager
          - engine.labels.operatingsystem == ubuntu 14.04
        preferences:
          - spread: node.labels.zone
replicas
如果服務(wù)是 replicated(默認(rèn)),需要指定運(yùn)行的容器數(shù)量

version: '3'
services:
  worker:
    image: dockersamples/examplevotingapp_worker
    networks:
      - frontend
      - backend
    deploy:
      mode: replicated
      replicas: 6
 resources
配置資源限制

version: '3'
services:
  redis:
    image: redis:alpine
    deploy:
      resources:
        limits:
          cpus: '0.50'
          memory: 50M
        reservations:
          cpus: '0.25'
          memory: 20M
此例子中,redis 服務(wù)限制使用不超過 50M 的內(nèi)存和 0.50(50%)可用處理時(shí)間(CPU),并且 保留 20M 了內(nèi)存和 0.25 CPU時(shí)間

restart_policy
配置容器的重新啟動(dòng),代替 restart

condition:值可以為 none 、on-failure 以及 any(默認(rèn))

delay:嘗試重啟的等待時(shí)間,默認(rèn)為 0

max_attempts:在放棄之前嘗試重新啟動(dòng)容器次數(shù)(默認(rèn):從不放棄)。如果重新啟動(dòng)在配置中沒有成功 window,則此嘗試不計(jì)入配置max_attempts 值。例如,如果 max_attempts 值為 2,并且第一次嘗試重新啟動(dòng)失敗,則可能會(huì)嘗試重新啟動(dòng)兩次以上。
windows:在決定重新啟動(dòng)是否成功之前的等時(shí)間,指定為持續(xù)時(shí)間(默認(rèn)值:立即決定)。

 

version: "3"
services:
  redis:
    image: redis:alpine
    deploy:
      restart_policy:
        condition: on-failure
        delay: 5s
        max_attempts: 3
        window: 120s
update_config
配置更新服務(wù),用于無縫更新應(yīng)用(rolling update)

parallelism:一次性更新的容器數(shù)量

delay:更新一組容器之間的等待時(shí)間。

failure_action:如果更新失敗,可以執(zhí)行的的是 continue、rollback 或 pause (默認(rèn))

monitor:每次任務(wù)更新后監(jiān)視失敗的時(shí)間(ns|us|ms|s|m|h)(默認(rèn)為0)

max_failure_ratio:在更新期間能接受的失敗率

order:更新次序設(shè)置,top-first(舊的任務(wù)在開始新任務(wù)之前停止)、start-first(新的任務(wù)首先啟動(dòng),并且正在運(yùn)行的任務(wù)短暫重疊)(默認(rèn) stop-first)

version: '3.4'
services:
  vote:
    image: dockersamples/examplevotingapp_vote:before
    depends_on:
      - redis
    deploy:
      replicas: 2
      update_config:
        parallelism: 2
        delay: 10s
        order: stop-first
不支持 Docker stack desploy 的幾個(gè)子選項(xiàng)
build、cgroup_parent、container_name、devices、tmpfs、external_links、inks、network_mode、restart、security_opt、stop_signal、sysctls、userns_mode

16. devices
設(shè)置映射列表,與 Docker 客戶端的 --device 參數(shù)類似 :

devices:
  - "/dev/ttyUSB0:/dev/ttyUSB0"
17. depends_on
此選項(xiàng)解決了啟動(dòng)順序的問題

在使用 Compose 時(shí),最大的好處就是少打啟動(dòng)命令,但是一般項(xiàng)目容器啟動(dòng)的順序是有要求的,如果直接從上到下啟動(dòng)容器,必然會(huì)因?yàn)槿萜饕蕾噯栴}而啟動(dòng)失敗。例如在沒啟動(dòng)數(shù)據(jù)庫容器的時(shí)候啟動(dòng)了應(yīng)用容器,這時(shí)候應(yīng)用容器會(huì)因?yàn)檎也坏綌?shù)據(jù)庫而退出,為了避免這種情況我們需要加入一個(gè)標(biāo)簽,就是 depends_on,這個(gè)標(biāo)簽解決了容器的依賴、啟動(dòng)先后的問題。

指定服務(wù)之間的依賴關(guān)系,有兩種效果

docker-compose up 以依賴順序啟動(dòng)服務(wù),下面例子中 redis 和 db 服務(wù)在 web 啟動(dòng)前啟動(dòng)
docker-compose up SERVICE 自動(dòng)包含 SERVICE 的依賴性,下面例子中,例如下面容器會(huì)先啟動(dòng) redis 和 db  
兩個(gè)服務(wù),最后才啟動(dòng) web 服務(wù):

version: '3'
services:
  web:
    build: .
    depends_on:
      - db
      - redis
  redis:
    image: redis
  db:
    image: postgres

注意的是,默認(rèn)情況下使用 docker-compose up web 這樣的方式啟動(dòng) web 服務(wù)時(shí),也會(huì)啟動(dòng) redis 和 db 兩個(gè)服務(wù),因?yàn)樵谂渲梦募卸x了依賴關(guān)系

18. dns
自定義 DNS 服務(wù)器,與 --dns 具有一樣的用途,可以是單個(gè)值或列表

dns: 8.8.8.8
dns:
  - 8.8.8.8
  - 9.9.9.9
19. dns_search
自定義 DNS 搜索域,可以是單個(gè)值或列表

dns_search: example.com
dns_search:
  - dc1.example.com
  - dc2.example.com
20. tmpfs
掛載臨時(shí)文件目錄到容器內(nèi)部,與 run 的參數(shù)一樣效果,可以是單個(gè)值或列表

tmpfs: /run
tmpfs:
  - /run
  - /tmp
21. entrypoint
在 Dockerfile 中有一個(gè)指令叫做 ENTRYPOINT 指令,用于指定接入點(diǎn)。在 docker-compose.yml 中可以定義接入點(diǎn),覆蓋 Dockerfile 中的定義:

entrypoint: /code/entrypoint.sh
entrypoint 也可以是一個(gè)列表,方法類似于 dockerfile

entrypoint:
    - php
    - -d
    - zend_extension=/usr/local/lib/php/extensions/no-debug-non-zts-20100525/xdebug.so
    - -d
    - memory_limit=-1
    - vendor/bin/phpunit
21. env_file
從文件中添加環(huán)境變量??梢允菃蝹€(gè)值或是列表
如果已經(jīng)用 docker-compose -f FILE 指定了 Compose 文件,那么 env_file 路徑值為相對(duì)于該文件所在的目錄

但 environment 環(huán)境中的設(shè)置的變量會(huì)會(huì)覆蓋這些值,無論這些值未定義還是為 None

env_file: .env
或者根據(jù) docker-compose.yml 設(shè)置多個(gè):

env_file:
  - ./common.env
  - ./apps/web.env
  - /opt/secrets.env
環(huán)境配置文件 env_file 中的聲明每行都是以 VAR=VAL 格式,其中以 # 開頭的被解析為注釋而被忽略

注意環(huán)境變量配置列表的順序*,例如下面例子

docker_compose.yml

services:
  some-service:
    env_file:
      - a.env
      - b.env
a.env 文件

# a.env
VAR=1
b.env文件

# b.env
VAR=2
對(duì)于在文件a.env 中指定的相同變量但在文件 b.env 中分配了不同的值,如果 b.env 像下面列在 a.env 之后,則剛在 a.env 設(shè)置的值被 b.env 相同變量的值覆蓋,此時(shí) $VAR 值為 hello。此外,這里所說的環(huán)境變量是對(duì)宿主機(jī)的 Compose 而言的,如果在配置文件中有 build 操作,這些變量并不會(huì)進(jìn)入構(gòu)建過程中,如果要在構(gòu)建中使用變量還是首選 arg 標(biāo)簽

22. environment
添加環(huán)境變量,可以使用數(shù)組或字典。與上面的 env_file 選項(xiàng)完全不同,反而和 arg 有幾分類似,這個(gè)標(biāo)簽的作用是設(shè)置鏡像變量,它可以保存變量到鏡像里面,也就是說啟動(dòng)的容器也會(huì)包含這些變量設(shè)置,這是與 arg 最大的不同。
一般 arg 標(biāo)簽的變量?jī)H用在構(gòu)建過程中。而 environment 和 Dockerfile 中的 ENV 指令一樣會(huì)把變量一直保存在鏡像、容器中,類似 docker run -e 的效果

environment:
  RACK_ENV: development
  SHOW: 'true'
  SESSION_SECRET:


environment:
  - RACK_ENV=development
  - SHOW=true
  - SESSION_SECRET
23. expose
暴露端口,但不映射到宿主機(jī),只被連接的服務(wù)訪問。這個(gè)標(biāo)簽與 Dockerfile 中的 EXPOSE 指令一樣,用于指定暴露的端口,但是只是作為一種參考,實(shí)際上 docker-compose.yml 的端口映射還得 ports 這樣的標(biāo)簽

expose:
 - "3000"
 - "8000"
24. external_links
鏈接到 docker-compose.yml 外部的容器,甚至 并非 Compose 項(xiàng)目文件管理的容器。參數(shù)格式跟 links 類似

在使用Docker過程中,會(huì)有許多單獨(dú)使用 docker run 啟動(dòng)的容器的情況,為了使 Compose 能夠連接這些不在docker-compose.yml 配置文件中定義的容器,那么就需要一個(gè)特殊的標(biāo)簽,就是 external_links,它可以讓Compose 項(xiàng)目里面的容器連接到那些項(xiàng)目配置外部的容器(前提是外部容器中必須至少有一個(gè)容器是連接到與項(xiàng)目?jī)?nèi)的服務(wù)的同一個(gè)網(wǎng)絡(luò)里面)。

格式如下

external_links:
 - redis_1
 - project_db_1:mysql
 - project_db_1:postgresql
25. extra_hosts
添加主機(jī)名的標(biāo)簽,就是往 /etc/hosts 文件中添加一些記錄,與 Docker 客戶端 中的 --add-host 類似:

extra_hosts:
 - "somehost:162.242.195.82"
 - "otherhost:50.31.209.229"
具有 IP 地址和主機(jī)名的條目在 /etc/hosts 內(nèi)部容器中創(chuàng)建。啟動(dòng)之后查看容器內(nèi)部 hosts ,例如:

162.242.195.82  somehost
50.31.209.229   otherhost
26.healthcheck
用于檢查測(cè)試服務(wù)使用的容器是否正常

healthcheck:
  test: ["CMD", "curl", "-f", "http://localhost"]
  interval: 1m30s
  timeout: 10s
  retries: 3
  start_period: 40s
interval,timeout 以及 start_period 都定為持續(xù)時(shí)間

test 必須是字符串或列表,如果它是一個(gè)列表,第一項(xiàng)必須是 NONE,CMD 或 CMD-SHELL ;如果它是一個(gè)字符串,則相當(dāng)于指定CMD-SHELL 后跟該字符串。

# Hit the local web app
test: ["CMD", "curl", "-f", "http://localhost"]
 
# As above, but wrapped in /bin/sh. Both forms below are equivalent.
test: ["CMD-SHELL", "curl -f http://localhost || exit 1"]
test: curl -f https://localhost || exit
如果需要禁用鏡像的所有檢查項(xiàng)目,可以使用 disable:true,相當(dāng)于 test:["NONE"]

healthcheck:
  disable: true
27. image
從指定的鏡像中啟動(dòng)容器,可以是存儲(chǔ)倉庫、標(biāo)簽以及鏡像 ID

image: redis
image: ubuntu:14.04
image: tutum/influxdb
image: example-registry.com:4000/postgresql
image: a4bc65fd
如果鏡像不存在,Compose 會(huì)自動(dòng)拉去鏡像

28. isolation
Linux 上僅僅支持 default 值

29. labels
使用 Docker 標(biāo)簽將元數(shù)據(jù)添加到容器,可以使用數(shù)組或字典。與 Dockerfile 中的 LABELS 類似:

labels:
  com.example.description: "Accounting webapp"
  com.example.department: "Finance"
  com.example.label-with-empty-value: ""
 
labels:
  - "com.example.description=Accounting webapp"
  - "com.example.department=Finance"
  - "com.example.label-with-empty-value"
30.links
鏈接到其它服務(wù)的中的容器,可以指定服務(wù)名稱也可以指定鏈接別名(SERVICE:ALIAS),與 Docker 客戶端的 --link 有一樣效果,會(huì)連接到其它服務(wù)中的容器






web:
  links:
   - db
   - db:database
   - redis
使用的別名將會(huì)自動(dòng)在服務(wù)容器中的 /etc/hosts 里創(chuàng)建。例如:

172.12.2.186  db
172.12.2.186  database
172.12.2.187  redis
相應(yīng)的環(huán)境變量也將被創(chuàng)建

31. logging
配置日志服務(wù)

logging:
  driver: syslog
  options:
    syslog-address: "tcp://192.168.0.42:123"
該 driver值是指定服務(wù)器的日志記錄驅(qū)動(dòng)程序,默認(rèn)值為 json-file,與 --log-diver 選項(xiàng)一樣

driver: "json-file"
driver: "syslog"
driver: "none"
  注意:只有驅(qū)動(dòng)程序 json-file 和 journald 驅(qū)動(dòng)程序可以直接從 docker-compose up 和 docker-compose logs 獲取日志。使用任何其他方式不會(huì)顯示任何日志。


對(duì)于可選值,可以使用 options 指定日志記錄中的日志記錄選項(xiàng)

driver: "syslog"
options:
  syslog-address: "tcp://192.168.0.42:123"
默認(rèn)驅(qū)動(dòng)程序 json-file  具有限制存儲(chǔ)日志量的選項(xiàng),所以,使用鍵值對(duì)來獲得最大存儲(chǔ)大小以及最小存儲(chǔ)數(shù)量

options:
  max-size: "200k"
  max-file: "10"
上面實(shí)例將存儲(chǔ)日志文件,直到它們達(dá)到max-size:200kB,存儲(chǔ)的單個(gè)日志文件的數(shù)量由該 max-file 值指定。隨著日志增長(zhǎng)超出最大限制,舊日志文件將被刪除以存儲(chǔ)新日志

docker-compose.yml 限制日志存儲(chǔ)的示例

services:
  some-service:
    image: some-service
    logging:
      driver: "json-file"
      options:
        max-size: "200k"
        max-file: "10"
32. network_mode
網(wǎng)絡(luò)模式,用法類似于 Docke 客戶端的 --net 選項(xiàng),格式為:service:[service name]

network_mode: "bridge"
network_mode: "host"
network_mode: "none"
network_mode: "service:[service name]"
network_mode: "container:[container name/id]"
可以指定使用服務(wù)或者容器的網(wǎng)絡(luò)

33. networks
加入指定網(wǎng)絡(luò)

services:
  some-service:
    networks:
     - some-network
     - other-network
34. aliases
同一網(wǎng)絡(luò)上的其他容器可以使用服務(wù)器名稱或別名來連接到其他服務(wù)的容器

services:
  some-service:
    networks:
      some-network:
        aliases:
         - alias1
         - alias3
      other-network:
        aliases:
         - alias
下面實(shí)例中,提供 web 、worker以及db 服務(wù),伴隨著兩個(gè)網(wǎng)絡(luò) new 和 legacy 。

version: '2'
 
services:
  web:
    build: ./web
    networks:
      - new
 
  worker:
    build: ./worker
    networks:
      - legacy
 
  db:
    image: mysql
    networks:
      new:
        aliases:
          - database
      legacy:
        aliases:
          - mysql
 
networks:
  new:
  legacy:
相同的服務(wù)可以在不同的網(wǎng)絡(luò)有不同的別名

35. ipv4_address、ipv6_address
為服務(wù)的容器指定一個(gè)靜態(tài) IP 地址

version: '2.1'
 
services:
  app:
    image: busybox
    command: ifconfig
    networks:
      app_net:
        ipv4_address: 172.16.238.10
        ipv6_address: 2001:3984:3989::10
 
networks:
  app_net:
    driver: bridge
    enable_ipv6: true
    ipam:
      driver: default
      config:
      -
        subnet: 172.16.238.0/24
      -
        subnet: 2001:3984:3989::/64
36. PID
pid: "host"
將 PID 模式設(shè)置為主機(jī) PID 模式,可以打開容器與主機(jī)操作系統(tǒng)之間的共享 PID 地址空間。使用此標(biāo)志啟動(dòng)的容器可以訪問和操作宿主機(jī)的其他容器,反之亦然。

37. ports
映射端口

SHORT 語法
可以使用 HOST:CONTAINER 的方式指定端口,也可以指定容器端口(選擇臨時(shí)主機(jī)端口),宿主機(jī)會(huì)隨機(jī)映射端口

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"
  注意:當(dāng)使用 HOST:CONTAINER 格式來映射端口時(shí),如果使用的容器端口小于 60 可能會(huì)得到錯(cuò)誤得結(jié)果,因?yàn)閅AML 將會(huì)解析 xx:yy 這種數(shù)字格式為 60 進(jìn)制,所以建議采用字符串格式。

LONG 語法
LONG 語法支持 SHORT 語法不支持的附加字段

target:容器內(nèi)的端口

published:公開的端口

protocol:  端口協(xié)議(tcp 或 udp)

mode:通過host 用在每個(gè)節(jié)點(diǎn)還是哪個(gè)發(fā)布的主機(jī)端口或使用 ingress 用于集群模式端口進(jìn)行平衡負(fù)載,

ports:
  - target: 80
    published: 8080
    protocol: tcp
    mode: host
38. secrets
通過 secrets為每個(gè)服務(wù)授予相應(yīng)的訪問權(quán)限

SHORT 語法
version: "3.1"
services:
  redis:
    image: redis:latest
    deploy:
      replicas: 1
    secrets:
      - my_secret
      - my_other_secret
secrets:
  my_secret:
    file: ./my_secret.txt
  my_other_secret:
    external: true
LONG 語法
LONG 語法可以添加其他選項(xiàng)

source:secret 名稱

target:在服務(wù)任務(wù)容器中需要裝載在 /run/secrets/ 中的文件名稱,如果 source 未定義,那么默認(rèn)為此值

uid&gid:在服務(wù)的任務(wù)容器中擁有該文件的 UID 或 GID 。如果未指定,兩者都默認(rèn)為 0。

mode:以八進(jìn)制表示法將文件裝載到服務(wù)的任務(wù)容器中 /run/secrets/ 的權(quán)限。例如,0444 代表可讀。

version: "3.1"
services:
  redis:
    image: redis:latest
    deploy:
      replicas: 1
    secrets:
      - source: my_secret
        target: redis_secret
        uid: '103'
        gid: '103'
        mode: 0440
secrets:
  my_secret:
    file: ./my_secret.txt
  my_other_secret:
    external: true
39. security_opt
為每個(gè)容器覆蓋默認(rèn)的標(biāo)簽。簡(jiǎn)單說來就是管理全部服務(wù)的標(biāo)簽,比如設(shè)置全部服務(wù)的 user 標(biāo)簽值為 USER

security_opt:
  - label:user:USER
  - label:role:ROLE
40. stop_grace_period
在發(fā)送 SIGKILL 之前指定 stop_signal ,如果試圖停止容器(如果它沒有處理 SIGTERM(或指定的任何停止信號(hào))),則需要等待的時(shí)間

stop_grace_period: 1s
stop_grace_period: 1m30s
默認(rèn)情況下,stop 在發(fā)送SIGKILL之前等待10秒鐘容器退出

41. stop_signal
設(shè)置另一個(gè)信號(hào)來停止容器。在默認(rèn)情況下使用的 SIGTERM 來停止容器。設(shè)置另一個(gè)信號(hào)可以使用 stop_signal 標(biāo)簽:

stop_signal: SIGUSR
42. sysctls
在容器中設(shè)置的內(nèi)核參數(shù),可以為數(shù)組或字典

sysctls:
  net.core.somaxconn: 1024
  net.ipv4.tcp_syncookies: 0
 
sysctls:
  - net.core.somaxconn=1024
  - net.ipv4.tcp_syncookies=0
43. ulimits
覆蓋容器的默認(rèn)限制,可以單一地將限制值設(shè)為一個(gè)整數(shù),也可以將soft/hard 限制指定為映射

ulimits:
  nproc: 65535
  nofile:
    soft: 20000
    hard: 40000
44. userns_mode
userns_mode: "host"
45. volumes
掛載一個(gè)目錄或者一個(gè)已存在的數(shù)據(jù)卷容器,可以直接使用 HOST:CONTAINER 這樣的格式,或者使用 HOST:CONTAINER:ro 這樣的格式,后者對(duì)于容器來說,數(shù)據(jù)卷是只讀的,這樣可以有效保護(hù)宿主機(jī)的文件系統(tǒng)

version: "3.2"
services:
  web:
    image: nginx:alpine
    volumes:
      - type: volume
        source: mydata
        target: /data
        volume:
          nocopy: true
      - type: bind
        source: ./static
        target: /opt/app/static
 
  db:
    image: postgres:latest
    volumes:
      - "/var/run/postgres/postgres.sock:/var/run/postgres/postgres.sock"
      - "dbdata:/var/lib/postgresql/data"
 
volumes:
  mydata:
  dbdata:
Compose 的數(shù)據(jù)卷指定路徑可以是相對(duì)路徑,使用 . 或者 .. 來指定相對(duì)目錄。

數(shù)據(jù)卷的格式可以是下面多種形式:

volumes:
  # 只是指定一個(gè)路徑,Docker 會(huì)自動(dòng)在創(chuàng)建一個(gè)數(shù)據(jù)卷(這個(gè)路徑是容器內(nèi)部的)。
  - /var/lib/mysql
  # 使用絕對(duì)路徑掛載數(shù)據(jù)卷
  - /opt/data:/var/lib/mysql
 
  # 以 Compose 配置文件為中心的相對(duì)路徑作為數(shù)據(jù)卷掛載到容器。
  - ./cache:/tmp/cache
 
  # 使用用戶的相對(duì)路徑(~/ 表示的目錄是 /home/<用戶目錄>/ 或者 /root/)。
  - ~/configs:/etc/configs/:ro
 
  # 已經(jīng)存在的命名的數(shù)據(jù)卷。
  - datavolume:/var/lib/mysql
如果你不使用宿主機(jī)的路徑,可以指定一個(gè) volume_driver

volume_driver: mydriver
 SHORT 語法
可以選擇在主機(jī)(HOST:CONTAINER)或訪問模式(HOST:CONTAINER:ro)上指定路徑。

可以在主機(jī)上掛載相對(duì)路徑,該路徑相對(duì)于正在使用的 Compose 配置文件的目錄進(jìn)行擴(kuò)展。相對(duì)路徑應(yīng)始終以 . 或 .. 開頭

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
  - datavolume:/var/lib/mysql
LONG 語法
LONG 語法有些附加字段

type:安裝類型,可以為 volume、bind 或 tmpfs

source:安裝源,主機(jī)上用于綁定安裝的路徑或定義在頂級(jí) volumes密鑰中卷的名稱 ,不適用于 tmpfs 類型安裝。

target:卷安裝在容器中的路徑

read_only:標(biāo)志將卷設(shè)置為只讀

bind:配置額外的綁定選項(xiàng)

propagation:用于綁定的傳播模式

volume:配置額外的音量選項(xiàng)

nocopy:創(chuàng)建卷時(shí)禁止從容器復(fù)制數(shù)據(jù)的標(biāo)志

tmpfs:配置額外的 tmpfs 選項(xiàng)

size:tmpfs 的大小,以字節(jié)為單位

version: "3.2"
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:
46. volumes_from
從其它容器或者服務(wù)掛載數(shù)據(jù)卷,可選的參數(shù)是 :ro 或 :rw,前者表示容器只讀,后者表示容器對(duì)數(shù)據(jù)卷是可讀可寫的(默認(rèn)情況為可讀可寫的)。

volumes_from:
  - service_name
  - service_name:ro
  - container:container_name
  - container:container_name:rw
47. 用于服務(wù)、群集以及堆棧文件的卷
在使用服務(wù),群集和 docker-stack.yml 文件時(shí),請(qǐng)記住支持服務(wù)的任務(wù)(容器)可以部署在群集中的任何節(jié)點(diǎn)上,并且每次更新服務(wù)時(shí)都可能是不同的節(jié)點(diǎn)。

在缺少指定源的命名卷的情況下,Docker 為支持服務(wù)的每個(gè)任務(wù)創(chuàng)建一個(gè)匿名卷。關(guān)聯(lián)的容器被移除后,匿名卷不會(huì)保留。

如果希望數(shù)據(jù)持久存在,請(qǐng)使用可識(shí)別多主機(jī)的命名卷和卷驅(qū)動(dòng)程序,以便可以從任何節(jié)點(diǎn)訪問數(shù)據(jù)?;蛘?,對(duì)該服務(wù)設(shè)置約束,以便將其任務(wù)部署在具有該卷的節(jié)點(diǎn)上。

下面一個(gè)例子,Docker Labs 中 votingapp 示例的 docker-stack.yml文件中定義了一個(gè)稱為 db 的服務(wù)。它被配置為一個(gè)命名卷來保存群體上的數(shù)據(jù), 并且僅限于在節(jié)點(diǎn)上運(yùn)行。下面是來自該文件的部分內(nèi)容:db postgres manager

version: "3"
services:
  db:
    image: postgres:9.4
    volumes:
      - db-data:/var/lib/postgresql/data
    networks:
      - backend
    deploy:
      placement:
        constraints: [node.role == manager]
48. restart
默認(rèn)值為 no ,即在任何情況下都不會(huì)重新啟動(dòng)容器;當(dāng)值為 always 時(shí),容器總是重新啟動(dòng);當(dāng)值為 on-failure 時(shí),當(dāng)出現(xiàn) on-failure 報(bào)錯(cuò)容器退出時(shí),容器重新啟動(dòng)。

restart: "no"
restart: always
restart: on-failure
restart: unless-stopped
49. 其他選項(xiàng)
關(guān)于標(biāo)簽:cpu_shares、cpu_quota、 cpuse、domainname、hostname、 ipc、 mac_address、privileged、 read_only、 shm_size、stdin_open、tty、 user、 working_dir

上面這些都是一個(gè)單值的標(biāo)簽,類似于使用 docker run 的效果

cpu_shares: 73
cpu_quota: 50000
cpuset: 0,1
 
user: postgresql
working_dir: /code
 
domainname: foo.com
hostname: foo
ipc: host
mac_address: 02:42:ac:11:65:43
 
privileged: true
 
 
read_only: true
shm_size: 64M
stdin_open: true
tty: true
50. 持續(xù)時(shí)間
某些配置選項(xiàng)如 check 的子選項(xiàng)interval以及timeout 的設(shè)置格式

2.5s
10s
1m30s
2h32m
5h34m56s
支持的單位有 us、ms、s、m 以及 h

51. 指定字節(jié)值
某些選項(xiàng)如 bulid 的子選項(xiàng)  shm_size

2b
1024kb
2048k
300m
1gb
支持的單位是 b,k,m 以及 g,或 kb, mb 和 gb。目前不支持十進(jìn)制值

52. extends
這個(gè)標(biāo)簽可以擴(kuò)展另一個(gè)服務(wù),擴(kuò)展內(nèi)容可以是來自在當(dāng)前文件,也可以是來自其他文件,相同服務(wù)的情況下,后來者會(huì)有選擇地覆蓋原有配置

extends:
  file: common.yml
  service: webapp
用戶可以在任何地方使用這個(gè)標(biāo)簽,只要標(biāo)簽內(nèi)容包含 file 和 service 兩個(gè)值就可以了。file 的值可以是相對(duì)或者絕對(duì)路徑,如果不指定 file 的值,那么 Compose 會(huì)讀取當(dāng)前 YML 文件的信息。