多容器应用程序

解释

启动单容器应用程序很容易。例如,执行特定数据处理任务的Python脚本在其所有依赖项与容器内运行。同样,使用小型API端点的静态网站服务的Node.js应用程序可以使用其所有必要的库和依赖项有效地容器化。但是,随着应用程序规模的增长,将它们作为单个容器进行管理变得越来越困难。

想象一下,数据处理Python脚本需要连接到数据库。突然之间,您现在不仅要管理脚本,还要管理同一容器内的数据库服务器。如果脚本需要用户登录,则需要身份验证机制,这将进一步增加容器的大小。

容器的一个最佳实践是每个容器都应该做好一件事并且做好它。虽然此规则有例外,但应避免一个容器执行多项任务的趋势。

现在您可能会问:“我需要分别运行这些容器吗?如果我分别运行它们,我该如何将它们连接在一起?”

虽然`docker run`是启动容器的便捷工具,但使用它来管理不断增长的应用程序堆栈会变得很困难。原因如下:

  • 想象一下,运行多个`docker run`命令(前端、后端和数据库),并为开发、测试和生产环境配置不同的配置。这是容易出错且费时的。
  • 应用程序经常相互依赖。随着堆栈的扩展,以特定顺序手动启动容器和管理网络连接变得很困难。
  • 每个应用程序都需要其`docker run`命令,这使得难以扩展单个服务。扩展整个应用程序意味着可能在不需要提升的组件上浪费资源。
  • 持久化每个应用程序的数据需要在每个`docker run`命令中单独挂载卷或配置。这创建了一种分散的数据管理方法。
  • 通过单独的`docker run`命令为每个应用程序设置环境变量既繁琐又容易出错。

这就是Docker Compose发挥作用的地方。

Docker Compose 在名为`compose.yml`的单个YAML文件中定义您的整个多容器应用程序。此文件指定所有容器的配置、它们的依赖项、环境变量,甚至卷和网络。使用Docker Compose:

  • 您不需要运行多个`docker run`命令。您只需在一个YAML文件中定义您的整个多容器应用程序即可。这集中了配置并简化了管理。
  • 您可以按特定顺序运行容器并轻松管理网络连接。
  • 您可以简单地向上或向下扩展多容器设置中的单个服务。这允许根据实时需求进行有效的分配。
  • 您可以轻松实现持久卷。
  • 在Docker Compose文件中轻松设置环境变量。

通过利用Docker Compose运行多容器设置,您可以构建以模块化、可扩展性和一致性为核心的复杂应用程序。

试一试

在本实践指南中,您将首先了解如何使用`docker run`命令基于Node.js、Nginx反向代理和Redis数据库构建和运行计数器Web应用程序。您还将了解如何使用Docker Compose简化整个部署过程。

设置

  1. 获取示例应用程序。如果您有Git,您可以克隆示例应用程序的存储库。否则,您可以下载示例应用程序。选择以下选项之一。


    在终端中使用以下命令克隆示例应用程序存储库。

    $ git clone https://github.com/dockersamples/nginx-node-redis
    

    导航到`nginx-node-redis`目录

    $ cd nginx-node-redis
    

    在此目录中,您将找到两个子目录——`nginx`和`web`。

    下载源代码并解压。

    导航到`nginx-node-redis-main`目录

    $ cd nginx-node-redis-main
    

    在此目录中,您将找到两个子目录——`nginx`和`web`。


  2. 下载并安装 Docker Desktop。

构建镜像

  1. 导航到`nginx`目录,通过运行以下命令构建镜像

    $ docker build -t nginx .
    
  2. 导航到`web`目录,并运行以下命令来构建第一个web镜像

    $ docker build -t web .
    

