docker-compose實戰


Docker-Compose是Docker的一種編排服務,是一個用於在Docker上定義並運行復雜應用的工具,可以讓用戶在集群中部署分布式應用。

通過Docker-Compose用戶可以很容易地用一個配置文件定義一個多容器的應用,然后使用一條指令安裝這個應用的所有依賴,完成構建。Docker-Compose解決了容器與容器之間如何管理編排的問題。

如Docker-Compose文件格式為2.0,Docker Engine版本必須大於1.10.0
如Docker-Compose文件格式為1.0,Docker Engine版本必須大於1.9.1

安裝Docker-Compose

直接使用二進制文件安裝:

# curl -L https://github.com/docker/compose/releases/download/1.17.0-rc1/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose
# chmod +x /usr/local/bin/docker-compose

驗證安裝成功
# docker-compose --version

Docker-Compose常用命令,可以查看docker-compose的用法,里面有詳細的解釋。

Docker-Compose YAML語法使用說明
默認的模板文件是 docker-compose.yml,其中定義的每個服務都必須通過image指令指定鏡像或build指令(需要 Dockerfile)來自動構建。其它大部分指令都跟docker run中的類似。

如果使用build指令,在Dockerfile中設置的選項(例如:CMD, EXPOSE, VOLUME, ENV 等) 將會自動被獲取,無需在docker-compose.yml中再次設置。

  • build

這個是創建docker鏡像時的選項,通過本地的dockerfile來創建,而不是通過image id來pull。
其中build還有一些小選項。

build:
  context: ./nginx
  dockerfile: Dockerfile
  args:
    - buildno=1
    - user=someuser

dockerfile選項是備選的dockerfile。args是一些提供的參數。

  • image: 

生成鏡像的ID,指定為鏡像名稱或鏡像 ID。如果鏡像在本地不存在,Compose 將會嘗試拉去這個鏡像。

image: ubuntu
image: orchardup/postgresql
  • links

鏈接到其它服務中的容器,使一個容器可以主動的去和另外一個容器通訊。使用服務名稱(同時作為別名)或服務名稱:服務別名 (SERVICE:ALIAS) 格式都可以。

links:
 - db
 - db:database
 - redis

使用的別名將會自動在服務容器中的 /etc/hosts 里創建,相應的環境變量也將被創建。例如

172.17.2.186  db
172.17.2.186  database
172.17.2.187  redis
  • external_links

鏈接到 docker-compose.yml 外部的容器,甚至 並非 Compose 管理的容器。參數格式跟 links 類似。

external_links:
 - redis_1
 - project_db_1:mysql
 - project_db_1:postgresql
  • expose

這個是給link用的,將一些端口暴露給link到這個container上的containers。暴露端口,但不映射到宿主機,只被連接的服務訪問

expose:
    - "3000"
    - "8000"
  • ports

暴露端口信息,這個是將端口和本機端口映射的選項,寫法如下,其實跟docker -p一樣。使用宿主:容器 (HOST:CONTAINER)格式或者僅僅指定容器的端口(宿主將會隨機選擇端口)都可以。

ports:
    - "3000"
    - "3000-3005"
    - "80:80"
    - "9090-9091:8080-8081"
    - "49100:22"
    - "127.0.0.1:8001:8001"
    - "127.0.0.1:5000-5010:5000-5010"

注:當使用 HOST:CONTAINER 格式來映射端口時,如果你使用的容器端口小於 60 你可能會得到錯誤得結果,因為 YAML 將會解析 xx:yy 這種數字格式為 60 進制。所以建議采用字符串格式。

  • environment:

設置環境變量。你可以使用數組或字典兩種格式。
只給定名稱的變量會自動獲取它在 Compose 主機上的值,可以用來防止泄露不必要的數據。

environment:
  RACK_ENV: development
  SESSION_SECRET:

environment:
  - RACK_ENV=development
  - SESSION_SECRET
  • env_file

