Python 如何有效地使气流dag定义数据库驱动

Python 如何有效地使气流dag定义数据库驱动,python,airflow,Python,Airflow,背景 我有一些从第三方api中提取数据的DAG 我们需要提取的账户可能会随着时间的推移而变化。为了确定要拉取哪些帐户,我们可能需要查询数据库或发出HTTP请求,具体取决于进程 在开始之前,我们只需要在python脚本的开头获得帐户列表。然后,我们将遍历帐户列表,并将每个帐户拉入文件或执行我们需要执行的任何操作 但是现在,使用airflow,在帐户级别定义任务并让airflow处理重试功能、日期范围和并行执行等是有意义的 因此,我的dag可能看起来像这样: 问题 由于每个帐户都是一个任务,因此每

背景

我有一些从第三方api中提取数据的DAG

我们需要提取的账户可能会随着时间的推移而变化。为了确定要拉取哪些帐户,我们可能需要查询数据库或发出HTTP请求,具体取决于进程

在开始之前,我们只需要在python脚本的开头获得帐户列表。然后,我们将遍历帐户列表,并将每个帐户拉入文件或执行我们需要执行的任何操作

但是现在,使用airflow,在帐户级别定义任务并让airflow处理重试功能、日期范围和并行执行等是有意义的

因此,我的dag可能看起来像这样:

问题

由于每个帐户都是一个任务,因此每次dag解析都需要访问帐户列表。但是,由于dag文件经常被解析,所以您不一定要查询数据库,或者整天等待来自每台机器的每次dag解析的REST调用。这可能是资源密集型的,而且可能需要花钱

问题

有没有一种很好的方法可以在本地文件中缓存这种类型的配置信息,最好是在指定的生存时间内

思想

我考虑过两种不同的方法:

  • 写入csv或pickle文件并使用mtime过期。
    • 这样做的问题是,如果两个进程同时试图使文件过期,可能会发生冲突。我不知道这种可能性有多大,也不知道后果会是什么,但可能没什么可怕的
  • 为所有这样的进程创建一个公共sqlite数据库。应在首次访问变量时自动创建。每个配置变量在表中获得一行。使用last_modified_datetime列告知何时过期。
    • 需要更详细的代码和依赖项
  • 使用气流变量
    • 这样做的好处是,它使用现有的数据库,所以每个查询不需要$1,也不需要合理的网络延迟,但它仍然需要网络往返
    • 具有在多节点设置中所有节点都相同的优点
    • 确定何时过期可能会有问题,因此可能会创建配置管理器dag来定期更新配置变量
    • 但这会增加部署和开发过程的复杂性——需要填充变量才能正确定义DAG——所有开发人员也需要在本地管理这一点,而不是采用更具创建-读取缓存的方法
  • 子代?
    • 从未使用过,但我怀疑它们可能在这里使用。但是社区似乎不鼓励使用它们

  • 你处理过这个问题吗?你找到好的解决办法了吗?所有这些似乎都不是很好。

    默认的DAG解析间隔非常合适:5分钟。但即使对大多数人来说,这也是相当多的,因此,如果您的部署不太接近新DAG的到期时间,那么增加这一数量也是相当合理的

    总的来说,我认为在每次DAG解析心跳时发出REST请求并不是那么糟糕。此外,现在的调度过程与解析过程是解耦的,因此不会影响任务调度的速度。气流为您缓存DAG定义

    如果您认为仍然有理由将自己的缓存放在上面,那么我的建议是将缓存放在定义服务器上,而不是放在服务器端。例如,在REST端点上使用缓存头,并在需要时自行处理缓存失效。但这可能是一些过早的优化,所以我的建议是从没有它开始,只有当你衡量出你需要它的令人信服的证据时才实施它

    编辑:关于Web服务器和工作程序

    的确,Web服务器也会触发DAG解析,但不确定其频率。可能遵循guicorn workers刷新间隔(默认为30秒)。默认情况下,工人也会在每个任务开始时执行此操作,但如果激活酸洗DAG,则可以保存此操作。不确定这是不是一个好主意,但我听说这是注定要被弃用的东西


    您可以尝试做的另一件事是将其缓存在流程本身中,记忆发出昂贵请求的函数。Python有一个内置的函数工具(
    lru\u cache
    ),再加上pickle,它可能就足够了,而且比其他选项要简单得多。

    我有同样的场景

    对多个帐户进行API调用。最初创建了一个python脚本来迭代列表

    当我开始使用气流时,我想到了你打算做什么。尝试了您列出的两个备选方案。经过一些实验后,决定在python中处理重试逻辑,如果HTTP调用失败,则使用简单的try-except块。原因是

  • 要维护的一个脚本
  • 气流较小的物体
  • 使用一个脚本,可重启性更容易。 (在气流中重新启动失败的作业不是轻而易举的事(没有双关语)

  • 最后,这取决于你,这是我的经验。

    是的,我们进行了过早的优化,我只是在考虑这是否可行。。。至于其他方面,你是对的,但我们的主要数据库是雪花,如果我们使用dag defs,那么我们承诺全天都有仓库,这是$$$。我认为解决方案是在airflow metastore服务器上为此创建一个DB,并使用它。我明白了。是的,这是一种特殊的情况,因为您的存储解决方案有特定的定价模型,所以即使是5分钟的间隔也是不可接受的。在这种情况下,使用廉价的DB作为视图是一个好办法;它们也被Web服务器解析;更糟