运行容器

  1. 在运行多容器应用程序之前,您需要为它们创建网络以便它们都可以通过该网络进行通信。您可以使用`docker network create`命令来执行此操作

    $ docker network create sample-app
    
  2. 通过运行以下命令启动Redis容器,这会将它附加到先前创建的网络并创建一个网络别名(对DNS查找很有用)

    $ docker run -d  --name redis --network sample-app --network-alias redis redis
    
  3. 通过运行以下命令启动第一个web容器

    $ docker run -d --name web1 -h web1 --network sample-app --network-alias web1 web
    
  4. 运行以下命令启动第二个web容器

    $ docker run -d --name web2 -h web2 --network sample-app --network-alias web2 web
    
  5. 通过运行以下命令启动Nginx容器

    $ docker run -d --name nginx --network sample-app  -p 80:80 nginx
    

    注意

    Nginx通常用作Web应用程序的反向代理,将流量路由到后端服务器。在这种情况下,它会路由到Node.js后端容器(web1或web2)。

  6. 通过运行以下命令验证容器是否已启动

    $ docker ps
    

    您将看到如下输出

    CONTAINER ID   IMAGE     COMMAND                  CREATED              STATUS              PORTS                NAMES
    2cf7c484c144   nginx     "/docker-entrypoint.…"   9 seconds ago        Up 8 seconds        0.0.0.0:80->80/tcp   nginx
    7a070c9ffeaa   web       "docker-entrypoint.s…"   19 seconds ago       Up 18 seconds                            web2
    6dc6d4e60aaf   web       "docker-entrypoint.s…"   34 seconds ago       Up 33 seconds                            web1
    008e0ecf4f36   redis     "docker-entrypoint.s…"   About a minute ago   Up About a minute   6379/tcp             redis
  7. 如果您查看Docker Desktop仪表板,您可以看到容器并更深入地了解其配置。

    A screenshot of the Docker Desktop Dashboard showing multi-container applications
  8. 在一切启动并运行后,您可以打开http://localhost 在您的浏览器中查看站点。刷新页面几次以查看处理请求的主机和请求总数。

    web2: Number of visits is: 9
    web1: Number of visits is: 10
    web2: Number of visits is: 11
    web1: Number of visits is: 12
    

    注意

    您可能已经注意到,Nginx充当反向代理,可能以轮询方式在两个后端容器之间分配传入请求。这意味着每个请求都可能被定向到不同的容器(web1和web2)进行轮换。输出显示web1和web2容器的连续增量,并且只有在将响应发送回客户端后才会更新存储在Redis中的实际计数器值。

  9. 您可以使用Docker Desktop仪表板通过选择容器并选择“删除”按钮来删除容器。

    A screenshot of Docker Desktop Dashboard showing how to delete the multi-container applications

使用Docker Compose简化部署

Docker Compose 提供了一种结构化且简化的方式来管理多容器部署。如前所述,使用 Docker Compose,您无需运行多个docker run命令。您只需在一个名为compose.yml的 YAML 文件中定义您的整个多容器应用程序即可。让我们看看它是如何工作的。

导航到项目根目录。在这个目录中,您会找到一个名为compose.yml的文件。这个 YAML 文件就是所有神奇之处发生的地方。它定义了构成您应用程序的所有服务及其配置。每个服务都指定其镜像、端口、卷、网络以及其功能所需的任何其他设置。

  1. 使用docker compose up命令启动应用程序。

    $ docker compose up -d --build
    

    运行此命令时,您应该会看到类似于以下内容的输出。

    Running 5/5
    ✔ Network nginx-nodejs-redis_default    Created                                                0.0s
    ✔ Container nginx-nodejs-redis-web1-1   Started                                                0.1s
    ✔ Container nginx-nodejs-redis-redis-1  Started                                                0.1s
    ✔ Container nginx-nodejs-redis-web2-1   Started                                                0.1s
    ✔ Container nginx-nodejs-redis-nginx-1  Started
    
  2. 如果您查看Docker Desktop仪表板,您可以看到容器并更深入地了解其配置。

    A screenshot of the Docker Desktop Dashboard showing the containers of the application stack deployed using Docker Compose
  3. 或者,您可以使用 Docker Desktop Dashboard 通过选择应用程序堆栈并选择**删除**按钮来删除容器。

    A screenshot of Docker Desktop Dashboard that shows how to remove the containers that you deployed using Docker Compose

在本指南中,您学习了与易于出错且难以管理的docker run相比,使用 Docker Compose 启动和停止多容器应用程序是多么容易。

附加资源