如何访问 Docker 容器中运行的 Web 应用程序

DockerBeginner
立即练习

简介

本教程将指导你访问在 Docker 容器中运行的 Web 应用程序的过程。你将学习 Docker 容器的基础知识,部署一个简单的 Web 应用程序,并了解如何从你的宿主机访问它。这些知识对于使用 Docker 开发和测试 Web 应用程序至关重要。

理解 Docker 并运行一个测试容器

Docker 是一个使用容器化来打包应用程序及其依赖项的平台。这使得应用程序能够在不同的环境中一致地运行。

验证 Docker 安装

首先,让我们检查 Docker 是否已正确安装在你的系统上:

docker --version

你应该看到类似这样的输出,显示 Docker 的版本:

Docker version 20.10.21, build baeda1f

理解 Docker 镜像和容器

在 Docker 术语中:

  • Docker 镜像(Docker image) 是一个模板,包含应用程序代码、库和依赖项
  • Docker 容器(Docker container) 是镜像的运行实例

可以将 Docker 镜像想象成蓝图,而 Docker 容器是根据该蓝图创建的建筑物。

运行你的第一个 Docker 容器

让我们运行一个简单的容器来验证 Docker 是否正常工作:

docker run hello-world

你应该看到类似这样的输出:

Hello from Docker!
This message shows that your installation appears to be working correctly.

To generate this message, Docker took the following steps:
 1. The Docker client contacted the Docker daemon.
 2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
 3. The Docker daemon created a new container from that image which runs the
    executable that produces the output you are currently reading.
 4. The Docker daemon streamed that output to the Docker client, which sent it
    to your terminal.
...

这确认了 Docker 在你的系统上正常工作。

基本 Docker 命令

以下是一些你应该知道的基本 Docker 命令:

  1. 列出所有正在运行的容器:
docker ps
  1. 列出所有容器(包括已停止的容器):
docker ps -a
  1. 列出你系统上的所有 Docker 镜像:
docker images

尝试这些命令并观察输出。在运行 hello-world 容器后,当你运行 docker ps -a 时,你应该会看到它被列出(但在 docker ps 中不会,因为它在显示消息后立即退出)。

创建一个简单的 Web 应用程序

在这一步中,我们将使用 Python 和 Flask 创建一个简单的 Web 应用程序,该应用程序可以在 Docker 容器中部署。

设置应用程序文件

首先,让我们为我们的 Web 应用程序创建一个新目录:

mkdir -p ~/project/my-web-app
cd ~/project/my-web-app

现在,让我们创建一个简单的 Flask 应用程序。使用 nano 编辑器创建一个名为 app.py 的文件:

nano app.py

将以下 Python 代码添加到文件中:

from flask import Flask

app = Flask(__name__)

@app.route('/')
def hello():
    return "<h1>Hello from Docker!</h1><p>This is a simple web application running in a Docker container.</p>"

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000)

Ctrl+O,然后按 Enter 保存文件,再按 Ctrl+X 退出 nano。

接下来,创建一个 requirements.txt 文件来指定我们应用程序的依赖项:

nano requirements.txt

将以下行添加到文件中:

flask==2.0.1

Ctrl+O,然后按 Enter 保存文件,再按 Ctrl+X 退出 nano。

创建一个 Dockerfile

现在,让我们创建一个 Dockerfile 来定义我们的应用程序应该如何被容器化:

nano Dockerfile

将以下内容添加到文件中:

FROM python:3.9-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY app.py .
EXPOSE 5000
CMD ["python", "app.py"]

这个 Dockerfile 执行以下操作:

  1. 使用轻量级的 Python 3.9 镜像作为基础
  2. 将工作目录设置为 /app
  3. 复制 requirements 文件并安装依赖项
  4. 复制应用程序代码
  5. 暴露端口 5000 以供传入连接
  6. 指定容器启动时要运行的命令

Ctrl+O,然后按 Enter 保存文件,再按 Ctrl+X 退出 nano。

构建 Docker 镜像

现在,让我们从我们的 Dockerfile 构建一个 Docker 镜像:

docker build -t my-flask-app .

-t 标志使用名称 my-flask-app 标记我们的镜像。末尾的 . 指定 Dockerfile 位于当前目录中。

你应该看到类似这样的输出:

Sending build context to Docker daemon  x.xxxkB
Step 1/6 : FROM python:3.9-slim
 ---> xxxxxxxxxx
Step 2/6 : WORKDIR /app
 ---> Using cache
 ---> xxxxxxxxxx
...
Successfully built xxxxxxxxxx
Successfully tagged my-flask-app:latest

现在,检查你的镜像是否已创建:

docker images | grep my-flask-app

你应该在列表中看到你新创建的镜像。

在 Docker 容器中运行 Web 应用程序

现在我们已经构建了 Docker 镜像,让我们将其作为容器运行并访问 Web 应用程序。

运行容器

要运行容器并映射端口以便我们可以访问 Web 应用程序,请使用以下命令:

docker run -d -p 5000:5000 --name my-web-container my-flask-app

此命令执行以下操作:

  • -d:在分离模式(后台)运行容器
  • -p 5000:5000:将容器的端口 5000 映射到主机的端口 5000
  • --name my-web-container:为容器分配一个名称
  • my-flask-app:指定要使用的镜像

验证容器是否正在运行

让我们检查一下我们的容器是否正在运行:

docker ps

你应该看到类似这样的输出:

