Implantar funções do Lambda em Node.js com imagens de contêiner - AWS Lambda

As traduções são geradas por tradução automática. Em caso de conflito entre o conteúdo da tradução e da versão original em inglês, a versão em inglês prevalecerá.

Implantar funções do Lambda em Node.js com imagens de contêiner

Existem três maneiras de criar uma imagem de contêiner para uma função do Lambda em Node.js:

dica

Para reduzir o tempo necessário para que as funções do contêiner do Lambda se tornem ativas, consulte Use multi-stage builds na documentação do Docker. Para criar imagens de contêiner eficientes, siga as Melhores práticas para gravar Dockerfiles.

Esta página explica como criar, testar e implantar imagens de contêiner para o Lambda.

Imagens base da AWS para Node.js

A AWS oferece as seguintes imagens base para Node.js:

Tags Runtime Sistema operacional Dockerfile Desaprovação

20

Node.js 20 Amazon Linux 2023 Dockerfile para Node.js 20 em GitHub

18

Node.js 18 Amazon Linux 2 Dockerfile para Node.js 18 em GitHub

16

Node.js 16 Amazon Linux 2 Dockerfile para Node.js 16 em GitHub

12 de junho de 2024

Repositório do Amazon ECR: gallery.ecr.aws/lambda/nodejs

As imagens base do Node.js 20 e versões posteriores são baseadas na imagem de contêiner mínimo do Amazon Linux 2023. As imagens básicas anteriores usam o Amazon Linux 2. O AL2023 oferece várias vantagens em relação ao Amazon Linux 2, incluindo uma área de implantação menor e versões atualizadas de bibliotecas, como glibc.

As imagens baseadas em AL2023 usam microdnf (com link simbólico comodnf) como gerenciador de pacotes em vez deyum, que é o gerenciador de pacotes padrão no Amazon Linux 2. microdnfé uma implementação independente do. dnf Para obter uma lista de pacotes incluídos nas imagens baseadas em AL2023, consulte as colunas Minimal Container em Comparando pacotes instalados no Amazon Linux 2023 Container Images. Para obter mais informações sobre as diferenças entre o AL2023 e o Amazon Linux 2, consulte Apresentando o tempo de execução do Amazon Linux 2023 para AWS Lambda no blog de AWS computação.

nota

Para executar imagens baseadas em AL2023 localmente, inclusive com AWS Serverless Application Model (AWS SAM), você deve usar o Docker versão 20.10.10 ou posterior.

Usar uma imagem base da AWS para Node.js

Para executar as etapas desta seção, você deve ter o seguinte:

Para criar uma imagem de contêiner a partir de uma imagem base da AWS para Node.js
  1. Crie um diretório para o projeto e depois mude para esse diretório.

    mkdir example cd example
  2. Crie um novo projeto Node.js com o npm. Para aceitar as opções padrão fornecidas na experiência interativa, pressione Enter.

    npm init
  3. Crie um novo arquivo chamado index.js. É possível adicionar o exemplo de código de função a seguir ao arquivo para testes ou usar o seu próprio código.

    exemplo Manipulador CommonJS
    exports.handler = async (event) => { const response = { statusCode: 200, body: JSON.stringify('Hello from Lambda!'), }; return response; };
  4. Se a função depender de outras bibliotecas que não o AWS SDK for JavaScript, use o npm para adicioná-las ao seu pacote.

  5. Crie um novo Dockerfile com a seguinte configuração:

    • Defina a propriedade FROM como o URI da imagem base.

    • Use o comando COPY para copiar o código da função e as dependências de tempo de execução para {LAMBDA_TASK_ROOT} uma variável de ambiente definida pelo Lambda.

    • Defina o argumento CMD como o manipulador de funções do Lambda.

    exemplo Dockerfile
    FROM public.ecr.aws/lambda/nodejs:20 # Copy function code COPY index.js ${LAMBDA_TASK_ROOT} # Set the CMD to your handler (could also be done as a parameter override outside of the Dockerfile) CMD [ "index.handler" ]
  6. Crie a imagem do Docker com o comando docker build. O exemplo a seguir nomeia a imagem como docker-image e atribui a ela a tag test.

    docker build --platform linux/amd64 -t docker-image:test .
    nota

    O comando especifica a opção --platform linux/amd64 para garantir que seu contêiner seja compatível com o ambiente de execução do Lambda, independentemente da arquitetura da sua máquina de compilação. Se você pretende criar uma função do Lambda usando a arquitetura do conjunto de instruções ARM64, certifique-se de alterar o comando para usar a opção --platform linux/arm64 em vez disso.

  1. Inicie a imagem do Docker com o comando docker run. Neste exemplo, docker-image é o nome da imagem e test é a tag.

    docker run --platform linux/amd64 -p 9000:8080 docker-image:test

    Esse comando executa a imagem como um contêiner e cria um endpoint local em localhost:9000/2015-03-31/functions/function/invocations.

    nota

    Se você criou a imagem do Docker para a arquitetura do conjunto de instruções ARM64, certifique-se de usar a opção --platform linux/arm64, em vez de --platform linux/amd64.

  2. Em uma nova janela de terminal, publique um evento no endpoint local.

    Linux/macOS

    No Linux e no MacOS, execute o seguinte comando curl:

    curl "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{}'

    Esse comando invoca a função com um evento vazio e retorna uma resposta. Caso esteja usando seu próprio código de função em vez do código de função de exemplo, você talvez queira invocar a função com uma carga útil JSON. Exemplo:

    curl "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{"payload":"hello world!"}'
    PowerShell

    Em PowerShell, execute o seguinte Invoke-WebRequest comando:

    Invoke-WebRequest -Uri "http://localhost:9000/2015-03-31/functions/function/invocations" -Method Post -Body '{}' -ContentType "application/json"

    Esse comando invoca a função com um evento vazio e retorna uma resposta. Caso esteja usando seu próprio código de função em vez do código de função de exemplo, você talvez queira invocar a função com uma carga útil JSON. Exemplo:

    Invoke-WebRequest -Uri "http://localhost:9000/2015-03-31/functions/function/invocations" -Method Post -Body '{"payload":"hello world!"}' -ContentType "application/json"
  3. Obtenha o ID do contêiner.

    docker ps
  4. Use o comando docker kill para parar o contêiner. Nesse comando, substitua 3766c4ab331c pelo ID do contêiner da etapa anterior.

    docker kill 3766c4ab331c
Para enviar a imagem ao Amazon ECR e criar a função do Lambda
  1. Execute o get-login-passwordcomando para autenticar a CLI do Docker no seu registro do Amazon ECR.

    • Defina o valor --region para a Região da AWS onde você deseja criar o repositório do Amazon ECR.

    • Substituir 111122223333 por seu ID da Conta da AWS.

    aws ecr get-login-password --region us-east-1 | docker login --username AWS --password-stdin 111122223333.dkr.ecr.us-east-1.amazonaws.com
  2. Crie um repositório no Amazon ECR usando o comando create-repository.

    aws ecr create-repository --repository-name hello-world --region us-east-1 --image-scanning-configuration scanOnPush=true --image-tag-mutability MUTABLE
    nota

    O repositório do Amazon ECR deve estar na mesma Região da AWS que a função do Lambda.

    Se tiver êxito, você verá uma resposta como esta:

    { "repository": { "repositoryArn": "arn:aws:ecr:us-east-1:111122223333:repository/hello-world", "registryId": "111122223333", "repositoryName": "hello-world", "repositoryUri": "111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world", "createdAt": "2023-03-09T10:39:01+00:00", "imageTagMutability": "MUTABLE", "imageScanningConfiguration": { "scanOnPush": true }, "encryptionConfiguration": { "encryptionType": "AES256" } } }
  3. Copie o repositoryUri da saída na etapa anterior.

  4. Execute o comando docker tag para aplicar uma tag na sua imagem local em seu repositório do Amazon ECR como a versão mais recente. Neste comando:

    • Substitua docker-image:test pelo nome e tag da sua imagem do Docker.

    • Substitua <ECRrepositoryUri> pelo repositoryUri que você copiou. Certifique-se de incluir :latest no final do URI.

    docker tag docker-image:test <ECRrepositoryUri>:latest

    Exemplo:

    docker tag docker-image:test 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
  5. Execute o comando docker push para implantar a imagem local no repositório do Amazon ECR. Certifique-se de incluir :latest no final do URI do repositório.

    docker push 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
  6. Crie um perfil de execução para a função, caso ainda não tenha um. Você precisará do nome do recurso da Amazon (ARN) do perfil na próxima etapa.

  7. Criar a função do Lambda. Em ImageUri, especifique o URI do repositório anterior. Certifique-se de incluir :latest no final do URI.

    aws lambda create-function \ --function-name hello-world \ --package-type Image \ --code ImageUri=111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest \ --role arn:aws:iam::111122223333:role/lambda-ex
    nota

    É possível criar uma função usando uma imagem em uma conta da AWS diferente desde que a imagem esteja na mesma região da função do Lambda. Para ter mais informações, consulte Permissões entre contas do Amazon ECR.

  8. Invoque a função.

    aws lambda invoke --function-name hello-world response.json

    Você obterá uma resposta parecida com esta:

    { "ExecutedVersion": "$LATEST", "StatusCode": 200 }
  9. Para ver a saída da função, verifique o arquivo response.json.

