【问题标题】:AWS lambda Unable to import module 'lambda_function': No module named PILAWS lambda 无法导入模块“lambda_function”:没有名为 PIL 的模块
【发布时间】:2018-11-16 23:12:09
【问题描述】:

我正在使用 SearchFacesbyimage 的 lambda 函数并且我正在使用此文档 https://aws.amazon.com/blogs/machine-learning/build-your-own-face-recognition-service-using-amazon-rekognition/

我在哪里进行比较

from PIL import Image

我收到了这个错误 Unable to import module 'lambda_function': No module named PIL

【问题讨论】:

  • 你是否安装了所有的依赖,压缩成 .zip 文件然后上传到 lambda??
  • @ManojAcharya 我试图搜索但没有得到解决方案。你能指导我在哪里安装吗?我没有在本地运行。
  • 请参考此链接一次:*.com/questions/50711722/…
  • 感谢您的回复。你能说出什么会有 lambda_function.py 吗?因为我的 lambda 函数是 ImageComp.py 。那么我需要改变什么?
  • 第二件事是如何将 zip 文件直接上传到 lambda?

标签: amazon-web-services amazon-s3 aws-lambda python-imaging-library amazon-rekognition


【解决方案1】:

您收到此错误是因为 Python 2.x 的 PIL 或 3.x 的 PILLOW 不是 Python lambda 环境中可用的标准库。

要使用这样的库,您必须为您需要的所有库以及要部署的 python 代码制作一个自定义部署包。这个包可以在 docker 或使用 EC2 实例中轻松制作。

这是您将如何在 EC2 上制作该部署包的过程:

  1. 假设您的文件名为 CreateThumbnail.py

  2. 如果您的源代码在本地主机上,请将其复制到 EC2。

    scp -i key.pem /path/to/my_code.py ec2-user@public-ip-address:~/CreateThumbnail.py

  3. 通过 SSH 连接到 64 位 Amazon Linux 实例。

    ssh -i key.pem ec2-user@public-ip-address

  4. 使用以下步骤安装 Python 3.6 和 virtualenv:

    a) sudo yum install -y gcc zlib zlib-devel openssl openssl-devel

    b) wget https://www.python.org/ftp/python/3.6.1/Python-3.6.1.tgz

    c) tar -xzvf Python-3.6.1.tgz

    d) cd Python-3.6.1 && ./configure && make

    e) sudo make installfsudo /usr/local/bin/pip3 install virtualenv

  5. 选择通过pip3安装的虚拟环境

    /usr/local/bin/virtualenv ~/shrink_venv

    来源 ~/shrink_venv/bin/activate

  6. 在虚拟环境中安装库

    pip install Pillow

    pip install boto3

  7. 将 lib 和 lib64 站点包的内容添加到您的 .zip 文件中。请注意,以下步骤假定您使用的是 Python 运行时版本 3.6。如果您使用的是 2.7 版,则需要进行相应更新。

    cd $VIRTUAL_ENV/lib/python3.6/site-packages

    zip -r9 ~/CreateThumbnail.zip

    注意- 要包含所有隐藏文件,请使用以下选项:

    zip -r9 ~/CreateThumbnail.zip

  8. 将您的 Python 代码添加到 .zip 文件中

    cd ~

    zip -g CreateThumbnail.zip CreateThumbnail.py

现在 CreateThumbnail.zip 是您的自定义部署包,只需将其复制到 s3 并上传到您的 lambda。

此示例取自 AWS 官方文档,网址为 https://docs.aws.amazon.com/lambda/latest/dg/with-s3-example-deployment-pkg.html

【讨论】:

  • CreateThumbnail.py 是 lambda 函数?
  • 你可以给它起任何名字,但总是以这种方式配置你的处理程序 filename.handler-function ,例如 disco.lambda_handler where disco. py 是文件名,lambda_handler 是 lambda 的代码处理程序模块
  • 第 4 步中的所有这些安装都在本地计算机或 EC2 上?
  • 安装需要在 EC2 上完成,从本地机器你唯一需要做的就是将你的 python 代码复制到 Ec2
  • 仍然无法导入模块“lambda_function”:无法导入名称“_imaging”:|
【解决方案2】:

尽管文档清楚地概述了用于为您的 lambda 函数手动创建 zip 工件的步骤。该解决方案的可扩展性不是很高。我一直在使用一个名为juniper 的非常小的包来无缝打包python lambda 函数。

在您的特定情况下,这是您需要采取的步骤:

假设这是您的文件夹结构:

.
├── manifest.yml
├── src
│   ├── requirements.txt
│   ├── lambda_function.py

在 requirements.txt 中,您将仅包含 lambda 函数的依赖项,在本例中为 PIL 库。

Pillow==6.0.0

现在,您只需创建一个小文件来告诉瞻博网络要在 zip 文件中包含的内容。 manifest.yml 看起来像:

functions:
  reko:
    requirements: ./src/requirements.txt.
    include:
    - ./src/lambda_function.py

现在您需要在本地环境中pip install juniper。执行cli命令:

juni build

Juniper 将创建:./dist/reko.zip。该文件将包含您的源代码以及您在 requirements.txt 文件中包含的任何依赖项。

默认情况下,juniper 使用 docker 容器,构建命令将使用 python3.6。您可以覆盖该默认值。

【讨论】:

【解决方案3】:

我也遇到了同样的问题。您可以在此处采取两个步骤:手动与自动打包和部署。

手动步骤将涉及创建正确的 virtualenv 并在该虚拟环境中安装依赖项。然后压缩所有内容并上传到 AWS。

为了实现自动化,我总是更喜欢使用无服务器框架来打包和部署 Lambda 函数。特别是 python-requirements-plugin 有助于打包。但我必须指定以下内容来告诉框架在 docker 容器中构建并且不要剥离任何库:

custom:
  pythonRequirements:
    dockerizePip: true
    strip: false

【讨论】:

    【解决方案4】:

    正如这里的大多数答案已经暗示的那样,AWS Lambda 执行环境仅包括 Python 内置包和 boto3,而没有其他内容。

    要包含外部包,您需要自己包含它们,方法是构建它们并将其包含在您的函数上传中,或者将它们打包为层。还要记住,软件包本身需要为 Amazon Linux 构建。

    如果您使用的是 python3.7,那么您可以将这个公开可用的层用于枕头: https://github.com/keithrozario/Klayers

    【讨论】: