在 Docker 中运行 Airflow

本快速入门指南将允许您快速启动并运行使用 Docker 中的 CeleryExecutor 的 Airflow。

注意

此过程对于学习和探索很有用。但是,将其调整为在实际情况中使用可能很复杂,并且 docker-compose 文件不提供生产系统所需的任何安全保证。对此过程进行更改将需要 Docker 和 Docker Compose 的专业知识,并且 Airflow 社区可能无法为您提供帮助。

因此,当您准备在生产环境中运行 Airflow 时,我们建议使用 Kubernetes 和 官方 Airflow 社区 Helm Chart

开始之前

此过程假设您熟悉 Docker 和 Docker Compose。如果您之前没有使用过这些工具,您应该花点时间浏览 Docker 快速入门 (特别是关于 Docker Compose 的部分),以便您熟悉它们的工作原理。

如果您尚未安装必要的工具,请按照以下步骤进行安装。

  1. 在您的工作站上安装 Docker Community Edition (CE)。根据您的操作系统,您可能需要将 Docker 配置为至少使用 4.00 GB 的内存才能使 Airflow 容器正常运行。有关更多信息,请参阅 Docker for WindowsDocker for Mac 文档的资源部分。

  2. 在您的工作站上安装 Docker Compose v2.14.0 或更高版本。

较旧版本的 docker-compose 不支持 Airflow docker-compose.yaml 文件所需的所有功能,因此请仔细检查您的版本是否满足最低版本要求。

提示

macOS 上 Docker 的默认可用内存量通常不足以启动并运行 Airflow。如果未分配足够的内存,可能会导致 Web 服务器不断重启。您应该为 Docker Engine 分配至少 4GB 的内存(理想情况下为 8GB)。

您可以通过运行此命令来检查您是否有足够的内存

docker run --rm "debian:bookworm-slim" bash -c 'numfmt --to iec $(echo $(($(getconf _PHYS_PAGES) * $(getconf PAGE_SIZE))))'

警告

某些操作系统(Fedora、ArchLinux、RHEL、Rocky)最近引入了内核更改,导致在 OS 团队维护的社区 Docker 实现中运行时,Docker Compose 中的 Airflow 消耗 100% 的内存。

这是由于一些 Airflow 依赖项存在问题的向后不兼容的 containerd 配置问题,并在一些问题中被跟踪

containerd 团队尚未提供解决方案,但似乎安装 Linux 上的 Docker Desktop 可以解决 此评论 中所述的问题,并且可以毫无问题地运行 Breeze。

获取 docker-compose.yaml

要在 Docker Compose 上部署 Airflow,您应该获取 docker-compose.yaml

curl -LfO 'https://airflow.apache.org/docs/apache-airflow/2.10.4/docker-compose.yaml'

重要

自 2023 年 7 月起,Compose V1 停止接收更新。我们强烈建议升级到较新版本的 Docker Compose,提供的 docker-compose.yaml 可能无法在 Compose V1 中准确运行。

此文件包含多个服务定义

  • airflow-scheduler - 调度器 监视所有任务和 DAG,然后在它们的依赖项完成后触发任务实例。

  • airflow-webserver - Web 服务器在 https://127.0.0.1:8080 上可用。

  • airflow-worker - 执行调度器给出的任务的 worker。

  • airflow-triggerer - 触发器为可延迟任务运行事件循环。

  • airflow-init - 初始化服务。

  • postgres - 数据库。

  • redis - Redis - 将消息从调度器转发到 worker 的代理。

(可选)您可以通过添加 --profile flower 选项来启用 flower,例如 docker compose --profile flower up,或者在命令行中显式指定它,例如 docker compose up flower

所有这些服务允许您使用 CeleryExecutor 运行 Airflow。有关更多信息,请参阅 架构概述

容器中的某些目录是挂载的,这意味着它们的内容在您的计算机和容器之间同步。

  • ./dags - 您可以将您的 DAG 文件放在这里。

  • ./logs - 包含任务执行和调度器的日志。

  • ./config - 您可以添加自定义日志解析器或添加 airflow_local_settings.py 来配置集群策略。

  • ./plugins - 您可以将您的 自定义插件 放在这里。

此文件使用最新的 Airflow 镜像 (apache/airflow)。如果您需要安装新的 Python 库或系统库,您可以 构建您的镜像

初始化环境

在第一次启动 Airflow 之前,您需要准备您的环境,即创建必要的文件、目录并初始化数据库。

设置正确的 Airflow 用户

在 **Linux** 上,快速入门需要知道您的主机用户 ID,并且需要将组 ID 设置为 0。否则,在 dagslogsplugins 中创建的文件将以 root 用户所有权创建。您必须确保为 docker-compose 配置它们

mkdir -p ./dags ./logs ./plugins ./config
echo -e "AIRFLOW_UID=$(id -u)" > .env

请参阅 Docker Compose 环境变量

对于其他操作系统,您可能会收到 AIRFLOW_UID 未设置的警告,但您可以安全地忽略它。您还可以在与 docker-compose.yaml 相同的文件夹中手动创建一个 .env 文件,其中包含此内容,以消除警告

AIRFLOW_UID=50000

初始化数据库

在**所有操作系统**上,您需要运行数据库迁移并创建第一个用户帐户。为此,请运行。

docker compose up airflow-init

初始化完成后,您应该会看到如下消息

airflow-init_1       | Upgrades done
airflow-init_1       | Admin user airflow created
airflow-init_1       | 2.10.4
start_airflow-init_1 exited with code 0

创建的帐户的登录名为 airflow,密码为 airflow

清理环境

我们准备的 docker-compose 环境是一个“快速入门”环境。它不是为在生产环境中使用而设计的,并且存在一些注意事项 - 其中之一就是解决任何问题的最佳方法是清理它并从头开始重新启动。

最好的方法是:

  • 在您下载 docker-compose.yaml 文件的目录中运行 docker compose down --volumes --remove-orphans 命令。

  • 删除您下载 docker-compose.yaml 文件的整个目录 rm -rf '<DIRECTORY>'

  • 从头开始,重新下载 docker-compose.yaml 文件,按照本指南进行操作。

运行 Airflow

现在您可以启动所有服务。

docker compose up

注意

docker-compose 是旧语法。请查看 Stackoverflow

在第二个终端中,您可以检查容器的状态,并确保没有容器处于不健康状态。

$ docker ps
CONTAINER ID   IMAGE                   COMMAND                  CREATED          STATUS                    PORTS                              NAMES
247ebe6cf87a   apache/airflow:2.10.4   "/usr/bin/dumb-init …"   3 minutes ago    Up 3 minutes (healthy)    8080/tcp                           compose_airflow-worker_1
ed9b09fc84b1   apache/airflow:2.10.4   "/usr/bin/dumb-init …"   3 minutes ago    Up 3 minutes (healthy)    8080/tcp                           compose_airflow-scheduler_1
7cb1fb603a98   apache/airflow:2.10.4   "/usr/bin/dumb-init …"   3 minutes ago    Up 3 minutes (healthy)    0.0.0.0:8080->8080/tcp             compose_airflow-webserver_1
74f3bbe506eb   postgres:13             "docker-entrypoint.s…"   18 minutes ago   Up 17 minutes (healthy)   5432/tcp                           compose_postgres_1
0bd6576d23cb   redis:latest            "docker-entrypoint.s…"   10 hours ago     Up 17 minutes (healthy)   0.0.0.0:6379->6379/tcp             compose_redis_1

访问环境

启动 Airflow 后,您可以通过 3 种方式与其交互:

运行 CLI 命令

您还可以运行 CLI 命令,但您必须在定义的 airflow-* 服务之一中执行此操作。例如,要运行 airflow info,请运行以下命令:

docker compose run airflow-worker airflow info

如果您有 Linux 或 Mac OS,您可以使您的工作更轻松,并下载一个可选的包装器脚本,该脚本将允许您使用更简单的命令运行命令。

curl -LfO 'https://airflow.apache.org/docs/apache-airflow/2.10.4/airflow.sh'
chmod +x airflow.sh

现在您可以更轻松地运行命令了。

./airflow.sh info

您还可以使用 bash 作为参数,在容器中输入交互式 bash shell,或者使用 python 进入 python 容器。

./airflow.sh bash
./airflow.sh python

访问 Web 界面

集群启动后,您可以登录到 Web 界面并开始尝试 DAG。

Web 服务器地址为:https://127.0.0.1:8080。默认帐户的登录名为 airflow,密码为 airflow

向 REST API 发送请求

REST API 当前支持 基本用户名密码身份验证,这意味着您可以使用常用工具向 API 发送请求。