從文件中獲取環境變量,可以為單獨的文件路徑或列表。
如果通過 docker-compose -f FILE 指定了模板文件,則 env_file 中路徑會基於模板文件路徑。
如果有變量名稱與 environment 指令沖突,則以后者為准。

env_file: .env

env_file:
  - ./common.env
  - ./apps/web.env
  - /opt/secrets.env
  • volumes

將本機的文件夾掛載到container中。

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
    # User-relative path
        - ~/configs:/etc/configs/:ro
    # Named volume
        - datavolume:/var/lib/mysql

卷掛載路徑設置。可以設置宿主機路徑 (HOST:CONTAINER) 或加上訪問模式 (HOST:CONTAINER:ro)

volumes:
 - /var/lib/mysql
 - cache/:/tmp/cache
 - ~/configs:/etc/configs/:ro
  • volumes_from

從另一個服務或容器掛載它的所有卷。

volumes_from:
 - service_name
 - container_name
  • extends

基於已有的服務進行擴展。例如我們已經有了一個webapp服務,模板文件為 common.yml。

# common.yml
webapp:
  build: ./webapp
  environment:
    - DEBUG=false
    - SEND_EMAILS=false

編寫一個新的 development.yml 文件,使用 common.yml 中的 webapp 服務進行擴展。

# development.yml
web:
  extends:
    file: common.yml
    service: webapp
  ports:
    - "8000:8000"
  links:
    - db
  environment:
    - DEBUG=true
db:
  image: postgres

后者會自動繼承 common.yml 中的 webapp 服務及相關環節變量。

  • net

設置網絡模式。使用和 docker client 的 –net 參數一樣的值。

net: "bridge"
net: "none"
net: "container:[name or id]"
  • pid

跟主機系統共享進程命名空間。打開該選項的容器可以相互通過進程 ID 來訪問和操作。

pid: "host"
  • dns

配置 DNS 服務器。可以是一個值,也可以是一個列表。

dns: 8.8.8.8
dns:
  - 8.8.8.8
  - 9.9.9.9
  • cap_add, cap_drop

添加或放棄容器的 Linux 能力(Capabiliity)。

cap_add:
  - ALL

cap_drop:
  - NET_ADMIN
  - SYS_ADMIN
  • dns_search

配置 DNS 搜索域。可以是一個值,也可以是一個列表。

dns_search: example.com
dns_search:
  - domain1.example.com
  - domain2.example.com
  • command

覆蓋容器啟動后默認執行的命令。

command: bundle exec thin -p 3000

其它選項

working_dir, entrypoint, user, hostname, domainname, mem_limit, privileged, restart, stdin_open, tty, cpu_sharesv 這些都是和 docker run 支持的選項類似。

cpu_shares: 73
working_dir: /code
entrypoint: /code/entrypoint.sh
user: postgresql
hostname: foo
domainname: foo.com
mem_limit: 1000000000
privileged: true
restart: always
stdin_open: true
tty: true

---------------------------

Docker-Compose使用實例:

Docker-compose搭建tomcat服務

# cat docker-compose.yml 
version: '3.1'
services:
  tomcat:
    restart: always
    image: tomcat
    container_name: tomcat
    ports:
      - 8080:8080
    volumes:
      - ./webapps:/usr/local/tomcat/webapps
    environment:
      TZ: Asia/Shanghai

Docker-compose搭建Redis Sentinel

Redis Sentinel是針對原始Master/Slave模型而衍生的高可用模型。我們為便於靈活部署,先易后難,先搭建Redis Master/Slave模型,再搭建Redis Sentinel模型。

文件目錄結構如下:

docker
├── redis
│   └── docker-compose.yml
└── sentinel
    ├── docker-compose.yml
    ├── sentinel1.conf
    ├── sentinel2.conf
    ├── sentinel3.conf
    └── sentinel.conf

一、搭建Redis Master/Slave模型

下面的Compose文件設置了redis的 一主兩從(Master-Slave)

1.創建並進入redis文件夾,並創建如下docker-compose.yml文件。

