Tat*_*eyr 6 google-cloud-platform google-cloud-dataflow apache-beam
我们希望降低在 GCP Dataflow 中运行特定 Apache Beam 管道 (Python SDK) 的成本。
我们构建了一个内存密集型 Apache Beam 管道,它需要大约 8.5 GB 的 RAM 才能在每个执行程序上运行。一个大型机器学习模型目前以一种转换DoFn.setup方法加载,因此我们可以为数百万用户预先计算推荐。
现有 GCP Compute Engine 机器类型的内存/vCPU 比率低于我们的要求(每个 vCPU 最多 8GB RAM)或更高的比例(每个 vCPU 24GB RAM):https : //cloud.google.com/compute/文档/机器类型#machine_type_comparison
我们已使用 GCPm1-ultramem-40机器类型成功运行此管道。然而,硬件使用——因此,成本——是次优的。此机器类型的比率为每个 vCPU 24 GB RAM。当使用它来运行上述管道时,虚拟机使用了不到 36% 的可用内存——但是,正如预期的那样,我们为此付出了全部。
尝试使用custom-2-13312机器类型(2 个 vCPU 和 13 GB RAM)运行相同的管道时,Dataflow 崩溃,并显示错误:
Root cause: The worker lost contact with the service.
Run Code Online (Sandbox Code Playgroud)
在监控运行 Dataflow 作业的 Compute Engine 实例时,很明显它们的内存不足。Dataflow 尝试将模型加载到内存中两次——每个 vCPU 一次——但可用内存仅够一个。
如果我们能够通知 Apache Beam/Dataflow 特定转换需要特定数量的内存,那么问题就会得到解决。但是我们没有设法找到实现这一目标的方法。
我们能想到的另一个解决方案是尝试更改每个 Compute Engine 虚拟机的 Dataflow 执行程序的比率。这将使我们能够找到一个比率,在该比率中,我们将在尊重管道内存要求的同时尽可能少地浪费 vCPU。在使用前面提到的custom-2-13312机器类型时,我们尝试使用以下配置运行管道:
--number_of_worker_harness_threads=1 --experiments=use_runner_v2--experiments=no_use_multiple_sdk_containers --experiments=beam_fn_api--sdk_worker_parallelism=1使用 (1) 时,我们设法拥有一个线程,但 Dataflow 为每个 VM 生成了两个 Python 执行程序进程。这导致管道崩溃,因为当只有一个空间足够时,尝试将模型加载到内存两次。
使用 (2) 时,每个 VM 生成一个 Python 进程,但它使用两个线程运行。这些线程中的每一个都试图加载模型,但 VM 内存不足。方法 (3) 的结果与 (1) 和 (2) 非常相似。
不可能组合多个这些配置。
是否有(一组)配置允许我们控制每个 VM 的 Dataflow 执行程序的数量?
是否还有其他替代方案可以降低我们可能没有的成本?
小智 4
我们正在研究这些问题的长期解决方案,但这里有一个战术修复方案,可以防止您在方法 1 和 2 中看到的模型重复:
跨工作线程共享虚拟机中的模型,以避免每个工作线程中重复模型。使用以下实用程序 ( https://github.com/apache/beam/blob/master/sdks/python/apache_beam/utils/shared.py ),如果您使用的是早期版本,则该实用程序在 Beam 2.24 中开箱即用Beam 版本,只需将shared.py 复制到您的项目并将其用作用户代码。
| 归档时间: |
|
| 查看次数: |
626 次 |
| 最近记录: |