如何从 AWS Lambda 上的预编译二进制文件导入 lxml?

How to import lxml from precompiled binary on AWS Lambda?

我正在尝试在 Python 中导入 lxml 库以执行 AWS Lambda 函数,但出现以下错误:[ERROR] Runtime.ImportModuleError: Unable to import module 'lambda_function': No module named 'lxml'。为了解决这个问题,我遵循了 this SO answer and used precompiled binaries from the following repo.

的建议

我使用了那个 repo 中的 lxml_amazon_binaries.zip 文件,它的结构是这样的:

 lxml_amazon_binaries
    ├── lxml
    └── usr

我将整个 zip 文件上传到 AWS Lambda 层,创建了一个新的 Lambda 函数,并使用简单的 from lxml import etree 进行了测试,这导致了上述错误。

我 uploading/using 这些二进制文件正确吗? 我不确定是什么导致了错误。使用不同的 Python 运行时没有帮助。

创建 lxml 图层的最可靠方法是使用 Docker,如 AWS blog 中所述。具体来说,已验证 步骤是(在 Linux 上执行,但只要您有 Docker,windows 也应该有效):

  1. 创建空文件夹,例如mylayer.

  2. 转到文件夹并创建 requirements.txt 文件,内容为

lxml
  1. 运行 以下 docker 命令:

该命令将为 python3.8:

创建图层
docker run -v "$PWD":/var/task "lambci/lambda:build-python3.8" /bin/sh -c "pip install -r requirements.txt -t python/lib/python3.8/site-packages/; exit"
  1. 将图层存档为 zip:
zip -9 -r mylayer.zip python 
  1. 在 AWS 控制台中基于 mylayer.zip 创建 lambda 层。不要忘记将 Compatible runtime 指定为 python3.8

  2. 将第 5 步中创建的图层添加到您的函数中。

  3. 我用你的代码测试了层:

from lxml import etree

def lambda_handler(event, context):
    
    root = etree.Element("root")
    root.append( etree.Element("child1") )
    print(etree.tostring(root, pretty_print=True))

它工作 正确:

b'<root>\n  <child1/>\n</root>\n'