Para atualizar o código da função, você deve criar a imagem novamente, fazer o upload da nova imagem para o repositório Amazon ECR e, em seguida, usar o update-function-codecomando para implantar a imagem na função Lambda.

Usar uma imagem base alternativa com o cliente da interface de runtime

Se você usar uma imagem base somente para sistema operacional ou uma imagem base alternativa, deverá incluir o cliente de interface de runtime na imagem. O cliente de interface de runtime estende API de tempo de execução do Lambda, que gerencia a interação entre o Lambda e o código da sua função.

Instale o cliente de interface de runtime em Node.js usando o gerenciador de pacotes npm:

npm install aws-lambda-ric

Você também pode baixar o cliente da interface de tempo de execução Node.js em GitHub. O cliente da interface de runtime é compatível com as seguintes versões do Node.js:

  • 14.x

  • 16.x

  • 18.x

  • 20.x

O exemplo a seguir demonstra como criar uma imagem de contêiner para Node.js usando uma imagem base que não é da AWS. O exemplo de Dockerfile usa a imagem base da buster. O Dockerfile inclui o cliente de interface de runtime.

Para executar as etapas desta seção, você deve ter o seguinte:

Para criar uma imagem de contêiner de uma imagem base que não é da AWS
  1. Crie um diretório para o projeto e depois mude para esse diretório.

    mkdir example cd example
  2. Crie um novo projeto Node.js com o npm. Para aceitar as opções padrão fornecidas na experiência interativa, pressione Enter.

    npm init
  3. Crie um novo arquivo chamado index.js. É possível adicionar o exemplo de código de função a seguir ao arquivo para testes ou usar o seu próprio código.

    exemplo Manipulador CommonJS
    exports.handler = async (event) => { const response = { statusCode: 200, body: JSON.stringify('Hello from Lambda!'), }; return response; };
  4. Crie um novo Dockerfile. O Dockerfile a seguir usa uma imagem base de buster em vez de uma imagem base da AWS. O Dockerfile inclui o cliente de interface de runtime, o que torna a imagem compatível com o Lambda. O Dockerfile usa uma compilação em vários estágios. O primeiro estágio cria uma imagem de compilação, que é um ambiente Node.js padrão em que as dependências da função são instaladas. O segundo estágio cria uma imagem mais fina que inclui o código da função e suas dependências. Isso reduz o tamanho final da imagem.

    • Defina a propriedade FROM como o identificador da imagem base.

    • Use o comando COPY para copiar o código da função e as dependências do runtime.

    • Defina o ENTRYPOINT como o módulo em que você deseja que o contêiner do Docker seja executado quando for iniciado. Nesse caso, o módulo é o cliente de interface de runtime.

    • Defina o argumento CMD como o manipulador de funções do Lambda.

    exemplo Dockerfile
    # Define custom function directory ARG FUNCTION_DIR="/function" FROM node:20-buster as build-image # Include global arg in this stage of the build ARG FUNCTION_DIR # Install build dependencies RUN apt-get update && \ apt-get install -y \ g++ \ make \ cmake \ unzip \ libcurl4-openssl-dev # Copy function code RUN mkdir -p ${FUNCTION_DIR} COPY . ${FUNCTION_DIR} WORKDIR ${FUNCTION_DIR} # Install Node.js dependencies RUN npm install # Install the runtime interface client RUN npm install aws-lambda-ric # Grab a fresh slim copy of the image to reduce the final size FROM node:20-buster-slim # Required for Node runtimes which use npm@8.6.0+ because # by default npm writes logs under /home/.npm and Lambda fs is read-only ENV NPM_CONFIG_CACHE=/tmp/.npm # Include global arg in this stage of the build ARG FUNCTION_DIR # Set working directory to function root directory WORKDIR ${FUNCTION_DIR} # Copy in the built dependencies COPY --from=build-image ${FUNCTION_DIR} ${FUNCTION_DIR} # Set runtime interface client as default command for the container runtime ENTRYPOINT ["/usr/local/bin/npx", "aws-lambda-ric"] # Pass the name of the function handler as an argument to the runtime CMD ["index.handler"]
  5. Crie a imagem do Docker com o comando docker build. O exemplo a seguir nomeia a imagem como docker-image e atribui a ela a tag test.

    docker build --platform linux/amd64 -t docker-image:test .
    nota

    O comando especifica a opção --platform linux/amd64 para garantir que seu contêiner seja compatível com o ambiente de execução do Lambda, independentemente da arquitetura da sua máquina de compilação. Se você pretende criar uma função do Lambda usando a arquitetura do conjunto de instruções ARM64, certifique-se de alterar o comando para usar a opção --platform linux/arm64 em vez disso.