CONTAINER ID   IMAGE          COMMAND           CREATED          STATUS          PORTS                    NAMES
xxxxxxxxxxxx   my-flask-app   "python app.py"   xx seconds ago   Up xx seconds   0.0.0.0:5000->5000/tcp   my-web-container

访问 Web 应用程序

现在,你可以通过两种方式访问 Web 应用程序:

  1. 使用命令行中的 curl:
curl http://localhost:5000

你应该看到 HTML 响应:

<h1>Hello from Docker!</h1><p>This is a simple web application running in a Docker container.</p>
  1. 使用 Web 浏览器:
    • 单击桌面环境中的 Web 浏览器图标
    • 在地址栏中输入 http://localhost:5000
    • 你应该看到 "Hello from Docker!" 后面跟着描述文本

理解端口映射

当我们使用 -p 5000:5000 运行容器时,我们正在创建以下映射:

  • 主机端口(第一个数字):5000
  • 容器端口(第二个数字):5000

这意味着发送到主机上端口 5000 的任何流量都将被转发到容器内的端口 5000。

我们也可以使用不同的端口号。例如,-p 8080:5000 将把主机端口 8080 映射到容器端口 5000,允许你通过 http://localhost:8080 访问该应用程序。

检查容器日志

如果你需要查看来自容器的日志(这对于调试很有帮助),请使用:

docker logs my-web-container

你应该看到 Flask 应用程序的启动消息。

停止和删除容器

要停止容器,请使用:

docker stop my-web-container

要删除已停止的容器,请使用:

docker rm my-web-container

你也可以在一个命令中停止和删除容器:

docker rm -f my-web-container

这在开发过程中很有用,当你想要快速重建和重新运行你的容器时。

高级 Docker 容器管理

现在你已经成功地在 Docker 容器中运行了你的 Web 应用程序,让我们探索一些用于管理 Docker 容器的附加功能和技术。

运行多个实例

你可以在不同的端口上运行你的 Web 应用程序的多个实例。这对于测试或同时运行不同版本的应用程序很有用。

首先,让我们停止并删除之前的容器:

docker rm -f my-web-container

现在,让我们在不同的端口上运行两个 Web 应用程序的实例:

docker run -d -p 5000:5000 --name web-app-1 my-flask-app
docker run -d -p 5001:5000 --name web-app-2 my-flask-app

验证两个容器是否都在运行:

docker ps

你应该看到两个正在运行的容器:

CONTAINER ID   IMAGE          COMMAND           CREATED          STATUS          PORTS                    NAMES
xxxxxxxxxxxx   my-flask-app   "python app.py"   xx seconds ago   Up xx seconds   0.0.0.0:5001->5000/tcp   web-app-2
xxxxxxxxxxxx   my-flask-app   "python app.py"   xx seconds ago   Up xx seconds   0.0.0.0:5000->5000/tcp   web-app-1

现在你可以在两个不同的端口上访问相同的应用程序:

容器资源限制

Docker 允许你为你的容器设置资源限制。这对于防止容器消耗过多的系统资源很有用。

让我们停止并删除之前的容器:

docker rm -f web-app-1 web-app-2

现在,让我们运行一个具有内存和 CPU 限制的容器:

docker run -d -p 5000:5000 --name limited-container --memory=512m --cpus=0.5 my-flask-app

此命令创建一个容器,具有:

  • 最大 512MB 的内存
  • 最大 0.5 个 CPU 核心

验证容器是否正在运行:

docker ps

容器环境变量

环境变量是在 Docker 容器中配置应用程序的常用方法。让我们修改我们的 Flask 应用程序以使用环境变量:

docker rm -f limited-container

创建新版本的 app.py 文件:

cd ~/project/my-web-app
nano app_env.py

添加以下代码:

import os
from flask import Flask

app = Flask(__name__)

@app.route('/')
def hello():
    app_name = os.environ.get('APP_NAME', 'Default App')
    return f"<h1>Hello from {app_name}!</h1><p>This is a simple web application running in a Docker container.</p>"

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000)

Ctrl+O,然后按 Enter 保存文件,再按 Ctrl+X 退出 nano。

创建一个新的 Dockerfile:

nano Dockerfile-env

添加以下内容:

FROM python:3.9-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY app_env.py ./app.py
EXPOSE 5000
CMD ["python", "app.py"]

Ctrl+O,然后按 Enter 保存文件,再按 Ctrl+X 退出 nano。

构建一个新镜像:

docker build -t my-flask-app-env -f Dockerfile-env .

现在,使用环境变量运行容器:

docker run -d -p 5000:5000 --name env-container -e APP_NAME="Customized App" my-flask-app-env

访问 Web 应用程序:

curl http://localhost:5000

你应该看到:

<h1>Hello from Customized App!</h1><p>This is a simple web application running in a Docker container.</p>

这演示了如何使用环境变量将配置传递给你的容器化应用程序。

总结

在这个实验中,你学习了如何访问在 Docker 容器中运行的 Web 应用程序。你创建了一个简单的 Flask Web 应用程序,使用 Docker 对其进行容器化,并使用端口映射从你的主机访问它。

涵盖的关键概念:

  • 理解 Docker 镜像和容器
  • 使用 Flask 创建一个简单的 Web 应用程序
  • 使用 Dockerfile 构建 Docker 镜像
  • 运行和访问容器化的 Web 应用程序
  • 使用各种命令管理 Docker 容器
  • 在不同的端口上运行多个容器实例
  • 为容器设置资源限制
  • 使用环境变量进行容器配置

这些技能为使用容器化应用程序提供了坚实的基础,并将帮助你使用 Docker 高效地部署和测试 Web 应用程序。