[root@localhost ~]# mkdir -p docker/redis
[root@localhost ~]# cd docker/redis
[root@localhost redis]# touch docker-compose.yml
docker-compose.yml文件內容如下:
 
version: '3'
services:
  master:
    image: redis
    container_name: redis-master
    command: redis-server --requirepass redis_pwd  --masterauth redis_pwd
    ports:
      - 6379:6379
  slave1:
    image: redis
    container_name: redis-slave-1
    ports:
      - 6380:6379
    command:  redis-server --slaveof redis-master 6379 --requirepass redis_pwd --masterauth redis_pwd
  slave2:
    image: redis
    container_name: redis-slave-2
    ports:
      - 6381:6379
    command: redis-server --slaveof redis-master 6379 --requirepass redis_pwd --masterauth redis_pwd

注意,如果設置了Redis客戶端訪問密碼requirepass, 那么也要設置相同的副本集同步密碼masterauth。
另外我們后面使用哨兵模式能夠完成故障轉移,現有的Master可能會變成Slave,故在當前Master容器中也要攜帶masterauth參數。

2. 執行 docker-compose up -d 會產生3個Redis容器,分別映射到宿主機6379、6380、6381端口, 默認連接在redis-default網橋。

[root@localhost redis]# docker-compose -f docker-compose.yml up -d
WARNING: IPv4 forwarding is disabled. Networking will not work.
Creating network "redis_default" with the default driver
Pulling master (redis:)...
Trying to pull repository docker.io/library/redis ... 
latest: Pulling from docker.io/library/redis
54fec2fa59d0: Pull complete
9c94e11103d9: Pull complete
04ab1bfc453f: Pull complete
a22fde870392: Pull complete
def16cac9f02: Pull complete
1604f5999542: Pull complete
Creating redis-slave-1 ... done
Creating redis-master  ... done
Creating redis-slave-2 ... done

3. 使用docker ps查看redis輸出:

[root@localhost redis]# docker ps -a
CONTAINER ID    IMAGE    COMMAND          CREATED              STATUS              PORTS                    NAMES
262b42fb0c9f    redis    "docker-en..."   About a minute ago   Up About a minute   0.0.0.0:6381->6379/tcp   redis-slave-2
a2243df4965d    redis    "docker-en..."   About a minute ago   Up About a minute   0.0.0.0:6379->6379/tcp   redis-master
e6d40f337118    redis    "docker-en..."   About a minute ago   Up About a minute   0.0.0.0:6380->6379/tcp   redis-slave-1

查看redis容器使用的網橋信息:

[root@localhost ~]# docker inspect -f {{.HostConfig.NetworkMode}} 262b42fb0c9f
redis_default

4. 驗證
Master/Slave副本集,進入Master容器,確認兩個Slave容器已經連接。

 二、docker-compose 部署Redis Sentinel

我們即將搭建的Sentinel容器需要能訪問到以上3個容器,故需要在形成Sentinel容器時使用外置的redis-default網橋(Redis Master/Slave docker-compose 已經創建).

[root@localhost ~]# mkdir -p docker/sentinel
[root@localhost ~]# cd docker/sentinel/

1 進入sentinel文件夾,創建docker-compose.yml

version: '3'
services:
  sentinel1:
    image: redis
    container_name: redis-sentinel-1
    ports:
      - 26379:26379
    command: redis-sentinel /usr/local/etc/redis/sentinel.conf
    volumes:
      - ./sentinel1.conf:/usr/local/etc/redis/sentinel.conf
  sentinel2:
    image: redis
    container_name: redis-sentinel-2
    ports:
    - 26380:26379
    command: redis-sentinel /usr/local/etc/redis/sentinel.conf
    volumes:
      - ./sentinel2.conf:/usr/local/etc/redis/sentinel.conf
  sentinel3:
    image: redis
    container_name: redis-sentinel-3
    ports:
      - 26381:26379
    command: redis-sentinel /usr/local/etc/redis/sentinel.conf
    volumes:
      - ./sentinel3.conf:/usr/local/etc/redis/sentinel.conf
