Docker基础

Docker介绍

Docker是一个开源的软件项目,在Linux操作系统上,Docker提供了一个额外的软件抽象层及操作系统层虚拟化的自动管理机制。Docker运行名为“Container(容器)”的软件包,容器之间彼此隔离,并捆绑了自己的应用程序、工具、库和配置文件。所有容器都由单个操作系统内核运行,因此比虚拟机更轻量级。Docker利用Linux资源分离机制,例如cgroups及Linux Namespace来创建相互独立的容器(Container),可以在单个Linux实体下运行,避免了启动一个虚拟机造成的额外负担。Linux核心对Namespace(命名空间)的支持完全隔离了不同Namespace下的应用程序的“视野”(即作用范围),包括进程树、网络、用户ID与挂载的文件系统等,而核心cgroups则提供了资源隔离,包括CPU、存储器、Block I/O与网络。

Docker基本命令

查看Docker版本

包括Docker版本号、API版本号、Git Commit、Go版本号等

[root@k8s-master home]# docker version
Client: Docker Engine - Community
 Version:           19.03.11
 API version:       1.40
 Go version:        go1.13.10
 Git commit:        42e35e61f3
 Built:             Mon Jun  1 09:13:48 2020
 OS/Arch:           linux/amd64
 Experimental:      false

Server: Docker Engine - Community
 Engine:
  Version:          19.03.11
  API version:      1.40 (minimum version 1.12)
  Go version:       go1.13.10
  Git commit:       42e35e61f3
  Built:            Mon Jun  1 09:12:26 2020
  OS/Arch:          linux/amd64
  Experimental:     false
 containerd:
  Version:          1.2.13
  GitCommit:        7ad184331fa3e55e52b890ea95e65ba581ae3429
 runc:
  Version:          1.0.0-rc10
  GitCommit:        dc9208a3303feef5b3839f4323d9beb36df0a9dd
 docker-init:
  Version:          0.18.0
  GitCommit:        fec3683
You have new mail in /var/spool/mail/root

查询镜像

OFFICIAL为OK的是官方镜像,默认搜索的是hub.docker.com。

[root@k8s-master home]# docker search nginx

拉取/下载镜像。默认是hub.docker.com(docker.io)上面的镜像,如果拉取公司内部的镜像或者其他仓库上的镜像,需要在镜像前面加上仓库的URL,如:

#拉取公网上的Nginx镜像
[root@k8s-master home]# docker pull nginx

#拉取指定版本
[root@k8s-master home]# docker pull nginx:1.15

推送镜像

把本地的镜像推送到公网仓库中,或者公司内部的仓库中。默认登录和推送的是公网的镜像,如果需要推送到公司仓库或者其他仓库,只需要在镜像前面使用tag并加上URL即可:

docker tag nginx:1.15 futongcloud/nginx_hu:1.15
docker login
docker push futongcloud/nginx_hu:1.15

前台启动一个容器

[root@k8s-master home]# docker run -it nginx bash
root@36d8bb21092a:/#

后台启动

[root@k8s-master home]# docker run -itd nginx bash

# 关闭容器
[root@k8s-master home]# docker ps -l|grep -v CON|awk '{print $1}'|xargs docker rm -f
08846dd8b468

端口映射

可以将本机的端口映射到容器的端口,比如将本机的1111端口映射到容器的80端口:

[root@k8s-master home]# docker run -itd -p 1111:80 nginx bash
5c8cc90025a1deaa1a4a27d799154381f2b7eafaf7b68b18b0df1cc01c5a92c2
[root@k8s-master home]# docker ps -l
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                  NAMES
5c8cc90025a1        nginx               "/docker-entrypoint.…"   3 seconds ago       Up 2 seconds        0.0.0.0:1111->80/tcp   elastic_hasle

查看当前正在运行的容器

[root@k8s-master home]# docker ps

查看所有容器,包括已经退出的

[root@k8s-master home]# docker ps -a

查看正在运行的容器(即显示出容器的ID)

[root@k8s-master home]# docker ps -l -q
5c8cc90025a1

查看所有容器的ID,包括已经退出的

[root@k8s-master home]# docker ps -aq
5c8cc90025a1
f19f82a174ea
36d8bb21092a
d09ebce9438b
cced4a08e81a
b516ebe6cc13

进入到一个后台运行的容器(即之前用-d命令参数来指定后台运行方式的容器)

[root@k8s-master home]# docker ps -l
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                  NAMES
5c8cc90025a1        nginx               "/docker-entrypoint.…"   8 minutes ago       Up 8 minutes        0.0.0.0:1111->80/tcp   elastic_haslett
[root@k8s-master home]# docker exec -it 5c8cc bash
root@5c8cc90025a1:/#

拷贝文件

双向拷贝,可以将本机的文件拷贝到容器,反之亦然:

docker cp image_pull-k8s.sh 5c8cc:/tmp
[root@k8s-master home]# docker exec 5c8cc ls /tmp/
image_pull-k8s.sh

删除已经退出的容器

[root@k8s-master home]# docker ps -a | grep Exited|tail -3
f19f82a174ea        nginx                    "/docker-entrypoint.…"   12 minutes ago      Exited (0) 12 minutes ago
modest_taussig36d8bb21092a        nginx                    "/docker-entrypoint.…"   15 minutes ago      Exited (130) 14 minutes ago
relaxed_maxwellcced4a08e81a        quay.io/coreos/flannel   "cp -f /etc/kube-fla…"   2 hours ago         Exited (0) 2 hours ago
k8s_install-cni_kube-flannel-ds-amd64-f4g2x_kube-system_b0806149-dba6-4e95-b46b-fb1adb77fafe_0[root@k8s-master home]# docker rm f19f 36d8 cced4
f19f
36d8
cced4

删除本机镜像。比如删除REPOSITORY为none的镜像

[root@k8s-master home]# docker rmi 2622
Untagged: nginx:latest
Untagged: nginx@sha256:21f32f6c08406306d822a0e6e8b7dc81f53f336570e852e25fbe1e3e3d0d0133
Deleted: sha256:2622e6cca7ebbb6e310743abce3fc47335393e79171b9d76ba9d4f446ce7b163
Deleted: sha256:e86d1b8b130bec203609b4b1d7b851bd763fa16e513e5a3fa6102ebea23260e0

镜像打标签(tag)。用于区分不同版本的镜像

[root@k8s-master home]# docker tag nginx:1.15 nginx_hu:1.15

使用dockerbuild通过Dockerfile制作镜像。注意最后的一个点(.),表示使用当前目录的Dockerfile:

docker build -t image_name:image_tag .

Dockerfile的编写

Dockerfile是用来快速创建自定义镜像的一种文本格式的配置文件,在持续集成和持续部署时,需要使用Dockerfile生成相关应用程序的镜像,然后推送到公司内部仓库中,再通过部署策略把镜像部署到Kubernetes中。通过Dockerfile提供的命令可以构建Dockerfile文件,Dockerfile的常用命令如下:

参考文献 https://www.runoob.com/docker/docker-dockerfile.html

以下简单演示每个命令的使用方法。使用RUN创建一个用户:

[root@k8s-master dockefile]# cat Dockerfile
# base image
FROM centos:6
MAINTAINER dot
RUN useradd dot
#执行构建
docker build -t centos:user .

使用ENV定义环境变量并用CMD执行命令:

[root@k8s-master dockefile]# cat Dockerfile
# base image
FROM centos:6
MAINTAINER dot
RUN useradd dot && mkdir dot
ENV envir=yesy version=1.0
CMD echo "envir:$envir version:$version"
# 执行构建
[root@k8s-master dockefile]# docker build -t centos:env-cmd .
# 启动镜像验证ENV和CMD
[root@k8s-master dockefile]# docker run centos:env-cmd
envir:yesy version:1.0

使用ADD添加一个压缩包,使用WORKDIR改变工作目录:

[root@k8s-master dockerfile2]# cat Dockerfile
# base image
FROM nginx
MAINTAINER dot
ADD ./index.tar.gz  /usr/share/nginx/html/
WORKDIR /usr/share/nginx/html

使用COPY拷贝指定目录下的所有文件到容器,不包括本级目录。此时只会拷贝webroot下的所有文件,不会将webroot拷贝过去:

cat Dockerfile
# base image
FROM nginx
MAINTAINER dot
ADD ./index.tar.gz  /usr/share/nginx/html/
WORKDIR /usr/share/nginx/html
COPY webroot/ .

设置启动容器的用户,在生产环境中一般不建议使用root启动容器,所以可以根据公司业务场景自定义启动容器的用户:

[root@k8s-master dockerfile2]# cat Dockerfile
# base image
FROM nginx
MAINTAINER dot
ADD ./index.tar.gz  /usr/share/nginx/html/
WORKDIR /usr/share/nginx/html
COPY webroot/ .
RUN useradd -m tomcat -u 1001
USER 1001

使用Volume创建容器可挂载点:

[root@k8s-master dockerfile3]# cat Dockerfile
#base image
FROM centos:6
MAINTAINER dot

VOLUME /data

挂载Web目录到/data,注意,对于宿主机路径,要写绝对路径:

[root@k8s-master dockerfile3]# docker run -it --rm -v `pwd`/web:/data centos:volume bash

Dockerfile示例

FROM ubuntu:18.04

RUN mkdir /kubespray
WORKDIR /kubespray
RUN apt update -y && \
    apt install -y \
    libssl-dev python3-dev sshpass apt-transport-https jq moreutils \
    ca-certificates curl gnupg2 software-properties-common python3-pip rsync
RUN  curl -fsSL https://download.docker.com/linux/ubuntu/gpg | apt-key add - && \
     add-apt-repository \
     "deb [arch=amd64] https://download.docker.com/linux/ubuntu \
     $(lsb_release -cs) \
     stable" \
     && apt update -y && apt-get install docker-ce -y
COPY . .
RUN /usr/bin/python3 -m pip install pip -U && /usr/bin/python3 -m pip install -r tests/requirements.txt && python3 -m pip install -r requirements.txt && update-alternatives --install /usr/bin/python python /usr/bin/python3 1
RUN curl -LO https://storage.googleapis.com/kubernetes-release/release/v1.17.5/bin/linux/amd64/kubectl \
    && chmod a+x kubectl && cp kubectl /usr/local/bin/kubectl

# Some tools like yamllint need this
ENV LANG=C.UTF-8