基本Docker

Docker一开始看起来很强大。然而,这些命令非常直观,只要稍加练习,你很快就会成为Docker向导。

Docker的语法可以分为四大类:

  • 运行容器
  • 管理和检查容器
  • 管理Docker镜像
  • Docker守护进程统计数据和信息

我们将在本任务中分解这些类别。

管理Docker镜像

Docker Pull

在运行Docker容器之前,我们首先需要一个镜像。回忆起“Intro to Containerisation集装箱化简介” 房间,图像是容器应该执行的指令。运行一个什么都不做的容器是没有用的!

器中运行Web服务器。在下载映像之前,让我们分解下载映像所需的命令和语法。可以使用 docker pull 命令并提供图像的名称。

比如说, docker pull nginx. Docker必须知道从哪里获取这个镜像(比如从一个我们将在后面的任务中提到的存储库)。

继续我们上面的例子,让我们下载这个Nginx镜像!

显示下载“Nginx”图像的终端

           cmnatic@thm:~$ docker pull nginx
Using default tag: latest
latest: Pulling from library/nginx
-- omitted for brevity --
Status: Downloaded newer image for nginx:latest
cmnatic@thm:~$

通过运行此命令,我们正在下载名为“nginx”的最新版本的图像。图像具有这些标签,称为 tags. 这些 tags 用于表示图像的变化。例如,图像可以具有相同的名称,但不同的标记表示不同的版本。我提供了一个如何在下表中使用标签的示例:

Docker镜像 TAG 命令示例 解释
Ubuntu 最新 docker pull ubuntu**- IS THE SAME AS -docker pull ubuntu:latest docker pull ubuntu-是什么-**docker pull ubuntu:latest 此命令将拉取最新版本的“ubuntu”镜像。如果没有指定标签,Docker会假设你想要的是“最新”版本。值得记住的是,你并不总是想要“最新的”。这个图像是相当字面上的“最新”的意义上,它将有最新的变化。这可能会修复或损坏您的容器。
ubuntu 22.04 docker pull ubuntu:22.04docker pull ubuntu:22.04 此命令将拉取“ubuntu”映像的“22.04(Jammy)”版本。
ubuntu 20.04 docker pull ubuntu:20.04Docker pull ubuntu:20.04 此命令将拉取“ubuntu”镜像的“20.04(Focal)”版本。
ubuntu 18.04 docker pull ubuntu:18.04 此命令将拉取“ubuntu”映像的“18.04(Bionic)”版本。

指定标记时,必须包含冒号 : 在图像名称和标签之间,例如, ubuntu:22.04 不要忘记标签-我们将在未来的任务中返回到这些!

Docker Image x/y/z

docker image
命令,以及适当的选项,允许我们管理本地系统上的映像。要列出可用的选项,我们可以简单地做 docker image
看看我们能做些什么我在下面的终端中为您做了这个:

一个终端,显示我们可以提供的各种参数“docker image”

           cmnatic@thm:~$ docker image

Usage: docker image COMMAND

Manage images

Commands:
build Build an image from a Dockerfile
history Show the history of an image
import Import the contents from a tarball to create a filesystem image
inspect Display detailed information on one or more images
load Load an image from a tar archive or STDIN
ls List images
prune Remove unused images
pull Pull an image or a repository from a registry
push Push an image or a repository to a registry
rm Remove one or more images
save Save one or more images to a tar archive (streamed to STDOUT by default)
tag Create a tag TARGET_IMAGE that refers to SOURCE_IMAGE

Run 'docker image COMMAND --help' for more information on a command.
cmnatic@thm:~$

  • 在这个房间里,我们只会介绍Docker镜像的以下选项:
    • pull (we have done this above!)pull(我们已经在上面做了!)
    • ls (list images)ls(列表图像)
    • rm (remove an image)
    • build (we will come onto this in the “Building your First Container” task)

Docker镜像ls

此命令允许我们列出本地系统上存储的所有图像。我们可以使用此命令来验证图像是否已正确下载,并查看有关它的更多信息(例如标记,图像创建时间和图像大小)。

列出存储在主机操作系统上的Docker镜像的终端

           cmnatic@thm:~$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
ubuntu 22.04 2dc39ba059dc 10 days ago 77.8MB
nginx latest 2b7d6430f78d 2 weeks ago 142MB
cmnatic@thm:~$

例如,在上面的终端中,我们可以看到系统上两个图像的一些信息:

Repository Tag Image ID Created Size
ubuntu 22.04 2dc39ba059dc 10 days ago 77.8MB
nginx latest 2b7d6430f78d 2 weeks ago 142MB

Docker镜像rm

如果我们想从系统中删除一个图像,我们可以使用 docker image rm 沿着名称(或映像ID)。在下面的示例中,我将删除“ubuntu“ image with the tag ““带标签的图像“22.04“. “.我的命令是 docker image rm ubuntu:22.04:

重要的是要记住, tag 图像名称。

一种显示对图像的取消标记的终端,

           cmnatic@thm:~$ docker image rm ubuntu:22.04
Untagged: ubuntu:22.04
Untagged: ubuntu@sha256:20fa2d7bb4de7723f542be5923b06c4d704370f0390e4ae9e1c833c8785644c1
Deleted: sha256:2dc39ba059dcd42ade30aae30147b5692777ba9ff0779a62ad93a74de02e3e1f
Deleted: sha256:7f5cbd8cc787c8d628630756bcc7240e6c96b876c2882e6fc980a8b60cdfa274
cmnatic@thm:~$

如果我们要运行一个 docker image ls, 我们将看到该图像不再列出:

确认我们的Docker镜像已被删除的终端

           cmnatic@thm:~$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest 2b7d6430f78d 2 weeks ago 142MB
cmnatic@thm:~$

运行您的第一个容器

Docker run命令从镜像创建运行容器。这是运行来自Dockerfile的命令(以及我们自己在运行时的输入)的地方。正因为如此,它必须是你学习的第一个语法。

该命令的工作方式如下:docker run [OPTIONS] IMAGE_NAME [COMMAND] [ARGUMENTS...] 括号中的选项不是容器运行所必需的。

Docker容器可以使用各种选项运行-这取决于我们如何使用容器。本任务将解释您可能要使用的一些最常见的选项。

首先,简单地运行一个容器

让我们回想一下运行Docker容器所需的语法: docker run [OPTIONS] IMAGE_NAME [COMMAND] [ARGUMENTS...]。在这个例子中,我将配置 容器运行:

  • 一个名为“helloworld”的图像
  • 通过在[OPTIONS]命令中提供-it开关实现“交互式”。这将允许我们直接与容器交互。
  • 我将通过提供/bin/bash作为[COMMAND]部分在容器中生成一个shell。这个参数是你放置你想要在容器中运行的命令的地方(比如文件,应用程序或者shell!)

因此,为了实现上述目标,我的命令将如下所示:docker run -it helloworld /bin/bash

一个终端显示一个集装箱在“交互”模式下被启动

           cmnatic@thm-intro-to-docker:~$ docker run -it helloworld /bin/bash
root@30eff5ed7492:/#

我们可以验证是否成功启动了shell,因为我们的提示符将更改为另一个用户帐户和主机名。容器的主机名是容器ID(可以使用docker ps找到)。例如,在上面的终端中,我们的用户名和主机名是root@30eff5ed7492

正在运行容器…继续

如前所述,Docker容器可以使用各种选项运行。容器的用途和Dockerfile中的指令集(我们将在后面的任务中讨论)决定了我们需要使用什么选项来运行容器。首先,我将一些运行Docker容器所需的最常见选项放入下表。

[OPTION] Explanation 相关Dockerfile说明 Example
-d- 这个参数告诉容器以“分离”模式启动。这意味着容器将在后台运行。 N/A docker run -d helloworld
-it 这个参数有两个部分。“i”表示交互运行,“t”告诉Docker在容器中运行shell。如果我们希望在容器运行后直接与它交互,我们将使用此选项。 N/A docker run -it helloworld
-v 这个参数是“Volume”的缩写,它告诉Docker将一个目录或文件从主机操作系统挂载到容器中的某个位置。这些文件的存储位置在Dockerfile中定义 VOLUME docker run -v /host/os/directory:/container/directory helloworld
-p 这个参数告诉Docker将主机操作系统上的端口绑定到容器中公开的端口。如果您正在容器中运行应用程序或服务(如Web服务器),并希望通过导航到IP地址来访问应用程序/服务,则可以使用此说明。 EXPOSE docker run -p 80:80 webserver
–rm 这个参数告诉Docker一旦容器完成运行它被指示做的任何事情,就删除容器。 N/A docker run --rm helloworld
–name 这个参数让我们为容器给予一个友好的、好记的名字。当一个容器在没有这个选项的情况下运行时,名称是两个随机的单词。我们可以使用这个open来命名一个容器,以该容器正在运行的应用程序命名。 N/A docker run --name helloworld

这些只是我们在运行容器时可以提供的一些参数。同样,我们需要运行的大多数参数将由容器的构建方式决定。但是,像--rm--name这样的参数将指示Docker如何运行容器。其他参数包括(但不限于!):

  • 告诉Docker容器应该使用哪个网络适配器
  • 容器应该访问哪些功能。这是在TryHackMe上的“Docker牛仔竞技表演“室中介绍的。
  • 将值存储到环境变量中

如果你想探索更多的这些论点,我强烈建议你阅读Docker run文档

列出正在运行的容器

要列出正在运行的容器,我们可以使用docker ps命令。此命令将列出当前正在运行的容器-如下所示:

一种显示运行中的容器及其信息的终端

           cmnatic@thm:~/intro-to-docker$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES

a913a8f6e30f cmnatic/helloworld:latest "sleep" 1 months ago Up 3 days 0.0.0.0:8000->8000/tcp helloworld
cmnatic@thm:~/intro-to-docker$

此命令还将显示有关容器的信息,包括:

  • 容器的ID
  • 容器正在运行什么命令
  • 容器是什么时候创建的
  • 容器运行多久了
  • 映射哪些端口
  • 容器的名称

提示:要列出所有容器(即使是停止的),您可以使用docker ps -a

显示所有集装箱及其信息列表的终端

           cmnatic@thm:~/intro-to-docker$ docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
00ba1eed0826 gobuster:cmnatic "./gobuster dir -url…" an hour ago Exited an hour ago practical_khayyam

Dockerfiles简介

Dockerfiles在Docker中扮演着重要的角色。Dockerfiles是一个格式化的文本文件,本质上是容器应该做什么的指导手册,并最终组装Docker镜像。

您使用Dockerfiles来包含容器在构建时应该执行的命令。要开始使用Dockerfiles,我们需要了解一些基本的语法和说明。Dockerfiles的格式如下:

INSTRUCTION argument

首先,让我们介绍一些基本的说明:

Instruction 指令 Description 描述 Example 例如
FROM 此指令为容器设置构建阶段以及设置基础映像(操作系统)。所有Dockerfiles都必须以这个开头。 FROM ubuntu
RUN 此指令将在新层的容器中执行命令。 RUN whoami
COPY 此指令将文件从本地系统复制到容器中的工作目录(语法类似于cp命令)。 COPY /home/cmnatic/myfolder/app/
WORKDIR 此指令设置容器的工作目录。(类似于在Linux上使用cd)。 WORKDIR / (sets to the root of the filesystem in the container)
CMD 此指令确定容器启动时运行的命令(您可以使用此命令启动服务或应用程序)。 CMD /bin/sh -c script.sh
EXPOSE .此指令用于告诉运行容器的人在运行容器时应该发布什么端口。 EXPOSE 80(告诉运行容器的人发布到端口80,即docker run -p 80:80

现在我们理解了组成Dockerfile的核心指令,让我们看一个Dockerfile的工作示例。但首先,我将解释我想要容器做什么:

  1. 使用“Ubuntu”(版本22.04)操作系统作为基础。
  2. 将工作目录设置为容器的根目录。
  3. 创建文本文件“helloworld.txt”。
# THIS IS A COMMENT
# Use Ubuntu 22.04 as the base operating system of the container
FROM ubuntu:22.04

# Set the working directory to the root of the container
WORKDIR /

# Create helloworld.txt
RUN touch helloworld.txt

请记住,您可以通过RUN指令运行的命令将取决于您在FROM指令中使用的操作系统。(In在这个例子中,我选择了Ubuntu。重要的是要记住,容器中使用的操作系统通常非常少。也就是说,don’t expect a command to be there from the start (even commands like 可能需要安装)。

构建您的第一个容器

一旦我们有了Dockerfile,我们就可以使用docker build命令创建一个镜像。此命令需要几条信息:

  1. 无论您是否想自己命名图像(我们将使用-t(标记)参数)。
  2. 您要为图像给予的名称。
  3. 您希望使用的Dockerfile的位置。

我将提供场景,然后解释相关的命令。假设我们想要构建一个图像-让我们填写上面列出的两条必需信息:

  1. 我们将自己命名它,所以我们将使用-t参数。
  2. 我们想给这个图像命名。
  3. Dockerfile位于我们当前的工作目录(.)。

我们要构建的Dockerfile如下:

# Use Ubuntu 22.04 as the base operating system of the container
FROM ubuntu:22.04

# Set the working directory to the root of the container
WORKDIR /

# Create helloworld.txt
RUN touch helloworld.txt

命令看起来像这样: docker build -t helloworld . 正在使用点来告诉Docker在我们的工作目录中查找)。如果我们正确填写了命令,我们将看到Docker开始构建镜像:

展示“helloworld”图像构建过程的终端

           cmnatic@thm:~$ docker build -t helloworld .
Sending build context to Docker daemon 4.778MB
Step 1/3 : FROM ubuntu:22.04
22.04: Pulling from library/ubuntu
2b55860d4c66: Pull complete
Digest: sha256:20fa2d7bb4de7723f542be5923b06c4d704370f0390e4ae9e1c833c8785644c1
Status: Downloaded newer image for ubuntu:22.04
---> 2dc39ba059dc
Step 2/3 : WORKDIR /
---> Running in 64d497097f8a
Removing intermediate container 64d497097f8a
---> d6bd1253fd4e
Step 3/3 : RUN touch helloworld.txt
---> Running in 54e94c9774be
Removing intermediate container 54e94c9774be
---> 4b11fc80fdd5
Successfully built 4b11fc80fdd5
Successfully tagged helloworld:latest
cmnatic@thm:~$

好极了!看上去很成功。让我们使用docker image ls来看看这个镜像是否已经构建好了:

使用“docker image ls”命令确认我们的镜像是否已经成功构建

           cmnatic@thm:~$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
helloworld latest 4b11fc80fdd5 2 minutes ago 77.8MB
ubuntu 22.04 2dc39ba059dc 10 days ago 77.8MB
cmnatic@thm:~$

Dockerfile中的指令也将被下载。这就是为什么我们可以看到两个图像:

  1. helloworld (our image)
  2. ubuntu(我们图像中使用的基本操作系统)。

您现在可以在容器中使用此映像。请参阅“运行您的第一个容器”任务以提醒您如何启动容器。

升级我们的Dockerfile

让我们升级我们的Dockerfile。到目前为止,我们的容器只会创建一个文件-这不是很有用!在下面的Dockerfile中,我将:

  1. 使用Ubuntu 22.04作为容器的基本操作系统。
  2. 安装“apache2”Web服务器。
  3. 增加一些网络。由于这是一个Web服务器,我们需要能够通过网络连接到容器。我将通过使用EXPOSE指令并告诉容器暴露端口80来实现这一点。
  4. 告诉容器在启动时启动“apache 2”服务。容器没有像systemd这样的服务管理器(这是设计的-在同一个容器中运行多个应用程序是不好的做法。例如,此容器用于apache 2 web服务器-并且仅用于apache 2 web服务器)。
# THIS IS A COMMENT
FROM ubuntu:22.04

# Update the APT repository to ensure we get the latest version of apache2
RUN apt-get update -y

# Install apache2
RUN apt-get install apache2 -y

# Tell the container to expose port 80 to allow us to connect to the web server
EXPOSE 80

# Tell the container to run the apache2 service
CMD ["apache2ctl", "-D","FOREGROUND"]

作为参考,构建此文件的命令是docker build -t webserver .(假设Dockerfile与您运行命令的目录相同)。一旦使用适当的选项(docker run -d --name webserver -p 80:80 webserver)启动容器,我们就可以在浏览器中导航到本地机器的IP地址!

The default landing page of apache2 which can be used to confirm that the service is running

WEB服务器工作!目前,Apache 2正在提供默认文件,因为我们还没有将自己的文件添加到容器中。

优化我们的Dockerfile

Docker当然是一门艺术-而且它不会停止于Dockerfiles!首先,我们需要问自己为什么优化我们的Dockerfile是必要的?臃肿的Dockerfiles很难阅读和维护,并且经常使用大量不必要的存储空间!例如,你可以减少Docker镜像的大小(并减少构建时间!)使用几种方法:

  1. 只安装必要的软件包。容器的好处在于,它们从一开始就几乎是空的–我们有完全的自由来决定我们想要什么。
  2. 删除缓存文件(如APT缓存或随工具安装的文档)。容器中的代码只执行一次(在构建时!),所以我们不需要储存任何东西以备后用。
  3. 在我们的FROM指令中使用最小的基本操作系统。尽管像Ubuntu这样的容器操作系统已经非常苗条了,但还是考虑使用更精简的版本(即ubuntu:22.04-minimal)。或者,例如,使用Alpine(可以小到5.59MB!)。
  4. 最小化层数-我将在下面进一步解释。

每个指令(即FROMRUN等)在自己的层中运行。层增加构建时间!目标是尽可能少的层。例如,尝试将来自RUN的命令链接在一起,如下所示:

Before:

FROM ubuntu:latest
RUN apt-get update -y
RUN apt-get upgrade -y
RUN apt-get install apache2 -y
RUN apt-get install net-tools -y

显示正在构建的Dockerfile的五个层的终端

           cmnatic@thm:~$ docker build -t before .
--omitted for brevity--
Step 2/5 : RUN apt-get update -y
---> Using cache
---> 446962612d20
Step 3/5 : RUN apt-get upgrade -y
---> Running in 8bed81c695f4
--omitted for brevity--
cmnatic@thm:~$

After:

FROM ubuntu:latest
RUN apt-get update -y && apt-get upgrade -y && apt-get install apache2 -y && apt-get install net-tools

显示正在构建的Dockerfile的两层的终端

           cmnatic@thm:~$ docker build -t after .
Sending build context to Docker daemon 4.78MB
Step 1/2 : FROM ubuntu
---> 2dc39ba059dc
Step 2/2 : RUN apt-get update -y && apt-get upgrade -y && apt-get install apache2 -y && apt-get install net-tools
---> Running in a4d4943bcf04
--omitted for brevity--
cmnatic@thm:~$

An illustration showing that the commands have been compressed into two layers.

请注意,现在只有两个构建步骤(这将是两个层,使构建更快)。这只是Dockerfile的一个小例子,所以构建时间不会那么激烈,但是在更大的Dockerfile中-减少层的数量将在构建过程中获得惊人的性能提升。

Docker Compose介绍

让我们首先了解Docker Compose是什么以及为什么它值得理解。到目前为止,我们只与单独的容器进行了交互。总之,Docker Compose允许多个容器(或应用程序)在需要时相互交互,同时彼此隔离运行。

到目前为止,你可能已经注意到Docker的一个问题。通常情况下,应用程序需要额外的服务才能运行,而我们无法在单个容器中完成这些工作。例如,现代动态网站使用诸如数据库和Web服务器之类的服务。为了完成这项任务,我们将把每个应用程序都视为一个“微服务”。

虽然我们可以单独启动多个容器或“微服务”并将它们连接起来,但一个接一个地这样做既麻烦又低效。Docker Compose允许我们将这些“微服务”创建为一个单一的“服务”。

此插图显示了如何使用Docker Compose与Docker一起部署容器:

A blue box (representing a computer) with a caption of docker, is isolated from another set of blue boxes (representing a computer).

在演示Docker Compose之前,让我们先介绍一下使用Docker Compose的基础知识。

  1. Docker Compose(默认情况下Docker不附带)。安装它超出了本会议室的范围,因为它会根据您的操作系统和其他因素而变化。您可以查看安装文档 here这里.
  2. 我们需要一个有效的docker-compose.yml文件-我们很快就会处理这个问题。
  3. 基本了解使用Docker Compose构建和管理容器。

我将一些基本的Docker Compose命令放入下表:

Command Explanation Example
up 此命令将(重新)创建/构建并启动组合文件中指定的容器。 docker-compose up docker run --rm helloworld
start 此命令将启动(但需要已构建的容器)组合文件中指定的容器。 docker-compose start
down 此命令将停止并删除在编写文件中指定的容器。 docker-compose down
stop 此命令将停止(而不是删除)组合文件中指定的容器。 docker-compose stop
build 此命令将构建(但不会启动)组合文件中指定的容器。 docker-compose build

注意:这些只是一些可能的命令。查看撰写文档了解所有可能的选项。*

Docker Compose展示

说到这里,让我们来看看如何使用Docker Compose。在这种情况下,我将假设以下要求:

  1. 在Apache上运行的电子商务网站
  2. 本电子商务网站将客户信息存储在MySQL数据库中

现在,我们可以通过以下方式手动运行两个容器:

  1. 在两个容器之间创建网络:docker network create ecommerce
  2. 运行Apache2 Web服务器容器:docker run -p 80:80 --name webserver --net ecommerce webserver
  3. 运行MySQL数据库服务器:docker run --name database --net ecommerce webserver

An illustration showing the two containers spun up using docker compose. Note that they are unable to communicate with one another

下图显示了两个容器彼此独立运行,并且无法相互通信。

但我们每次都要这样吗或者,如果我们决定扩大规模,让许多Web服务器参与进来呢?我们是否要对每个容器每次都这样做?我当然不知道

相反,我们可以通过docker-compose up使用Docker Compose来一起运行这些容器,这给我们带来了以下优势:

  1. 一个简单的命令来运行它们
  2. 这两个容器联网在一起,所以我们不需要配置网络。
  3. 非常便携。我们可以与其他人共享docker-compose.yml文件,他们可以让设置工作完全相同,而无需了解容器如何单独工作。
  4. 易于维护和更换。我们不必担心特定的容器使用(可能是过时的)图像。

img

显示作为组合服务部署的两个容器的插图。这两个容器可以相互通信。

Docker-compose.yml files 101

一个文件来管理所有文件。docker-compose.yml文件的格式与Dockerfile的格式不同。需要注意的是,YAML需要缩进(一个好的做法是两个空格必须一致!)。首先,在我们开始创建docker-compose.yml文件之前,我

Instruction Explanation Example
version 它位于文件的顶部,用于标识docker-compose.yml是为哪个版本的Compose编写的。 ‘3.3’
services 此指令标记要管理的容器的开始。 services:
name (replace value) 此指令是定义容器及其配置的地方。“name”需要替换为您要定义的容器的实际名称,即“webserver”或“database”。 webserver
build 此指令定义包含此容器/服务的Dockerfile的目录。(you将需要使用此或图像)。 ./webserver
ports 此指令将端口发布到暴露的端口(这取决于image/Dockerfile)。 ‘80:80’
volumes 此指令列出了应该从主机操作系统装入容器的目录。 ‘./home/cmnatic/webserver/:/var/www/html’’
environment 此指令用于传递环境变量(不安全),即密码,用户名,时区配置等。 MYSQL_ROOT_PASSWORD=helloworld
image .这个指令定义了容器应该使用什么镜像来构建(你需要使用this或者build)。 mysql:latest
networks 此指令定义容器将成为哪些网络的一部分。容器可以是多个网络的一部分(即Web服务器只能连接一个数据库,但数据库可以连接多个Web服务器)。 ecommerce

注意:这些只是一些可能的指令。查看compose文件文档以获取所有可能的说明。*

说到这里,让我们看看我们的第一个docker-compose.yml文件。这个docker-compose.yml文件假设如下:

  1. 我们将从前面提到的场景中运行一个Web服务器(名为Web)。
  2. 我们将从前面提到的场景中运行一个数据库服务器(命名为database)。
  3. Web服务器将使用其Dockerfile构建,但我们将使用已经构建的数据库服务器(MySQL)映像
  4. 集装箱将联网以相互通信(该网络称为电子商务)。
  5. 我们的目录列表如下所示:
  6. docker-compose.yml
  7. web/DockerfileWeb/Dockerfile

下面是我们的docker-compose.yml文件的样子(提醒一下,必须注意缩进):

version: '3.3'
services:
web:
build: ./web
networks:
- ecommerce
ports:
- '80:80'


database:
image: mysql:latest
networks:
- ecommerce
environment:
- MYSQL_DATABASE=ecommerce
- MYSQL_USERNAME=root
- MYSQL_ROOT_PASSWORD=helloword

networks:
ecommerce:

Docker Socket简介

本任务将解释Docker如何在操作系统和容器之间进行交互。当你安装Docker时,会安装两个程序:

  1. The Docker Client
  2. The Docker Server

Docker采用客户端/服务器模式。具体来说,这两个程序相互通信,形成了我们所熟悉和喜爱的Docker。Docker使用一种叫做socket的东西来实现这种通信。套接字是操作系统的一个基本特征,它允许数据进行通信。

例如,当使用聊天程序时,可能有两个套接字:

  1. 用于存储您要发送的消息的套接字
  2. 用于存储某人发送给您的消息的套接字。

程序将与这两个套接字交互以存储或检索其中的数据!套接字可以是网络连接或表示为文件的内容。关于套接字,重要的是要知道它们允许进程间通信(IPC)。这仅仅意味着操作系统上的进程可以相互通信!

在Docker的上下文中,Docker Server实际上只是一个API。Docker Server使用此API来侦听请求,而Docker Client使用API来发送请求。

例如,让我们使用这个命令:docker run helloworld。Docker客户端将请求Docker服务器运行一个使用镜像“helloworld”的容器。现在,虽然这个解释是相当基本的,但它是Docker如何工作的基本前提。

让我们看看下面的图表来展示这个过程的实际情况:

illustrating the flow of Docker interaction using the docker.sock file on the operating system

有趣的是,正因为如此,我们可以使用curl这样的命令或API开发人员工具(如Postman)与Docker Server交互。现在,使用这个超出了这个房间的范围,但我将演示使用Postman与Docker Server通信,以列出存储在操作系统上的所有映像:

the list of Docker images on an operating system captured using postman

最后,重要的是要注意,正因为如此,运行Docker的主机可以配置为处理从另一个设备发送的命令。如果没有正确配置,这是一个非常危险的漏洞,因为这意味着有人可以远程停止,启动和访问Docker容器。尽管如此,在一些用例中,Docker的这个功能非常有用!我们将在稍后的会议室中进一步详细介绍这一点!