如何在AWS Lambda中加载npm模块?

ni65a41a  于 2022-12-23  发布在  其他
关注(0)|答案(9)|浏览(272)

我已经使用基于Web的编辑器创建了几个Lambda函数。到目前为止一切顺利。我现在想开始用模块扩展这些函数(比如Q代表promises)。我不知道如何将模块导出到Lambda,以便它们可以被我的函数使用。
我已经通读了this,但它似乎涉及到设置一个EC2和运行Lambda函数。有一个机制,以上传一个压缩时,创建一个函数,但似乎涉及到发送本地开发的函数。因为我在基于Web的编辑器工作,这似乎是一个奇怪的工作流程。
如何简单地部署一些模块以在Lambda函数中使用?

qzlgjiam

qzlgjiam1#

如果不上传.zip文件,就无法加载NPM模块,但实际上可以将此过程简化为两个快速命令行。
具体方法如下:
1.将您的Lambda函数文件放在一个单独的目录中,这是因为您在本地安装了用于Lambda的npm包,并且希望能够隔离和测试将要上传到Lambda的内容。
1.在步骤#1中创建的单独Lambda目录中,使用npm install packageName在本地安装NPM包。
1.确保您的函数在本地运行时正常工作:node lambdaFunc.js(您可以简单地注解掉代码中的两行export.handler,以使代码适合在本地与Node一起运行)。
1.转到Lambda的目录并压缩内容,确保而不是包含目录本身。

zip -r lambdaFunc.zip .

1.如果您已经安装了aws-cli(如果您想让您的工作更轻松,我建议您安装),现在可以输入以下命令:

aws lambda update-function-code --function-name lambdaFunc \
--zip-file fileb://~/path/to/your/lambdaFunc.zip

(no上面lambdaFunc部分周围的引号,以防你像我一样想知道)
1.现在您可以在Lambda控制台中单击 * test *。
1.我建议为以上两个命令添加一个简短的别名,下面是我为更长的Lambda update命令所做的:

alias up="aws lambda update-function-code --function-name lambdaFunc \
--zip-file fileb://~/path/to/your/lambdaFunc.zip"
u3r8eeie

u3r8eeie2#

为了在Lambda中包含npm模块,需要一个.zip文件。你真的不应该使用Lambda web编辑器做任何事情--就像任何生产代码一样,你应该在本地开发,提交给git,等等。

我的流程:

1)我的Lambda函数通常是大型项目的辅助工具,因此我在其中创建了一个**/aws/lambdas目录来存放它们。
2)每个lambda目录都包含一个包含函数代码的
index.js文件、一个定义依赖项的package.json文件和一个/node_modules**子目录(package.json文件不被Lambda使用,它只是为了让我们可以在本地运行npm install命令)。

包.json:

{
  "name": "my_lambda",
  "dependencies": {
    "svg2png": "^4.1.1"
  }
}

3)I .gitignore忽略所有node_modules目录和.zip文件,这样从npm安装和压缩生成的文件就不会弄乱我们的repo。

.忽略不计:

# Ignore node_modules
**/node_modules

# Ignore any zip files
*.zip