Web 服务器地址为:https://127.0.0.1:8080。默认帐户的登录名为 airflow,密码为 airflow

这是一个示例 curl 命令,它发送一个请求以检索池列表。

ENDPOINT_URL="https://127.0.0.1:8080/"
curl -X GET  \
    --user "airflow:airflow" \
    "${ENDPOINT_URL}/api/v1/pools"

清理

要停止并删除容器,删除包含数据库数据的卷并下载镜像,请运行:

docker compose down --volumes --rmi all

使用自定义镜像

当您想在本地运行 Airflow 时,您可能需要使用扩展的镜像,其中包含一些额外的依赖项 - 例如,您可能添加新的 python 包,或将 airflow providers 升级到更高版本。这可以通过在 docker-compose.yaml 中指定 build: . 并将自定义 Dockerfile 与您的 docker-compose.yaml 放在一起,非常容易地完成。然后,您可以使用 docker compose build 命令来构建您的镜像(您只需要执行一次)。您还可以将 --build 标志添加到您的 docker compose 命令中,以便在您运行其他 docker compose 命令时动态重建镜像。

有关如何使用自定义 providers、python 包、apt 包等扩展镜像的示例,请参见 构建镜像

注意

创建自定义镜像意味着您还需要维护一定程度的自动化,因为当您要安装的软件包或 Airflow 升级时,您需要重新创建镜像。请不要忘记保留这些脚本。还要记住,在运行纯 Python 任务时,您可以使用 Python Virtualenv 函数,它将在运行时动态地获取和安装 python 依赖项。在 Airflow 2.8.0 中,Virtualenvs 也可以缓存。

特殊情况 - 通过 requirements.txt 文件添加依赖项

自定义镜像的常见情况是,当您要向其中添加一组需求时 - 通常存储在 requirements.txt 文件中。对于开发,您可能希望在启动原始 airflow 镜像时动态添加它,但这会产生一些副作用(例如,您的容器启动速度会慢得多 - 每个额外的依赖项都会进一步延迟容器的启动时间)。此外,这是完全没有必要的,因为 docker compose 内置了开发工作流程。当您在本地使用 docker compose 进行迭代时,您可以 - 按照上一章所述,自动构建和使用您的自定义镜像。具体来说,当您要添加自己的需求文件时,您应该执行以下步骤:

  1. 注释掉 image: ... 行,并删除 docker-compose.yaml 文件中 build: . 行的注释。您的 docker-compose 文件的相关部分应类似于(使用正确的镜像标签):

#image: ${AIRFLOW_IMAGE_NAME:-apache/airflow:2.10.4}
build: .
  1. 在您的 docker-compose.yaml 文件所在的同一文件夹中创建 Dockerfile,其内容类似于:

FROM apache/airflow:2.10.4
ADD requirements.txt .
RUN pip install apache-airflow==${AIRFLOW_VERSION} -r requirements.txt

最佳实践是以与原始镜像相同的版本安装 apache-airflow。这样,您可以确保 pip 在安装其他需求时不会尝试降级或升级 apache airflow,如果您尝试添加与您正在使用的 apache-airflow 版本冲突的依赖项,则可能会发生这种情况。

  1. requirements.txt 文件放在同一目录中。

运行 docker compose build 来构建镜像,或将 --build 标志添加到 docker compose updocker compose run 命令中,以便根据需要在启动时自动构建镜像。

特殊情况 - 添加自定义配置文件

如果您有自定义配置文件并希望在您的 Airflow 实例中使用它,则需要执行以下步骤:

  1. 删除 docker-compose.yaml 文件中 AIRFLOW_CONFIG: '/opt/airflow/config/airflow.cfg' 行的注释。

  2. 将您的自定义 airflow.cfg 文件放置在本地 config 文件夹中。

  3. 如果您的配置文件名称与 airflow.cfg 不同,请调整 AIRFLOW_CONFIG: '/opt/airflow/config/airflow.cfg' 中的文件名。

网络

通常,如果您想在本地使用 Airflow,您的 DAG 可能会尝试连接到主机上运行的服务器。为了实现这一点,必须在 docker-compose.yaml 中添加额外的配置。例如,在 Linux 上,配置必须在 services: airflow-worker 部分中添加 extra_hosts: - "host.docker.internal:host-gateway";并使用 host.docker.internal 代替 localhost。此配置在不同的平台上有所不同。有关详细信息,请查看 Docker 文档中关于 WindowsMac 的信息。

