Docker 基础知识点和命令
Docker 相关基础
配置
- docker-Post-installation steps for Linux
- 镜像加速器
- 配置指定 Docker 运行的文件夹(放置 images container),通过修改
daemon.json
增加data-root
来指定非默认目录,如果已经运行了一段时间,还需要将之前的数据通过rsync
同步到新的目录. so-docker image installation directory , 详细步骤
基础知识
- docker-compose 中的
depends_on
会依据依赖顺序启动服务,被depends_on
的容器会先启动,但是主动depends_on
的容器不会等到被depends_on
,例如下面的例子:db,redis 容器启动顺序要优先于 web 容器;当启动 web 容器时会自动创建 redis 和 db 容器.不过需要注意的是,depends_on 不会等到 db 和 redis 容器 ready 再启动,web 容器仅仅等到 redis 和 db 容器启动就开始启动.具体可参考 官网启动顺序 了解
version: '2'
services:
web:
build: .
depends_on:
- db
- redis
redis:
image: redis
db:
image: postgres
dockerignore
和 gitignore 一样,用于忽略掉部分不需要的文件,用于加快传输文件到 docker 上下文。写法有很多种:
- 将部分 build 不需要的文件写入 dockerignore 文件:这个是按需排除不需要的文件
- 仅将 build 需要的文件写入 dockerignore 文件:反向思考,参考例子是 apache-airflow 的 dockerignore
# Ignore everything
**
# Allow only these directories
!airflow
!common
!dags
!dev
!docs
!licenses
!scripts
!tests
基础命令
run
- 增加 hosts 到
/etc/hosts
文件中docker run --add-host parameter
,如果使用 docker-compose 用的时extra_hosts
关键字 How to update /etc/hosts file in Docker image during “docker build”
ps
docker ps
: 查看正在运行的容器docker ps -a
: 查看全部容器包括已经退出的容器docker ps -s
: 查看正在运行的容器信息( 包括大小 )
cp
Copy files/folders between a container and the local filesystem.
docker cp src container:dest
: 从宿主机复制文件/文件夹到 docker 容器docker cp container:src dest
: 从 docker 容器复制文件/文件夹到宿主机
network
- 查看 network 下的
Containers
的具体内容docker network inspect --format='{{range .Containers}}{{println .Name}}{{end}}'
- 清除一个 network 中的所有 active endpoints:
docker network inspect --format='{{range .Containers}}{{println .Name}}{{end}}' <network_name> | xargs -I % echo 'docker network disconnect <network_name> %' | sh
inspect
用于查看对象详细信息
--format
: 详见 Format command and log outputjoin
: concatenates a list of strings to create a single stringjson
: encodes an element as a json stringlower
: transforms a string into its lowercase representationsplit
: slices a string into a list of strings separated by a separatortitle
: capitalizes the first character of a stringupper
: transforms a string into its uppercase representationprintln
: prints each value on a new line
system
docker system prune
: clean up all images, containers, networks, volumes not used, offical-systemdocker system prune -a --volumes
: clear all including volumes, 只要是没有 container 使用的 volumes 都会被清除,这可能会带来关键数据丢失的问题,使用前请注意
tag
docker tag SRC:TAG DEST:TAG
或者使用 images iddocker tag d583c3ac45fd DEST:TAG
anddocker rmi SRC:TAG/IMAGE-ID
,参照 Docker how to change repository name or rename image
基本命令
- 进入 docker 容器
docker exec -it container_name bash
- docker 删除虚悬镜像
docker rmi $(docker images -f dangling=true)
- 删除所有停止/退出镜像
docker rm $(docker ps -aq -f status=exited)
-f
是过滤参数 - docker-compose 运行指定 yml 文件
docker-compose -f docker-compose-file.yml up -d
- 用 docker-compose 部署的时候如果要先 build 一些东西的话,可以直接在 service 下面放一个
build
任务,部署的时候用docker-compose up --build
如果没有--build
的话就会引用已经存在的镜像,没有更新到 - docker 格式化 ps 输出
docker ps -format 'table {{.ID}}\t{{.Image}}\t{{.Command}}\t{{.CreatedAt}}\t{{.Status}}\t{{.Ports}}\t{{.Names}}'
这是docker ps
的原生输出,format 后面的table
是格式化输出成表格 - docker-compose 重启单个 workerHow to restart a single container with docker-compose :
docker-compose restart worker
可以设置时间等待杀死容器docker-compose restart -t 30 worker
- docker-compose 停止其中一个容器:
docker-compose stop service-name
- docker-compose 通过 scale 来创建多个容器: docker-compose version 2
docker-compose scale service_a=3; docker-compose scale service_b=3
会生成 3 个 service_a 和 3 个 service_b, 如果 docker-compose version 3 的话要达到同样的效果要docker-compose up -d --scale service_a=3 --scale service_b=3 --no-recreate
而不能单独的运行docker-compose up -d --scale <service_name>=3
这个会只生成 3 个 service_name 容器 - 将本机容器制作导出:
docker save IMAGE | gzip > LOCAL_IMAGE.gz
,将导出的镜像导入:docker load -i LOCAL_IMAGE.gz
网络相关
- 查看容器的网络,参考 how to get a docker containers ip address from the host :
- modern Docker client syntax:
docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' container_name_or_id
- old Docker client syntax:
docker inspect --format '{{ .NetworkSettings.IPAddress }}' container_name_or_id
- modern Docker client syntax:
- 查看 docker 指定 network 上面有的容器
docker network inspect network_name -f "{{range .Containers}}{{.Name}} {{end}}"
主要参照了 how to get a docker containers ip address from the host 的写法 - docker-compose v2 + external container
- docker 显示容器的 IP
docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' container_name_or_id
参见 how to get a docker containers ip address from the host
Dockerfile
multi-stage build
Dockerfile 的 multi-stage build 属性允许你创建更小的镜像,更好的使用 cache,为每个特定的镜像编写更加小的 entrypoint,了解更多查看 这里
# 在 dockerfile 文件中指定镜像的版本 可以在构建镜像时使用 `--build-arg UBUNTU_VERSION=value` 修改镜像的版本
# 如果么有传对应的值 则会以默认的版本(18.6) 进行构建
ARG UBUNTU_VERSION=18.6
# 可以对当前的 stage 进行别名方便后面的 stage 调用
FROM ubuntu:${UBUNTU_VERSION} AS base
RUN apt-get update && apt-get install git
# 可以从之前的 stage 中来
FROM base AS src1
RUN git clone …
FROM alpine
# --from 可以直接从已有的镜像中拿对应的值
# 也可以使用之前已经完成的 stage,如 `--from=base`
COPY --from=linuxkit/ca-certificates / /
# 可以使用更加有意义的别名 如对 release 镜像衍生出 dev-env test 镜像分别用于开发和测试
FROM scratch AS release
FROM golang:alpine AS dev-env
COPY --from=release / /
ENTRYPOINT ["ash"]
FROM golang:alpine AS test
COPY --from=release / /
RUN go test …
先编译然后复制编译后的值
FROM nodejs as builder
WORKDIR /usr/src/app
COPY . .
RUN npm build
FROM nginx
COPY --from=builder /usr/src/app/build/ /nginx_home
docker-compose
docker-compose 汇总
docker-compose up -d --no-build
: docker-compose 启动但是不重新 build 镜像
ulimits
指定容器的 ulimits 限制值。例如,指定最大进程数为 65535,指定文件句柄数为 20000(软限制,应用可以随时修改,不能超过硬限制) 和 40000(系统硬限制,只能 root 用户提高)
ulimits:
nproc: 65535
nofile:
soft: 20000
hard: 40000
example
- MySQL Docker Containers: Understanding the basics : 通过一步步部署 mysql 的例子说明了 docker 是怎么运行的,链接一个已经存在的 container
- severalnines-dockder+mysql
docker FAQ
- Cannot install packages inside docker Ubuntu image : should
apt-get -qq update
first, because no package cache in the image - docker-mysql 用数据卷自定义配置之后 connect mysql 会变慢,可以在自定义配置文件 section mysqld 增加
skip-name-resolve
选项 - docker-mysql 自定义文件编码 section mysql & client default-character-set=utf8 并且 section mysqld
character-set-server=utf8
- docker Hub Automated Build with specify tag
- docker build 如果上一次运行成功,下次再运行会直接使用 cache,
docker build --no-cache
可以指定不使用 cache, How to force docker for clean build of an image - docker 默认的 registry 地址
https://index.docker.io/v1/
,可以通过docker info | grep -i registry
得到 docker 中所有的信息.如果国内镜像仓库中部分镜像没有更新(例如自己编译的镜像没有及时更新),docker pull registry.hub.docker.com/library/busybox
不要以 root 用户运行容器
docker 的其中一个最佳实践就是不要已 root 用户运行容器,因为容器中的 root 和宿主机中的 root(uid 0) 是同一个,这意味着在容器用户可以对宿主机文件目录进行读写,这样会导致很多可能的问题.相见 这里
docker 模拟网址
play-with-docker : t’s an online playground where you can test all the latest Docker features without having to install anything locally
docker 中中文乱码
进入对应 image 生成的容器中,输入 locale
查看支持什么编码, C.UTF-8
以及 zh_CN.UTF-8
都可以,但是大部分 docker 镜像都只有 C.UTF-8
,之后在 dockerfile 中增加一行 ENV LANG C.UTF-8
即可,如果还不行就增加
ENV LANGUAGE C.UTF-8
ENV LANG C.UTF-8
ENV LC_ALL C.UTF-8
ENV LC_CTYPE C.UTF-8
ENV LC_MESSAGES C.UTF-8
docker 开放远程 API 调用
- 开启 docker 远程调用 API 端口
- MAC: 根据 docker/for-mac:ISSUE-770 ,默认不开启远程调用端口,可以 fork 一个容器开启端口
docker run -d -v /var/run/docker.sock:/var/run/docker.sock -p 127.0.0.1:2375:2375 bobrik/socat TCP-LISTEN:2375,fork UNIX-CONNECT:/var/run/docker.sock
,然后export DOCKER_HOST=unix:///var/run/docker.sock
- Linux:
- Windows: 点击 docker 图标,在
设置->通用
选项勾选Expose daemon on tcp://localhost:2375 without TLS
- MAC: 根据 docker/for-mac:ISSUE-770 ,默认不开启远程调用端口,可以 fork 一个容器开启端口
- 在 docker-deamon 运行的机器中,检查端口是否开放
netstat -anp | grep 2375
或者lsof -i:2375
- 在 docker-deamon 运行的机器中,检查能否通过 tcp 访问 docker-deamon,
docker -H tcp://localhost:2375 images
- 在需要调用 remote-api 的机器检查 2375 端口是否开启,
telnet <IP>:2375
,如果上面都能成功倒是这步不成功,就是服务器防火墙没有开放 2375 端口,开放端口即可
pycharm 中使用 docker 中的解释器
参照 Configure a remote interpreter using Docker ,需要根据 docker 开放远程 API 调用 先启动远程调用端口,然后新增配置解释器配置.如果是离线的话需要 busybox:latest
以及 pycharm_helper:PY-<对应的版本号>
docker build 时 apt-get 的速度慢的解决办法
和本机 apt-get
慢是同一解决办法,使用国内的源,使用的方式参考 tenxcloud/docker-debian ,将国内源写入 sources.list
文件,使用时在 Dockerfile
中使用 COPY sources.list /path/to/docker_sources.list
替换原来的源,最后在 RUN
中运行 apt clean \ && apt update
docker build 中需要使用代理下载
docker 在本地 build 的时候可能需要下载需要翻墙的二进制包,可以参考 SO ,在 docker 的 configure 中配置 proxy 属性,然后重启 docker 就能使用了。如果是 mac 客户端的话,可以在 Prefrences -> Resources -> PROXIES
开启手动代理配置,然后重启 docker
docker build 时 COPY ADD 提示文件不存在
相关的[SO][]可能原因如下:
- 文件路径写错:文件路径可能比较复杂,导致本地路径写错。此时修改成正确路径即可
- 运行 docker build 的路径错了:本应该在指定路径运行 docker build 的,但却在别的路径下运行了。此时切换到正确的路径即可
- dockerignore 文件错误:要 COPY/ADD 的文件在 dockerignore 文件中,或者 dockerignore 仅允许指定文件发送到 docker 上下文中。此时检查 dockerignore 的配置然后修改即可
docker-compose 运行时发现 COMPOSE_HTTP_TIMEOUT
更加可配置地方案是,编辑 .env
文件,加入 COMPOSE_HTTP_TIMEOUT=200
项目 SO
MAC 配置 2375 端口可以登录
docker 的 mac 默认不启动 2375 端口, 参考 ,方便的方式是直接写一个快捷方式到 zshrc
alias docker-api-start='docker run -d -v /var/run/docker.sock:/var/run/docker.sock -p 127.0.0.1:2375:1234 --name docker-api bobrik/socat TCP-LISTEN:1234,fork UNIX-CONNECT:/var/run/docker.sock'
alias docker-api-stop='docker rm -f docker-api'
Tips
- 当遇到部分
Dockerfile
没有办法没有正确写出来的时候,可以去 github 搜索一下base images + pkg_to_install
- 当遇到本地
docker build
过慢时,可以将 Dockerfile 放到 github 上,然后在 docker hub 上设置对应automated-build
当提交到 github master 上后就会自动 build - 如果从国内镜像中 pull 镜像失败,可以直接去 dockerhub 官网拉取
docker pull registry.hub.docker.com/zhongjiajie/docker-airflow
- centos7 安装 docker 之后可能出现不能打开端口的情况,根据 configure Centos7 firewallD to allow docker containers free access to the host's network ports
firewall-cmd --permanent --zone=trusted --change-interface=docker0
firewall-cmd --permanent --zone=trusted --add-port=4243/tcp
firewall-cmd --reload
systemctl restart docker.service
script
一些 docker 相关的 shell 脚本
- 删除 dangling 镜像和停止的容器
echo "remove dangling images" if [[ ! -z $(docker images -f dangling=true -aq) ]]; then docker rmi $(docker images -f dangling=true -aq) fi echo "remove extied container" if [[ ! -z $(docker ps -aq -f status=exited) ]]; then docker rm -f $(docker ps -aq -f status=exited) fi
- 备份非 dangling 的容器
echo "backup not dangling images"
Ref
- docker-Post-installation steps for Linux
- Docker — 从入门到实践
- Docker 中国官方镜像加速
- Docker 官网解释的加速引擎
- 注册并使用阿里云镜像库
- how to get a docker containers ip address from the host
- MySQL Docker Containers: Understanding the basics
- severalnines-dockder+mysql
- severalnines-mysql
- Docker Hub Automated Build - Tagging
- Docker how to change repository name or rename image
- How to force docker for clean build of an image
- How to restart a single container with docker-compose
- 官网启动顺序
- How to update /etc/hosts file in Docker image during “docker build”
- configure Centos7 firewallD to allow docker containers free access to the host's network ports
- Format command and log output
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论