4)我从目录中运行npm install来安装模块,并在本地开发/测试函数。
5)I .压缩lambda目录并通过控制台上传。
(**重要提示:**请勿使用Mac Finder中的“compress”实用程序来压缩文件!您必须从目录根目录中的CLI运行zip-请参阅here

zip -r ../yourfilename.zip *

注:

如果您在Mac上本地安装节点模块,可能会遇到问题,因为一些特定于平台的模块在部署到Lambda基于Linux的环境时可能会失败。(参见https://stackoverflow.com/a/29994851/165673
解决方案是在从AMI启动的EC2示例上编译模块,该示例与您正在使用的Lambda Node.js运行时相对应(参见Lambda runtimes and their respective AMIs列表)。
另请参见AWS Lambda Deployment Package in Node.js - AWS Lambda

hs1rzwqc

hs1rzwqc3#

现在你可以使用Lambda图层来解决这个问题,只需添加一个包含你需要的包的图层,它就会完美地运行。
关注此帖子:https://medium.com/@anjanava.biswas/nodejs-runtime-environment-with-aws-lambda-layers-f3914613e20e

bogh5gae

bogh5gae4#

希望这能有所帮助,使用无服务器框架,您可以做一些类似的事情:
1.在serverless.yml文件中添加以下内容:

plugins:
      - serverless-webpack
    custom:
      webpackIncludeModules:
        forceInclude:
          - <your package name> (for example: node-fetch)

1.然后创建你的Lambda函数,通过serverless deploy部署它,serverless.yml中包含的包将为你准备好。
有关无服务器的详细信息:https://serverless.com/framework/docs/providers/aws/guide/quick-start/

czfnxgou

czfnxgou5#

在摆弄了几个小时的包裹后,我发现它似乎对在浏览器中运行做了一些假设(即使我告诉它使用engine: node)。
相反:

esbuild

    • esbuild**更容易,也更快!

只需运行npm add --save-dev esbuild,并将以下脚本添加到package.json中:

{
  ...
  "scripts": {
    "build": "esbuild --bundle --minify --platform=node --target=node12 --outdir=build main.js",
    "export": "cd build && zip main.js.zip main.js"
  },
  ...
  "devDependencies": {
    "esbuild": "^0.11.19",
    ...
  }
}

这使我能够在使用aws-sdk的同时仍然获得树抖动和缩小,同时仍然能够安装其他依赖项,如jest和eslint,而不必打包整个node_modules文件夹。
要在CI中构建软件包,只需:npm ci && npm run build && npm run export
文件build/main.js.zip将包含您需要的所有内容!

mzmfm0qo

mzmfm0qo6#

目前在许多IDE中也有,例如:VSC,你可以安装一个扩展的AWS和简单地点击上传从那里,没有努力键入所有这些命令+地区。
下面是一个例子:

sqserrrh

sqserrrh7#

npm模块必须捆绑在您的nodejs包中,并以zip格式上传到AWS Lambda Layers,然后您需要引用您的模块/js,如下所示,并使用其中可用的方法。const mymodule = require('/opt/nodejs/MyLogger');

66bbxpm5

66bbxpm58#

这是一个老问题,但它帮助我找到了一种向Alexa技能添加新的Lambda依赖项的非常简单的方法。
就像JohnAllen的答案一样,你需要在本地机器上创建一个文件夹,给它命名任何你想要的标题(这是任意的):

mkdir lambdaFunc
cd lambdaFunc

进入文件夹后,使用npm安装必要的软件包。对我来说,我需要解析ISO 8601 duration(我的命令是npm install iso8601-duration):

npm install <your-package-here>

一旦安装,退出该目录,并压缩它.打开你的Alexa技能在Alexa技能开发者控制台,然后选择“导入代码”选项.从这里,你会上传你的.zip文件,并选择所有的代码:

就是这样!然后你可以像我一样导入代码:

const DateConverter = require('iso8601-duration');
c2e8gylq

c2e8gylq9#

如果你有多个AWS资源需要管理,使用AWS CDK部署lambda函数可能是个不错的选择。它是一个IaC工具,可以部署AWS资源并使用CloudFormation。要设置CDK,请参见getting started
设置好CDK之后,可以创建一个Function构造,并使用它的lambda.Code.fromAsset轻松地捆绑源代码(包括node_modules),然后将其用作Function的代码。

import * as lambda from "aws-cdk-lib/aws-lambda";
import * as path from "path";

export class MyStack extends cdk.Stack {
  constructor(scope: Construct, id: string, props?: cdk.StackProps) {

    const lambdaFunc = new lambda.Function(this, "lambdaFunc", {
      code: lambda.Code.fromAsset(path.join(__dirname, "..", "..", "project-containing-node-modules")),
      ...
    });

  }
}

然后使用cdk deploy将其部署到您的AWS帐户。
如果您在多个Lambda中使用相同的node_modules,并且不想上传重复的依赖项,CDK也支持Lambda层。

相关问题