使用 PyCharm 在 Docker 容器内调试 Airflow

先决条件:在 PyCharm 中创建一个项目并下载 (docker-compose.yaml)。

步骤

  1. 修改 docker-compose.yaml

    services 部分下添加以下部分:

airflow-python:
<<: *airflow-common
profiles:
    - debug
environment:
    <<: *airflow-common-env
user: "50000:0"
entrypoint: [ "/bin/bash", "-c" ]

注意

此代码片段创建一个名为 “airflow-python” 的新服务,专门用于 PyCharm 的 Python 解释器。在 Linux 系统上,如果您已执行命令 echo -e "AIRFLOW_UID=$(id -u)" > .env,则需要在 airflow-python 服务中设置 user: "50000:0",以避免 PyCharm 的 Unresolved reference 'airflow' 错误。

  1. 配置 PyCharm 解释器

    • 打开 PyCharm 并导航至 Settings > Project: <您的项目名称> > Python Interpreter

    • 点击 “Add Interpreter” 按钮并选择 “On Docker Compose”

    • Configuration file 字段中,选择您的 docker-compose.yaml 文件。

    • Service field 中,选择新添加的 airflow-python 服务。

    • 点击 “Next” 并按照提示完成配置。

Configuring the container's Python interpreter in PyCharm, step diagram

构建解释器索引可能需要一些时间。 3) 将 exec 添加到 docker-compose/command 和 python 服务中的 actions

Configuring the container's Python interpreter in PyCharm, step diagram

配置完成后,您可以在容器环境中调试您的 Airflow 代码,模拟您的本地设置。

FAQ: 常见问题解答

ModuleNotFoundError: No module named 'XYZ'

Docker Compose 文件使用最新的 Airflow 镜像 (apache/airflow)。如果您需要安装新的 Python 库或系统库,您可以自定义和扩展它

下一步是什么?

从这里开始,您可以前往教程部分获取更多示例,或者如果您准备好开始动手,则可以前往操作指南部分。

Docker Compose 支持的环境变量

请不要将这里的变量名称与构建镜像时设置的构建参数混淆。AIRFLOW_UID 构建参数在构建镜像时默认为 50000,因此它是“烘焙”到镜像中的。另一方面,下面的环境变量可以在容器运行时设置,例如使用 id -u 命令的结果,这允许使用在构建镜像时未知的动态主机运行时用户 ID。

变量

描述

默认值

AIRFLOW_IMAGE_NAME

要使用的 Airflow 镜像。

apache/airflow:2.10.4

AIRFLOW_UID

运行 Airflow 容器的用户的 UID。如果您想使用非默认的 Airflow UID(例如,当您映射主机中的文件夹时,它应该设置为 id -u 调用的结果)时,则覆盖此值。当它被更改时,将创建一个具有该 UID 的用户,其在容器内名为 default,并且该用户的主目录设置为 /airflow/home/,以便共享安装在那里的 Python 库。这是为了实现 OpenShift 的兼容性。有关更多信息,请参见 任意 Docker 用户

50000

注意

在 Airflow 2.2 之前,Docker Compose 也有 AIRFLOW_GID 参数,但它没有提供任何其他功能 - 只是增加了混乱 - 因此已被删除。

如果您正在尝试/测试通过 Docker Compose 安装 Airflow,则这些额外的变量很有用。它们不打算在生产中使用,但它们使首次使用最常见自定义的用户的环境可以更快地启动。

变量

描述

默认值

_AIRFLOW_WWW_USER_USERNAME

管理员 UI 帐户的用户名。如果指定此值,则会自动创建管理员 UI 用户。这仅当您想运行 Airflow 进行试用并想启动带有嵌入式开发数据库的容器时才有用。

airflow

_AIRFLOW_WWW_USER_PASSWORD

管理员 UI 帐户的密码。仅当设置 _AIRFLOW_WWW_USER_USERNAME 时才使用。

airflow

_PIP_ADDITIONAL_REQUIREMENTS

如果非空,Airflow 容器将尝试安装在变量中指定的 requirements。示例: lxml==4.6.3 charset-normalizer==1.4.1。在 Airflow 镜像 2.1.1 及更高版本中可用。

此条目是否有帮助?