【问题标题】:How to use extra files for AWS glue job如何为 AWS 粘合作业使用额外文件
【发布时间】:2023-03-25 07:40:01
【问题描述】:

我有一个用python编写的ETL作业,它由多个具有以下目录结构的脚本组成;

my_etl_job
 |
 |--services
 |  |
 |  |-- __init__.py
 |  |-- dynamoDB_service.py
 |
 |-- __init__.py
 |-- main.py
 |-- logger.py

main.py 是从上述目录导入其他脚本的入口点脚本。上传到由 dev 端点创建的 ETL 集群后,上面的代码在 dev-endpoint 上运行得非常好。因为现在我想在生产中运行它,所以我想为它创建一个合适的胶水作业。但是当我以.zip 格式压缩整个目录my_etl_job 时,将其上传到artifacts s3 存储桶中,并将.zip 文件位置指定到脚本位置,如下所示

s3://<bucket_name>/etl_jobs/my_etl_job.zip

这是我在胶水作业 UI 仪表板上看到的代码;

PK
    ���P__init__.pyUX�'�^"�^A��)PK#7�P  logger.pyUX��^1��^A��)]�Mk�0����a�&v+���A�B���`x����q��} ...AND ALLOT MORE...

似乎胶水作业不接受 .zip 格式?如果是,那么我应该使用什么压缩格式?

更新: 我检查了胶水作业可以选择接收额外文件Referenced files path,其中我提供了上述文件所有路径的逗号分隔列表,并将 script_location 更改为仅引用main.py 文件路径。但这也没有奏效。胶水作业抛出错误找不到模块记录器(我在 logger.py 文件中定义了这个模块)

【问题讨论】:

标签: python amazon-s3 aws-glue


【解决方案1】:

您必须将 zip 文件作为额外的 python lib 传递,或者为代码包构建一个 wheel 包并将 zip 或 wheel 上传到 s3,提供与额外的 python lib 选项相同的路径

注意:将你的主要功能写在胶水控制台中,从 zipped/wheel 依赖项中引用所需的功能,你的脚本位置不应该是一个 zip 文件

https://docs.aws.amazon.com/glue/latest/dg/aws-glue-programming-python-libraries.html

【讨论】:

  • 没错。我提供了 script_location: s3://&lt;bucket_name&gt;/etl_jobs/main.py--extra-py-files s3://&lt;bucket_name&gt;/etl_jobs/my_etl_job.zip 并且有效。
【解决方案2】:
  1. 您的主要工作不应该被压缩。那应该是一个py文件本身。在这种情况下,这将是您的 main.py。这不应该是 zip 文件的一部分。
  2. 您在代码中引用的任何其他库文件都可以压缩或制作为 wheel 文件,并通过 extra-files 选项引用。您的文件夹结构可以稍微修改以保存您在 main 中引用的所有这些额外的 py 文件,最好如下所示。如果您有更多服务,请考虑进一步分解,但下面是一个简单的示例
my_etl_job
 |
 |--corelib
 |  |
 |  |--__init__.py
 |  |-- services
 |      |
 |      | -- dynamoDB_service.py
 |      | -- logger.py
 |
 |-- main.py

然后您可以将 main.py 中的 dynamodbservices 模块导入为 corelib.services.dynamoDB_service。 准备库时,只需转到 corelib 之前的文件夹,然后像下面这样压缩文件夹

zip -r corelib.zip corelib/

然后,您可以将 crelib.zip 添加为胶水中的额外文件。 (您可以根据自己的喜好准备一个轮子文件)

【讨论】:

  • 感谢艾默生提供的线索。是的,遵循相同,除了我保持目录结构不变,并且它有效。请参阅我对 karan 回答的评论。
【解决方案3】:

我正在使用 Spark 作业类型(而不是 Python shell)的 Glue v2.0,并且遇到了类似的问题。

除了之前关于 zip 文件的答案之外,还讨论了:

  • main.py 不应压缩。
  • .zip 文件存档corelib.zip(或services.zip)应包含corelib(或services)文件夹及其内容。

我遵循了这个,但在尝试导入我的模块时仍然收到 ImportError: No module named 错误。

将以下 sn-p 添加到我的 Glue Job 脚本后:

import sys
import os

print(f"os.getcwd()={os.getcwd()}")
print(f"os.listdir('.')={os.listdir('.')}")

print(f"sys.path={sys.path}")

我可以看到当前工作目录包含我的 zip 文件。

但是sys.path 没有包含当前工作目录。

因此 Python 无法导入我的 zip 文件,导致出现 ImportError: No module named 错误。

为了解决导入问题,我只是将以下代码添加到我的 Glue Job 脚本中。

import sys
sys.path.insert(0, "utils.zip")

import utils

供参考: 我的utils.zip的内容

Archive:  utils.zip
 Length   Method    Size  Cmpr    Date    Time   CRC-32   Name
--------  ------  ------- ---- ---------- ----- --------  ----
       0  Defl:N        5   0% 01-01-2049 00:00 00000000  __init__.py
    6603  Defl:N     1676  75% 01-01-2049 00:00 f4551ccb  utils.py
--------          -------  ---                            -------
    6603             1681  75%                            2 files

(请注意__init__.py 必须存在才能使模块导入工作)

我的本​​地项目文件夹结构

my_job_stuff
 |-- utils
 |   |-- __init__.py
 |   |-- utils.py
 |-- main.py

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2022-07-08
    • 2020-05-26
    • 2023-03-28
    • 1970-01-01
    • 2018-10-31
    • 2018-07-01
    • 2021-10-10
    • 2021-07-26
    相关资源
    最近更新 更多