docker基础

docker

镜像管理

docker image pull alpin:latest
docker image ls / docker images 
    --filter xx=xx
        danging = true/false 返回(非)悬虚镜像
        before 镜像名称或id
        since 镜像名称或id
        label 镜像标签
    --digests   # 查看镜像摘要
docker image build -t img:tag 
    --nocache=true 
    --squash    # 将镜像合并不分层;但生成的镜像层过大,无法共享
    # 用 apt-get install no-install-recommends 减少下载量
docker image inspect # 查看镜像层
docker history  # 显示镜像构建记录

docker image tag now:tag new-name:new-tag # 创建新标签

容器管理

docker container ls
docker container run -it ubuntu:latest /bin/bash
    -it 交互式执行命令 并将shell连接到当前终端
    Ctrl-PQ 退出容器还保持运行
docker conrainer run 
    -d 
    --name 容器名称 
    -p 80:80
    -e  # 定义环境变量
    --network docker0/network-name # 指定连接的网络
    -v /opt/data:/var/lib/mysql
    --restart always / unless-stopped / on-failed
    --flag # 将卷挂载到新建容器中
    img:tag
docker exec -it 3234d5 /bin/bash    # 进入到运行中的容器

docker container stop docker-id
docker container rm docker-id
docker container rm -f $(docker container ls -aq) # 删除所有容器




dockerfile

FROM    image
LABEL   信息="xxx"

RUN     执行的命令   # 没执行一次创建一个新的层
COPY    终端路径 镜像路径
ADD     复制文件,同上
WORKDIR 当前工作目录

EXPOSE  记录应用使用的端口
ENV     定义环境变量

ENTRYPOINT ["镜像运行后执行的命令", "参数"] # 在shell环境下运行
CMD     执行命令    # 无shell环境,此命令会被 docker run 后的shell命令取代

例子:

FROM alpine
LABEL maintainer="nigelpoulton@hotmail.com"
RUN apk add --update nodejs nodejs-npm
COPY . /src
WORKDIR /src
RUN npm install
EXPOSE 8080
ENTRYPOINT ["node", "./app.js"]
FROM python:3.4-alpine  # 基础镜像
ADD . /code             # 将app复制到镜像中
WORKDIR /code           # 设置工作目录
RUN pip install -r requirements.txt # 安装依赖
CMD ["python", "app.py"]    # 设置默认启动命令

onbuild:当包含onbuild指令的镜像在作为父镜像生成子镜像,在子镜像构建时父镜像onbuild指令会最先执行

FROM node:0.12.6

RUN mkdir -p /usr/src/app 
WORKDIR /usr/src/app

ONBUILD COPY package.json /usr/src/app/ 
ONBUILD RUN npm install 
ONBUILD COPY . /usr/src/app

CMD [ "npm", "start" ]

使用以上dockerfile生成的镜像构建子镜像时,Docker会自动将文件复制并下载依赖再复制代码

段阶段构建

FROM node:latest AS storefront
WORKDIR /usr/src/atsea/app/react-app
COPY react-app .
RUN npm install
RUN npm run build

例子:

FROM maven:latest AS appserver
WORKDIR /usr/src/atsea
COPY pom.xml .
RUN mvn -B -f pom.xml -s /usr/share/maven/ref/settings-docker.xml dependency
\:resolve
COPY . .
RUN mvn -B -s /usr/share/maven/ref/settings-docker.xml package -DskipTests
FROM java:8-jdk-alpine AS production
RUN adduser -Dh /home/gordon gordon
WORKDIR /static
COPY --from=storefront /usr/src/atsea/app/react-app/build/ .
WORKDIR /app    # 从其他镜像复制应用
COPY --from=appserver /usr/src/atsea/target/AtSea-0.0.1-SNAPSHOT.jar .  # 从其他镜像复制
ENTRYPOINT ["java", "-jar", "/app/AtSea-0.0.1-SNAPSHOT.jar"]
CMD ["--spring.profiles.active=postgres"]

docker-compose

docker-compose  up -d
down / top / stop / ps / restart
version: "3.5"
services:
web-fe:
    build: .        # 指定dockerfile的目录
    command: python app.py      # 在docker容器中执行
    ports:
        - target: 5000      # 将内部端口映射到外部
        - published: 5000
    networks:
        - counter-net       # 连接到制定网络
    volumes:
        - type: volume
          source: counter-vol
          target: /code     # 数据持久化
        
        - .:/lib/dir        # 两种持久化方式

redis:
    image: "redis:alpine"
    networks:
        counter-net:

networks:
counter-net:

volumes:
counter-vol:

# docker-compose [-f ./docker-compose.yml] -d