networks:
  default:
    external:
      name: redis_default

2 創建哨兵文件sentinel.conf,將如下內容拷貝進去:

port 26379
dir /tmp
sentinel monitor mymaster 172.18.0.4 6379 2
sentinel auth-pass mymaster redis_pwd
sentinel down-after-milliseconds mymaster 30000
sentinel parallel-syncs mymaster 1
sentinel failover-timeout mymaster 180000
sentinel deny-scripts-reconfig yes

注意,以上 172.18.0.4是之前Redis Master/slave啟動之后Master節點的IP,通過docker inspect [container]獲取, 這里我們要配合設置Master/Slave訪問密碼。

3 將哨兵文件復制三份,Volume進Sentinel容器。

[root@localhost sentinel]# cp sentinel.conf sentinel1.conf
[root@localhost sentinel]# cp sentinel.conf sentinel2.conf
[root@localhost sentinel]# cp sentinel.conf sentinel3.conf

4 docker-compose up -d生成3個Sentinel容器。

[root@localhost sentinel]# docker-compose -f docker-compose.yml up -d

5 此時docker ps顯示如下:

[root@localhost sentinel]# docker ps -a
CONTAINER ID    IMAGE     COMMAND          CREATED       STATUS         PORTS                                NAMES
33473b024a55    redis     "docker-en..."   12 hours ago  Up 12 hours    6379/tcp, 0.0.0.0:26380->26379/tcp   redis-sentinel-2
65ed9d4032a4    redis     "docker-en..."   12 hours ago  Up 12 hours    6379/tcp, 0.0.0.0:26379->26379/tcp   redis-sentinel-1
02ae36076592    redis     "docker-en..."   12 hours ago  Up 12 hours    6379/tcp, 0.0.0.0:26381->26379/tcp   redis-sentinel-3
262b42fb0c9f    redis     "docker-en..."   17 hours ago  Up 11 hours    0.0.0.0:6379->6379/tcp               redis-master
a2243df4965d    redis     "docker-en..."   17 hours ago  Up 11 hours    0.0.0.0:6381->6379/tcp               redis-slave-2
e6d40f337118    redis     "docker-en..."   17 hours ago  Up 11 hours    0.0.0.0:6380->6379/tcp               redis-slave-1

6 驗證

進入其中一個redis-sentinel容器,確認Master、2個Slave、另外2個Sentinel.

[root@localhost sentinel]# docker exec -it redis-sentinel-1 /bin/bash
root@65ed9d4032a4:/data# redis-cli -p 26379
127.0.0.1:26379> sentinel master mymaster

flags: master表明master正常運作,異常情況會顯示s-down,o-down
num-slaves:偵測到2個Slave副本集
num-other-sentinels:除此之外,還有2個哨兵

3.Redis Sentinel高可用
停止 redis-master容器,等待10s,進入任意sentinel容器,使用sentinel master mymaster命令觀察主節點發生變化,觀察外掛的Sentinel*.conf 主節點IP發生變化,然后重新啟動master節點,檢查集群狀態.

Docker-compose搭建Redis-jenkins

1、創建docker在主機的jenkins數據映射目錄

mkdir -p /data/jenkins_home
chown -R 1000 /data/jenkins_home

2、用docker-compose安裝,當然你也可以用docker run的方式,創建一個docker-jenkins-compose.yml文件。

version: "3"
services:
  jenkins:
    image: jenkins/jenkins:lts
    ports:
      - 8080:8080
      - 50000:50000
    restart: "always"
    container_name: jenkins
    environment:
      JAVA_OPTS: -Duser.timezone=Asia/Shanghai
    volumes:
      - /opt/jenkins/home:/var/jenkins_home
      - /var/run/docker.sock:/var/run/docker.sock
      - /usr/bin/docker:/usr/bin/docker
    privileged: true
    user: root

3、啟動Jenkins容器

docker-compose -f docker-jenkins-compose.yml up -d

 

參考文檔:https://www.cnblogs.com/JulianHuang/p/12650721.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM