关于 Docker
几乎在一夜之间,Docker 已成为开发人员和系统管理员用于打包、部署和运行分布式和云原生应用程序的事实标准。 它提供了简化 DevOps 的工具,使开发人员能够创建称为映像的模板,这些模板可用于创建称为容器的轻量级虚拟机,其中包括他们的应用程序及其所有应用程序的依赖项。 这些轻量级虚拟机可以通过系统管理员部署和运行它们的测试和生产环境进行推广。
Docker 使组织更容易自动化基础设施、隔离应用程序、保持一致性和提高资源利用率。
与流行的版本控制软件 Git 一样,Docker 具有社交功能,开发人员和系统管理员可以通过 Docker Hub 共享他们的图像。
Docker 是一种开源解决方案,可作为免费的社区版或基于订阅的企业版用于多个平台。 Docker 在 Linux 上原生运行,因为 Docker 最初是在 Linux 容器上构建的,但它也可以在 Mac 和 Windows 上运行。 许多企业工具也围绕 Docker 发展起来,以便更轻松地管理和编排复杂的分布式和集群应用程序架构。
码头工人架构
Docker 利用客户端-服务器架构和远程 API 来管理和创建 Docker 容器和映像。 Docker 容器是从 Docker 镜像创建的。 容器和镜像的关系类似于面向对象编程中对象和类的关系,镜像描述容器,容器是镜像的运行实例。
泊坞窗图像 | 用于创建 Docker 容器的配方或模板。 它包括安装和运行必要软件的步骤 |
---|---|
码头集装箱 | 就像根据 Docker 映像中的指令创建的微型虚拟机 |
码头工人客户端 | 利用 Docker API (https://docs.docker.com/reference/api/docker_remote_api) 与 Docker 守护进程通信的命令行实用程序或其他工具 |
码头工人主机 | 运行 Docker 守护程序并包含缓存图像以及从图像创建的可运行容器的物理或虚拟机 |
Docker 注册表 | 可用于创建 Docker 容器的 Docker 映像存储库。 Docker Hub (https://hub.docker.com) 是 Docker 存储库最流行的社交示例。 |
码头机器 | 用于管理多个 Docker 主机的实用程序,可以在 VirtualBox 中本地运行,也可以在 Amazon Web Services、Microsoft Azure、Google Cloud Platform 或 Digital Ocean 等云托管服务中远程运行。 |
入门
安装 Docker
对于 Mac 和 Windows,安装 Community Edition 有几个不同的选项。 安装 Docker 的现代方法是分别使用 Docker for Mac (https://www.docker.com/docker-mac) 或 Docker for Windows (https://www.docker.com/docker-windows)。 安装包括 Docker 平台、命令行、撰写和公证工具。 这种方法的一个优点是它使用本机平台虚拟化来更好地利用资源。 对于 Windows,这提供了额外的好处,即除了 Linux 容器之外,还能够运行 Windows 容器,但不能同时运行。
注意:适用于 Windows 的 Docker 需要 Windows 10 专业版或企业版 64 位。
在 Mac 和 Windows 上安装 Docker 的另一种方法是使用 Docker Toolbox (https://www.docker.com/products/docker-toolbox)。 它包括 Docker 平台、命令行(包括 Docker Machine)、compose、Kitematic 和 VirtualBox。 Docker Toolbox 的优势在于它可以在旧版本的 Windows 上运行,并且可以更轻松地模拟一些集群场景。 缺点是它在 Virtual Box 中运行 Linux 虚拟机,这会使用额外的资源,这意味着必须使用不同的 IP 地址而不是 localhost 来引用每个虚拟机。
对于 Linux,每个发行版都有独特的 Docker 安装方式,因此建议您访问 https://docs.docker.com/engine/installation/ 了解具体的安装说明。
在 Linux 上,您可以选择以 root 身份安装 Docker-Machine; 为此,请执行以下操作:
curl -L https://github.com/docker/machine/releases/download/v0.12.2/docker-machine-`uname -s`-`uname -m` >/tmp/docker-machine && chmod +x /tmp/docker-machine && sudo cp /tmp/docker-machine /usr/local/bin/docker-machine
运行容器
安装 Docker 后,您可以从命令行开始运行容器。 如果您还没有要运行的镜像,Docker 将自动从 Docker Hub 拉取或下载构建容器所需的镜像并运行它。
要运行简单的 hello-world 容器以确保一切配置正确,请运行以下命令:
docker run --rm hello-world
下载图像并运行容器后,此命令会打印“Hello from Docker!” 消息到标准输出,解释了显示消息所发生的所有步骤。 使用 –rm 选项还会自动删除容器并回收磁盘空间。
典型的本地工作流程
Docker 有一个典型的工作流程,使您能够创建镜像、拉取镜像、发布镜像和运行容器。
典型的 Docker 工作流程涉及从 Dockerfile 构建映像,其中包含有关如何配置容器或从 Docker Registry(例如 Docker Hub)中提取映像的说明。 使用 Docker 环境中的映像,您可以运行该映像,这将创建一个容器作为运行时环境,其中包含该映像所描述的操作系统、软件和配置。 例如,您的结果可能是 Debian 操作系统上运行 MySQL 5.5 版本的容器,该容器创建一个特定的数据库,其中包含您的 Web 应用程序所需的用户和表。 这些可运行的容器可以像启动和停止虚拟机或计算机一样启动和停止。 如果进行了手动配置或软件安装,则可以提交一个容器以创建一个新映像,该映像以后可用于从中创建容器。 最后,当您想与您的团队或全世界共享镜像时,您可以将镜像推送到 Docker 注册表。
从 Docker Registry 中拉取镜像
获取镜像的最简单方法是访问 https://hub.docker.com 并找到一个已经准备好的镜像来构建容器。 MySQL、Node.js、Java、Nginx、WordPress等常用软件的认证公众号有很多,但也有几十万张普通人创建的图片。 如果找到想要的镜像,比如mysql,执行pull命令下载镜像。
docker pull mysql
如果您还没有本地镜像,Docker 将从 Docker Hub 下载该镜像的最新版本并在本地缓存该镜像。 如果您不想要当前图像而是想要特定版本,您还可以使用标签来标识所需的版本。
docker pull mysql:8.0.2
如果您知道要在拉取图像后立即运行该图像,则只需使用运行命令即可保存一个步骤,它将自动在后台拉取它。
从 Dockerfile 构建映像
如果你找不到你需要的东西或者不信任你在 Docker Hub 上找到的镜像的来源,你总是可以通过创建一个 Dockerfile 来创建你自己的镜像。 Dockerfile 包含从现有映像继承的说明,然后您可以在其中添加软件或自定义配置。
以下是一个简单的示例,说明您可能在名为 Dockerfile 的文件中找到的内容:
FROM mysql:5.5.45 RUN echo America/New_York | tee /etc/timezone && dpkg-reconfigure --frontend noninteractive tzdata
此 Dockerfile 示例显示创建的映像将继承自经过认证的 mysql 存储库(特别是 5.5.45 版本的 MySQL)。 然后它运行 Linux 命令将时区更新为东部时间。
稍后将提供有关创建 Dockerfile 的更多详细信息。
要从包含 Dockerfile 的目录构建此映像,请运行以下命令:
docker build .
此命令将创建一个未命名的图像。 您可以通过运行列出图像的命令来查看它。
ocker images
这将显示所有本地缓存的图像,包括使用 build 命令创建的图像。
REPOSITORY TAG IMAGE ID VIRTUAL SIZE <none> <none> 4b9b8b27fb42 214.4 MB mysql 8.0.2 0da0b10c6fd8 213.5 MB
如您所见,构建命令创建了一个存储库名称和标记名称为 <none> 的映像。 这往往不是很有帮助,因此您可以使用 -t 选项来命名图像以便于使用:
docker build –t est-mysql .
再次列出图像,您可以看到图像更清晰。
REPOSITORY TAG IMAGE ID VIRTUAL SIZE est-mysql latest 4b9b8b27fb42 214.4 MB mysql 8.0.2 0da0b10c6fd8 213.5 MB
除了编写 Dockerfile 之外,还有一个创建自定义映像的替代选项。 您可以使用 bash 访问权限运行现有映像,然后通过安装软件或更改配置手动自定义映像。 完成后,您可以运行 docker commit 命令来创建正在运行的容器的映像。 与 Dockerfile 方法不同,这不被认为是最佳实践,因为它不可重复或自记录。
运行图像
要运行 Docker 镜像,您只需使用 docker run 命令,后跟本地镜像名称或在 Docker Hub 中找到的名称。 通常,一个 Docker 镜像需要一些额外的配置。 这通常使用环境变量来完成,可以使用 -e 选项指定。 对于像守护进程这样长时间运行的进程,您还需要使用 -d 选项。 要启动 est-mysql 映像,您将运行以下命令来配置 MySQL root 用户的密码和新数据库,如 Docker Hub mysql 存储库文档中所述:
docker run -d -e MYSQL_ROOT_PASSWORD=root+1 -e MYSQL_DATABASE=mydb est-mysql
要查看正在运行的容器,可以使用 Docker ps 命令:
docker ps
ps 命令列出所有正在运行的进程、创建它们的映像名称、运行的命令、软件正在侦听的任何端口以及容器的名称。
CONTAINER ID IMAGE COMMAND PORTS NAMES 30645f307114 est-mysql "/entrypoint.sh mysql" 3306/tcp serene_brahmagupta
从上面运行的进程可以看出,容器的名字是serene_brahmagupta。 这是一个自动生成的名称,可能难以维护。 因此,最好的做法是使用 –name 选项显式命名容器,以便在容器启动时提供您的名称:
docker run --name my-est-mysql -d -e MYSQL_ROOT_PASSWORD=root+1 -e MYSQL_DATABASE=mydb est-mysql
您会从 ps 输出中注意到容器正在侦听端口 3306,但这并不意味着您可以在本地使用 mysql 命令行或 MySQL Workbench 与数据库进行交互,因为该端口只能在安全的 Docker 环境中访问它推出了。 要使其在该环境之外可用,您必须使用 -p 选项映射端口。
docker run --name my-est-mysql -d -e MYSQL_ROOT_PASSWORD=root+1 -e MYSQL_DATABASE=mydb -p 3306:3306 -d est-mysql
现在 mysql 正在侦听您可以连接的端口。 但是您仍然必须知道要连接的 IP 地址。 如果您使用 Docker for Mac、Windows 或 Linux,它只是 localhost。 要确定 Docker Toolbox 的 IP 地址,可以使用 docker-machine ip 命令来确定。
docker-machine ip default
使用 default 作为机器名称,即随 Docker Toolbox 安装的默认机器,您将收到托管 docker 容器的机器的 IP 地址。
有了 IP 地址,您现在可以使用本地 mysql 命令行连接到 mysql。
mysql -h 192.168.99.100 -u root -proot+1
停止和启动容器
现在您已经运行了一个 Docker 容器,您可以使用 Docker stop 命令和容器名称来停止它:
docker stop my-est-mysql
容器的整个状态都会写入磁盘,因此如果您想以关闭时的状态再次运行它,可以使用 start 命令:
docker start my-est-mysql
网络容器
一个常见的用例是让一个容器中的应用程序与另一个容器中的服务通信,例如 Web 应用程序与数据库通信。 您可以通过在一个容器中使用 mysql 命令行与下图所示的另一个容器中的 MySQL 数据库进行通信来模拟这一点。
默认情况下,Docker 会自动为您创建 3 个网络。 您可以使用以下命令查看这些以及您创建的任何其他用户定义的网络:
docker network ls
为了使容器能够相互通信,您需要创建一个新的自定义网络。 这还将包括一个内部 DNS 服务器,因此 IP 地址可以解析为其容器名称。 要创建一个名为 mysql-network 的新网络,请使用以下命令:
docker network create mysql-network
如果您想将容器添加到该网络,例如已经运行的 my-est-mysql 容器,您可以通过运行以下网络连接命令将它们连接到网络:
docker network connect mysql-network my-est-mysql
或者,当您启动容器时,您可以使用 –network 选项传递网络名称,例如:
docker run --rm --network mysql-network -it mysql:8.0.2 bash
在上面的示例中,您启动了一个自动删除的新 MySQL 容器,并使用 it 选项将在容器中启动一个交互式终端。 network 选项将其添加到 mysql-network。 bash 是在此容器启动时运行并覆盖默认启动行为的应用程序。
现在在新启动的容器中,您只需运行以下命令即可连接到 my-est-mysql 容器中运行的 MySQL 数据库,其中 -h 是使用容器名称的主机。
mysql -h my-est-mysql -u root -p
映射卷
另一个常见的用例是在运行的容器和主机之间共享一个或多个目录。 这通常在容器包含数据库并且数据文件希望从主机持久化和备份时完成,或者在开发期间当开发人员想要在主机上使用他们的 IDE 但在完全配置的容器中运行他们的代码时完成。 这是通过使用 v 选项将主机目录映射到内部目录来完成的。
docker run --name my-est-mysql -d -v /my/host/datadir:/var/lib/msyql -e MYSQL_ROOT_PASSWORD=root+1 -e MYSQL_DATABASE=mydb -p 3306:3306 -d est-mysql
标记图像
既然您已经拥有了一个已运行并验证过的映像,那么在将其推送到存储库之前,最好使用用户名、映像名称和版本号对其进行标记。 您可以使用 Docker tag 命令完成此操作:
docker tag est-mysql javajudd/est-mysql:1.0
将图像推送到存储库
最后,您已准备好将您的映像推送到 Docker Hub 以供全世界使用或您的团队通过私有存储库使用。 首先,如果你还没有这样做,你需要去 https://hub.docker.com/ 创建一个免费帐户。 接下来,您需要使用 docker login 命令登录。
docker login
出现提示时,输入您注册时使用的用户名、密码和电子邮件地址。
现在使用 push 命令推送您的图像,指定您的用户名、图像名称和版本号。
docker push javajudd/est-mysql:1.0
一段时间后,您将收到一条消息,说明存储库已成功推送。 如果您重新登录 Docker Hub 帐户,您将看到新的存储库。
其他有用的命令
列出容器
您已经看到 docker ps 命令如何列出正在运行的容器,但是所有容器呢,不管它们的状态如何? 通过添加 –a 选项,您可以查看所有内容
docker ps -a
通过列出所有容器,您可以决定启动或删除哪些容器。
移除容器
当你使用完一个容器后,而不是让它到处乱放,你会想要移除它以回收磁盘空间。 要删除容器,可以使用 rm 命令:
docker rm my-est-mysql
删除图像
您已经看到了 images 命令如何列出所有本地缓存的图像。 这些图像可能会占用大量空间,从 1 兆字节到数百兆字节不等,因此您需要使用 rmi 命令清除不需要的图像:
docker rmi est-mysql
在创建新映像的调试周期中,您可能会生成大量不需要的和未命名的映像,这些映像以 <none> 的名称表示。 您可以使用以下命令轻松删除所有悬空图像:
docker rmi $(docker images -q -f dangling=true)
列出端口
了解容器公开了哪些端口通常很有帮助,例如用于访问 MySQL 数据库的端口 3306 或用于访问 Web 服务器的端口 80。 port 命令可用于显示暴露的端口。
docker port my-est-mysql
列出进程
如果需要查看容器中运行的进程,可以使用 top 命令(类似于运行 Linux top 命令):
docker top my-est-mysql
执行命令
您可以使用 exec 命令在正在运行的容器中执行命令。 例如,要列出硬盘驱动器根目录的内容,您可以执行以下操作:
docker exec my-est-mysql ls
如果您想以 root 身份 ssh 进入容器,可以运行等效的 exec 命令来访问 bash shell,并且由于 Docker 客户端和 Docker 守护程序之间的所有通信都已加密,因此它是安全的。
docker exec -it my-est-mysql bash
运行容器
run 命令是所有 Docker 命令中最复杂和最有特色的。 它可以用来做一些事情,比如管理网络设置; 管理系统资源,例如内存、CPU 和文件系统; 并配置安全性。 访问 https://docs.docker.com/reference/run/ 查看所有可用选项。
Dockerfile
如您所见,Dockerfile 是创建 Docker 映像的主要方式。 它包含诸如用于安装和配置软件的 Linux 命令之类的说明。 build 命令可以引用 PATH 上的 Dockerfile 或 URL,例如 GitHub 存储库。 与 Dockerfile 一起,同一目录或其子目录中的任何文件也将作为构建过程的一部分包含在内。 如果您希望构建包含要执行的脚本或其他必要的部署文件,这将很有帮助。
如果您希望排除任何文件或目录,您可以选择使用 .dockerignore 文件来实现此目的。
指示
指令按照它们在 Dockerfile 中的顺序执行。 Docker 文件还可以包含以 # 字符开头的行注释。
此表包含可用命令的列表。
操作说明 | 描述 |
---|---|
从 | 这必须是 Dockerfile 中的第一条指令,并标识要继承的映像。 |
维护者 | 为图像的作者提供可见性和信誉 |
跑步 | 执行用于配置和安装的 Linux 命令 |
入口点 | 用于引导容器的最终脚本或应用程序,使其成为可执行应用程序 |
命令 | 使用 JSON 数组格式向 ENTRYPOINT 提供默认参数 |
标签 | 关于图像的名称/值元数据 |
环境噪声 | 设置环境变量 |
复制 | 将文件复制到容器中 |
添加 | 替代复制 |
工作目录 | 为 RUN、CMD、ENTRYPOINT、COPY 和/或 ADD 指令设置工作目录 |
暴露 | 容器将侦听的端口 |
体积 | 创建挂载点 |
用户 | 用户运行 RUN、CMD 和/或 ENTRYPOINT 指令 |
Dockerfile 示例
这是官方 MySQL 5.5 Dockerfile 的示例,位于 https://github.com/docker-library/mysql/blob/5836bc9af9deb67b68c32bebad09a0f7513da36e/5.5/Dockerfile,它使用了许多可用的指令。
FROM debian:jessie RUN groupadd -r mysql && useradd -r -g mysql mysql RUN mkdir /docker-entrypoint-initdb.d RUN apt-get update && apt-get install -y perl --no-install-recommends && rm -rf /var/lib/apt/lists/* RUN apt-get update && apt-get install -y libaio1 && rm -rf /var/lib/apt/lists/* RUN gpg --keyserver ha.pool.sks-keyservers.net --recv-keys A4A9406876FCBD3C456770C88C718D3B5072E1F5 ENV MYSQL_MAJOR 5.5 ENV MYSQL_VERSION 5.5.45 RUN apt-get update && apt-get install -y curl --no-install-recommends && rm -rf /var/lib/apt/lists/* \ && curl -SL "http://dev.mysql.com/get/Downloads/MySQL-$MYSQL_MAJOR/mysql-$MYSQL_VERSION-linux2.6-x86_64.tar.gz" -o mysql.tar.gz \ && curl -SL "http://mysql.he.net/Downloads/MySQL-$MYSQL_MAJOR/mysql-$MYSQL_VERSION-linux2.6-x86_64.tar.gz.asc" -o mysql.tar.gz.asc \ && apt-get purge -y --auto-remove curl \ && gpg --verify mysql.tar.gz.asc \ && mkdir /usr/local/mysql \ && tar -xzf mysql.tar.gz -C /usr/local/mysql \ && rm mysql.tar.gz* \ && rm -rf /usr/local/mysql/mysql-test /usr/local/mysql/sql-bench \ && rm -rf /usr/local/mysql/bin/*-debug /usr/local/mysql/bin/*_embedded \ && find /usr/local/mysql -type f -name "*.a" -delete \ && apt-get update && apt-get install -y binutils && rm -rf /var/lib/apt/lists/* \ && { find /usr/local/mysql -type f -executable -exec strip --strip-all '{}' + || true; } \ && apt-get purge -y --auto-remove binutils ENV PATH $PATH:/usr/local/mysql/bin:/usr/local/mysql/scripts RUN mkdir -p /etc/mysql/conf.d \ && { \ echo '[mysqld]'; \ echo 'skip-host-cache'; \ echo 'skip-name-resolve'; \ echo 'user = mysql'; \ echo 'datadir = /var/lib/mysql'; \ echo '!includedir /etc/mysql/conf.d/'; \ } > /etc/mysql/my.cnf VOLUME /var/lib/mysql COPY docker-entrypoint.sh /entrypoint.sh ENTRYPOINT ["/entrypoint.sh"] EXPOSE 3306 CMD ["mysqld"]
此示例 Dockerfile 执行以下操作:
- 从名为“debian:jessie”的现有 Debian 映像扩展而来
- 使用 RUN 指令通过添加一些组、创建目录和使用 Debian apt-get 包管理器安装所需软件来配置映像
- 运行 gpg 以使用 PGP 设置一些加密
- 使用 ENV 指令定义此图中表示的 MySQL 的主要和次要版本
- 运行一长串命令来安装和配置系统,然后运行另一个环境变量来设置系统 PATH
- 使用 RUN 命令创建配置文件
- 使用 VOLUME 命令映射文件系统
- 使用 COPY 命令复制并重命名容器启动时将执行的脚本,然后使用 ENTRYPOINT 指定要执行的相同脚本
- 使用 EXPOSE 声明端口 3306 为要暴露的标准 MySQL 端口
- 使用 CMD 指定在容器启动时传递给 ENTRYPOINT 的命令行参数是字符串“mysqld”
码头机器
Docker Machine 是另一个用于管理一个或多个本地或远程机器的命令行实用程序。 本地机器通常在单独的 VirtualBox 实例中运行。 远程机器可以托管在云提供商上,例如 Amazon Web Services (AWS)、Digital Ocean 或 Microsoft Azure。
创建本地机器
安装 Docker Toolbox 时,您将获得一个名为“default”的默认 Docker 机器。 这很容易上手,但在某些时候,您可能需要多台机器来分割您正在运行的不同容器。 您可以使用 docker-machine create 命令执行此操作:
docker-machine create -d virtualbox qa
这将使用名为“qa”的 VirtualBox 映像创建一个新的本地计算机。
列出机器
如果需要查看自己配置了哪些机器,可以运行 docker-machine ls 命令:
docker-machine ls
启动和停止机器
可以使用 docker-machine start 命令启动 Docker 机器。
docker-machine start qa
机器启动后,您必须配置 Docker 命令行以确定它应该与哪个 Docker 守护进程交互。 您可以使用 docker-machine env 命令执行此操作并使用 eval 对其进行评估。
docker-machine env qa eval “$(docker-machine env qa)”
要停止机器,请使用 docker-machine stop 命令。
docker-machine stop qa
docker-machine start 和 stop 命令实际上是启动和停止 VirtualBox VM。 如果您打开了 VirtualBox Manager,您可以在运行命令时观察 VM 的状态变化。
企业码头工人
对于需要编排、高可用性、容错或只是简单复杂的大规模部署,已经有几种工具可以简化 Docker 的使用。
码头工人撰写(https://docs.docker.com/compose/) | 用于定义和运行多容器 Docker 应用程序的工具。 |
Docker Swarmkit (https://github.com/docker/swarmkit) | 用于大规模编排分布式 Docker 系统的工具包。 |
Kubernetes ( https://kubernetes.io/) | 一种工具生产级容器编排,提供自动化部署、扩展和管理。 |
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2303805254@qq.com,本站将立刻删除。