Swarm

https://docs.docker.com/engine/swarm/

docker自带的集群管理工具,使用标准docker api,可通过正常的 docker run 启动,swarm自动选择合适的主机。寻找主机和加入集群成为发现,默认使用基于令牌的方法。

swarm结构:每台主机一个Swarm代理,一台机器上运行swarm主管。有高可用模式,使用etcd、Consul、ZooKeeper使发生故障时可切换到其他主管主机。

使用端口

  • 2377/tcp:用于客户端与 Swarm 进行安全通信。
  • 7946/tcp 与 7946/udp:用于控制面 gossip 分发。
  • 4789/udp:用于基于 VXLAN 的覆盖网络。
# 初始化节点
docker swarm init \
--advertise-addr 10.0.0.1:2377 \
--listen-addr 10.0.0.1:2377

# 列出节点
docker node ls

# 在管理节点上获得token,以 工作/管理 节点身份加入
docker swarm join-token (worker|manager)

# 工作节点加入集群
docker swarm join \
--token SWMTKN-1-0uahebax...c87tu8dx2c \
10.0.0.1:2377 \
--advertise-addr 10.0.0.4:2377 \
--listen-addr 10.0.0.4:2377

--autolock	# 强制要求重启的管理节点在提供一个集群解锁码之后才有权从新接入集群

docker swarm update --autolock=true # 开启并生成解锁码
>>  SWMKEY-1-5+ICW2kRxPxZrVyBDWzBkzZdSd0Yc7Cl2o4Uuf9NPU4
# 开启后再意外退出的节点加入需要解锁码
docker swarm unlock	# 解锁

集群中使用了raft技术。部署奇数个管理节点,防止脑裂;不部署太多管理节点(一般3-5个最多7个),越多达成共识的时间越长。

管理swarm服务

docker service create --name web-fe \
-p 8080:8080 \
--replicas 5 \
nigelpoulton/pluralsight-docker-ci	# 启动服务

docker service ls
docker service ps <service>
docker service inspect --pretty	# 获取详细信息
docker service scale demo=5	# 对副本个数进行增减
docker service update		# 对属性进行变更
docker service logs
docker service rm

docker stack

参考: https://zhuanlan.zhihu.com/p/182198031

在swarm集群基础上,以yml文件为配置表单实现docker容器的跨主机部署。

# 部署
docker stack deploy -c docker-stack.yml stack_name
# 查看stack
docker stack ls
# 查看stack包含的service
docker stack ps stack_name
# 获得stack包含的service id后可使用 docker service 查看
一个 docker-stack.yml 示例
version: "3" # 版本号,deploy功能是3版本特有的,所以只能写3
services: #服务,每个服务对应配置相同的一个或者多个docker容器
  stack_mosquitto: # 服务名,自取
    image: toke/mosquitto #创建该服务所基于的镜像
    ports: # 容器内外的端口映射情况
      - "1883:1883"
      - "9001:9001"
    networks: # 替代了命令行模式的--link选项
      fiware:
        aliases:
          - mosquitto
    volumes: # 容器内外数据传输的对应地址
      - "/srv/mqtt/config:/mqtt/config:ro"
      - "/srv/mqtt/log:/mqtt/log"
      - "/srv/mqtt/data/:/mqtt/data/"
    deploy: 
      replicas: 1 # replicas模式, 复制数目为1
      restart_policy:
        condition: on-failure
      placement:
        constraints: [node.role == worker] # 部署位置,只在工作节点部署

  stack_mongo:
    image: mongo
    ports:
      - "27017:27017"
    networks:
      fiware:
        aliases:
          - mongo
    volumes:
      - "/home/ubuntu/db:/data/db"
    deploy:
      replicas: 1
      restart_policy:
        condition: on-failure
      placement:
        constraints: [node.role == manager]
  stack_orion:
    image: fiware/orion
    ports:
      - "1026:1026"
    networks:
      fiware:
        aliases:
          - orion
    command: -dbhost stack_mongo # 命令行模式中跟在最后的参数,此条没有固定的格式,建议参照所部署的docker镜像的说明文档来确定是否需要该项、需要写什么
    deploy:
      replicas: 1
      restart_policy:
        condition: on-failure
      placement:
        constraints: [node.role == manager] 

  stack_iotagent:
    image: telefonicaiot/iotagent-ul
    ports:
      - "4041:4041"
      - "7896:7896"
    networks:
      fiware:
        aliases:
          - iotagent
    deploy:
      replicas: 1
      placement:
        constraints: [node.role == worker]

networks: #定义部署该项目所需要的网络
  fiware:

网络管理