Use o emulador de interface de runtime para testar a imagem localmente. Você pode criar o emulador em na imagem ou instalá-lo na sua máquina local.

Para instalar o emulador de interface de runtime na sua máquina local
  1. No diretório do projeto, execute o comando a seguir para baixar o emulador de interface de tempo de execução (arquitetura x86-64) GitHub e instalá-lo em sua máquina local.

    Linux/macOS
    mkdir -p ~/.aws-lambda-rie && \ curl -Lo ~/.aws-lambda-rie/aws-lambda-rie https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie && \ chmod +x ~/.aws-lambda-rie/aws-lambda-rie

    Para instalar o emulador arm64, substitua o URL do GitHub repositório no comando anterior pelo seguinte:

    https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie-arm64
    PowerShell
    $dirPath = "$HOME\.aws-lambda-rie" if (-not (Test-Path $dirPath)) { New-Item -Path $dirPath -ItemType Directory } $downloadLink = "https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie" $destinationPath = "$HOME\.aws-lambda-rie\aws-lambda-rie" Invoke-WebRequest -Uri $downloadLink -OutFile $destinationPath

    Para instalar o emulador de arm64, substitua $downloadLink pelo seguinte:

    https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie-arm64
  2. Inicie a imagem do Docker com o comando docker run. Observe o seguinte:

    • docker-image é o nome da imagem e test é a tag.

    • /usr/local/bin/npx aws-lambda-ric index.handler é o ENTRYPOINT seguido pelo CMD do Dockerfile.

    Linux/macOS
    docker run --platform linux/amd64 -d -v ~/.aws-lambda-rie:/aws-lambda -p 9000:8080 \ --entrypoint /aws-lambda/aws-lambda-rie \ docker-image:test \ /usr/local/bin/npx aws-lambda-ric index.handler
    PowerShell
    docker run --platform linux/amd64 -d -v "$HOME\.aws-lambda-rie:/aws-lambda" -p 9000:8080 ` --entrypoint /aws-lambda/aws-lambda-rie ` docker-image:test ` /usr/local/bin/npx aws-lambda-ric index.handler

    Esse comando executa a imagem como um contêiner e cria um endpoint local em localhost:9000/2015-03-31/functions/function/invocations.

    nota

    Se você criou a imagem do Docker para a arquitetura do conjunto de instruções ARM64, certifique-se de usar a opção --platform linux/arm64, em vez de --platform linux/amd64.

  3. Publique um evento no endpoint local.

    Linux/macOS

    No Linux e no MacOS, execute o seguinte comando curl:

    curl "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{}'

    Esse comando invoca a função com um evento vazio e retorna uma resposta. Caso esteja usando seu próprio código de função em vez do código de função de exemplo, você talvez queira invocar a função com uma carga útil JSON. Exemplo:

    curl "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{"payload":"hello world!"}'
    PowerShell

    Em PowerShell, execute o seguinte Invoke-WebRequest comando:

    Invoke-WebRequest -Uri "http://localhost:9000/2015-03-31/functions/function/invocations" -Method Post -Body '{}' -ContentType "application/json"

    Esse comando invoca a função com um evento vazio e retorna uma resposta. Caso esteja usando seu próprio código de função em vez do código de função de exemplo, você talvez queira invocar a função com uma carga útil JSON. Exemplo:

    Invoke-WebRequest -Uri "http://localhost:9000/2015-03-31/functions/function/invocations" -Method Post -Body '{"payload":"hello world!"}' -ContentType "application/json"
  4. Obtenha o ID do contêiner.

    docker ps
  5. Use o comando docker kill para parar o contêiner. Nesse comando, substitua 3766c4ab331c pelo ID do contêiner da etapa anterior.

    docker kill 3766c4ab331c
Para enviar a imagem ao Amazon ECR e criar a função do Lambda
  1. Execute o get-login-passwordcomando para autenticar a CLI do Docker no seu registro do Amazon ECR.

    • Defina o valor --region para a Região da AWS onde você deseja criar o repositório do Amazon ECR.

    • Substituir 111122223333 por seu ID da Conta da AWS.

    aws ecr get-login-password --region us-east-1 | docker login --username AWS --password-stdin 111122223333.dkr.ecr.us-east-1.amazonaws.com
  2. Crie um repositório no Amazon ECR usando o comando create-repository.

    aws ecr create-repository --repository-name hello-world --region us-east-1 --image-scanning-configuration scanOnPush=true --image-tag-mutability MUTABLE
    nota

    O repositório do Amazon ECR deve estar na mesma Região da AWS que a função do Lambda.

    Se tiver êxito, você verá uma resposta como esta:

    { "repository": { "repositoryArn": "arn:aws:ecr:us-east-1:111122223333:repository/hello-world", "registryId": "111122223333", "repositoryName": "hello-world", "repositoryUri": "111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world", "createdAt": "2023-03-09T10:39:01+00:00", "imageTagMutability": "MUTABLE", "imageScanningConfiguration": { "scanOnPush": true }, "encryptionConfiguration": { "encryptionType": "AES256" } } }
  3. Copie o repositoryUri da saída na etapa anterior.

  4. Execute o comando docker tag para aplicar uma tag na sua imagem local em seu repositório do Amazon ECR como a versão mais recente. Neste comando:

    • Substitua docker-image:test pelo nome e tag da sua imagem do Docker.

    • Substitua <ECRrepositoryUri> pelo repositoryUri que você copiou. Certifique-se de incluir :latest no final do URI.

    docker tag docker-image:test <ECRrepositoryUri>:latest

    Exemplo:

    docker tag docker-image:test 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
  5. Execute o comando docker push para implantar a imagem local no repositório do Amazon ECR. Certifique-se de incluir :latest no final do URI do repositório.

    docker push 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
  6. Crie um perfil de execução para a função, caso ainda não tenha um. Você precisará do nome do recurso da Amazon (ARN) do perfil na próxima etapa.

  7. Criar a função do Lambda. Em ImageUri, especifique o URI do repositório anterior. Certifique-se de incluir :latest no final do URI.

    aws lambda create-function \ --function-name hello-world \ --package-type Image \ --code ImageUri=111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest \ --role arn:aws:iam::111122223333:role/lambda-ex
    nota

    É possível criar uma função usando uma imagem em uma conta da AWS diferente desde que a imagem esteja na mesma região da função do Lambda. Para ter mais informações, consulte Permissões entre contas do Amazon ECR.

  8. Invoque a função.

    aws lambda invoke --function-name hello-world response.json

    Você obterá uma resposta parecida com esta:

    { "ExecutedVersion": "$LATEST", "StatusCode": 200 }
  9. Para ver a saída da função, verifique o arquivo response.json.

Para atualizar o código da função, você deve criar a imagem novamente, fazer o upload da nova imagem para o repositório Amazon ECR e, em seguida, usar o update-function-codecomando para implantar a imagem na função Lambda.