docker 默认使用 bridge 模式
docker 默认创建名为 docker0 的Linux网桥设备,拥有一个私有网络地址和子网。所有容器被连接到该网桥并分配一个子网的IP地址,并把docker0设置为网关。创新容器时,Docker创建一对网络设备接口,一个放入容器的网络命名空间(即eth0),另一个放入宿主机的网络命名空间并连接到docker0网桥设备上。容器的流量通过NAT技术转发。

使用 docker run --network xxx 指定网络类型

  1. none 不使用网络
  2. host 容器中网络设备将与宿主机完全一致,包括docker0网桥设备。容器进程被隔离在自己的命名空间中,资源被cgroups限制,容器的网络命名空间和宿主相同。这时不能在容器内对网络进行修改。(当root用户使用--network=host --privileged=true启用host网络主机时非常危险,但适合对网络IO性能非常敏感的进程)
  3. bridge 单机桥接网络,只能本机上的容器相互通信
  4. overlay 分布式网络,swarm集群中网络
docker network ls
docker network create -d bridge localnet # 创建本地桥接网络

docker network create -d macvlan \
--subnet=10.0.0.0/24 \
--ip-range=10.0.0.0/24 \
--gateway=10.0.0.1 \
-o parent=eth0.100 \
macvlan100

docker network create -d overlay uber-net
子命令 说明
docker network connect 将容器连接到网络。
docker network create 创建新的 Docker 网络。默认情况下,在 Windows 上会采用 NAT 驱动,在 Linux 上会采用 Bridge 驱动。可以使用 -d 参数指定驱动(网络类型)。
docker network disconnect 断开容器的网络。
docker network inspect 提供 Docker 网络的详细配置信息。
docker network ls 用于列出运行在本地 Docker 主机上的全部网络。
docker network prune 删除 Docker 主机上全部未使用的网络。
docker network rm 删除 Docker 主机上指定网络。

卷管理

docker volume create myvol
docker volume inspect
docker volume ls
docker volume prune
docker volume rm
version: '2.0'
services:
  web:
    build: .
    ports:
      - "5000:5000"
    volumes:
      - .:/code
      - logvolume01:/var/log
    links:
      - redis   network:     - mynetwork
  redis:
    image: redis   network:       - mynetwork
volumes:
  logvolume01: {}network:  mynetwork:    driver: bridge
# 可能等同于下方命令
docker  build   .
docker  run -d  -p 5000:5000  \
            -v  .:/code  -v logvolume01  \
            --link  redis   --name  web  
            
docker  run -d  --name  redis  redisdocker  volume  create logvolume01docker  network create  mynetwork

几个 docker-compose 配置文件的例子

# wordpress-mysql
version: '3'

services:

  wordpress:
    image: wordpress
    ports:
      - 8080:80
    environment:
      WORDPRESS_DB_HOST: mysql
      WORDPRESS_DB_PASSWORD: root
    networks:
      - my-bridge

  mysql:
    image: mysql
    environment:
      MYSQL_ROOT_PASSWORD: root
      MYSQL_DATABASE: wordpress
    volumes:
      - mysql-data:/var/lib/mysql
    networks:
      - my-bridge

volumes:
  mysql-data:

networks:
  my-bridge:
    driver: bridge
version: "3"

services:
  voting-app:
    build: ./voting-app/.
    volumes:
     - ./voting-app:/app
    ports:
      - "5000:80"
    links:
      - redis
    networks:
      - front-tier
      - back-tier

  result-app:
    build: ./result-app/.
    volumes:
      - ./result-app:/app
    ports:
      - "5001:80"
    links:
      - db
    networks:
      - front-tier
      - back-tier

  worker:
    build: ./worker
    links:
      - db
      - redis
    networks:
      - back-tier

  redis:
    image: redis
    ports: ["6379"]
    networks:
      - back-tier

  db:
    image: postgres:9.4
    volumes:
      - "db-data:/var/lib/postgresql/data"
    networks:
      - back-tier

volumes:
  db-data:

networks:
  front-tier:
  back-tier:
  
docker service create  --name wordpress\
        -p 80:80\
        -e WORDPRESS_ROOT_PASSWORD=000000\
        -e WORDPRESS_DB_NAME=wordpress\
        --network  my-overlay\
        wordpress


docker service create  --name mysql \
        -e MYSQL_ROOT_PASSWORD=000000\
        -e MYSQL_DATABASE=wordpress\
        --network my-overlay\
        --mount type=volume,source=volume-demo,destination=/var/lib/mysql\
        mysql
posted @ 2020-12-30 08:44  某某人8265  阅读(64)  评论(0编辑  收藏  举报