

# Node.js를 사용하여 Lambda 함수 빌드
<a name="lambda-nodejs"></a>

AWS Lambda에서 Node.js로 JavaScript 코드를 실행할 수 있습니다. Lambda는 이벤트 처리를 위해 코드를 실행하는 Node.js를 위한 [런타임](lambda-runtimes.md)을 제공합니다. 코드는 사용자가 관리하는 AWS Identity and Access Management(IAM) 역할의 자격 증명을 사용하여 AWS SDK for JavaScript가 포함된 환경에서 실행됩니다. Node.js 런타임에 포함된 SDK 버전에 대해 자세히 알아보려면 [런타임에 포함된 SDK 버전](#nodejs-sdk-included) 섹션을 참조하세요.

Lambda는 다음과 같은 Node.js 런타임을 지원합니다.<a name="nodejs-supported-runtimes"></a>


| 이름 | 식별자 | 운영 체제 | 사용 중단 날짜 | 블록 함수 생성 | 블록 함수 업데이트 | 
| --- | --- | --- | --- | --- | --- | 
|  Node.js 24  |  `nodejs24.x`  |  Amazon Linux 2023  |   2028년 4월 30일   |   2028년 6월 1일   |   2028년 7월 1일   | 
|  Node.js 22  |  `nodejs22.x`  |  Amazon Linux 2023  |   2027년 4월 30일   |   2027년 6월 1일   |   2027년 7월 1일   | 
|  Node.js 20  |  `nodejs20.x`  |  Amazon Linux 2023  |   2026년 4월 30일   |   2026년 8월 31일   |   2026년 9월 30일   | 

**Node.js 함수를 만들려면**

1. [Lambda 콘솔](https://console.aws.amazon.com/lambda)을 엽니다.

1. **함수 생성**을 선택합니다.

1. 다음 설정을 구성합니다:
   + **함수 이름**: 함수의 이름을 입력합니다.
   + **런타임**: **Node.js 24.x**를 선택합니다.

1. **함수 생성**을 선택합니다.

콘솔은 `index.mjs`(이)라는 단일 소스 파일로 Lambda 함수를 생성합니다. 이 파일을 편집하고 기본 제공 코드 편집기에서 더 많은 파일을 추가할 수 있습니다. **배포** 섹션에서 **배포**를 선택하여 함수의 코드를 업데이트하세요. 그런 다음, 코드를 실행하려면 **테스트 이벤트** 섹션에서 **테스트 이벤트 생성**을 선택합니다.

`index.mjs` 파일은 이벤트 객체와 컨텍스트 객체를 취하는 `handler`라는 이름의 함수를 내보냅니다. 이는 함수가 호출될 때 Lambda가 호출하는 [핸들러 함수](nodejs-handler.md)입니다. Node.js 함수 런타임은 Lambda에서 호출 이벤트를 가져와 핸들러로 전달합니다. 함수 구성에서 핸들러 값은 `index.handler`입니다.

함수 코드를 저장하면 Lambda 콘솔에서 .zip 파일 아카이브 배포 패키지를 만듭니다. 콘솔 외부에서 (IDE를 사용해) 함수 코드를 개발하는 경우 Lambda 함수에 코드를 업로드하려면 [배포 패키지를 생성](nodejs-package.md)해야 합니다.

함수 런타임은 호출 이벤트 외에도 컨텍스트 객체를 핸들러에 전달합니다. [컨텍스트 객체](nodejs-context.md)에는 호출, 함수 및 실행 환경에 관한 추가 정보가 포함되어 있습니다. 자세한 내용은 환경 변수에서 확인할 수 있습니다.

Lambda 함수는 CloudWatch Logs 로그 그룹을 함께 제공됩니다. 함수 런타임은 각 호출에 대한 세부 정보를 CloudWatch Logs에 보냅니다. 호출 중 [함수가 출력하는 로그](nodejs-logging.md)를 전달합니다. 함수가 오류를 반환하면 Lambda은 오류에 서식을 지정한 후 이를 간접 호출자에게 반환합니다.

**Topics**
+ [

## 런타임에 포함된 SDK 버전
](#nodejs-sdk-included)
+ [

## TCP 연결에 연결 유지 사용
](#nodejs-keep-alive)
+ [

## CA 인증서 로딩
](#nodejs-certificate-loading)
+ [

## 실험 단계 Node.js 기능
](#nodejs-experimental-features)
+ [

# Node.js에서 Lambda 함수 핸들러 정의
](nodejs-handler.md)
+ [

# .zip 파일 아카이브를 사용하여 Node.js Lambda 함수 배포
](nodejs-package.md)
+ [

# 컨테이너 이미지를 사용하여 Node.js Lambda 함수 배포
](nodejs-image.md)
+ [

# Node.js Lambda 함수를 위한 계층 작업
](nodejs-layers.md)
+ [

# Lambda 컨텍스트 객체를 사용하여 Node.js 함수 정보 검색
](nodejs-context.md)
+ [

# Node.js Lambda 함수 로깅 및 모니터링
](nodejs-logging.md)
+ [

# AWS Lambda에서 Node.js 코드 계측
](nodejs-tracing.md)

## 런타임에 포함된 SDK 버전
<a name="nodejs-sdk-included"></a>

[지원되는 모든 Lambda Node.js 런타임](#nodejs-supported-runtimes)에는 [최신 버전](https://github.com/aws/aws-sdk-js-v3/releases)이 아닌 AWS SDK for JavaScript v3의 특정 마이너 버전이 포함됩니다. 런타임에 포함된 특정 마이너 버전은 런타임 버전과 사용자의 AWS 리전에 따라 달라집니다. 사용 중인 런타임에 포함된 SDK의 특정 버전을 찾으려면 다음 코드를 사용하여 Lambda 함수를 생성합니다.

**Example index.mjs**  

```
import packageJson from '@aws-sdk/client-s3/package.json' with { type: 'json' };

export const handler = async () => ({ version: packageJson.version });
```
다음과 같은 형식으로 응답을 반환합니다.  

```
{
  "version": "3.632.0"
}
```

자세한 내용은 [핸들러에서 SDK for JavaScript v3 사용](nodejs-handler.md#nodejs-example-sdk-usage) 섹션을 참조하세요.

## TCP 연결에 연결 유지 사용
<a name="nodejs-keep-alive"></a>

기본 Node.js HTTP/HTTPS 에이전트는 모든 새 요청에 대해 새로운 TCP 연결을 생성합니다. 새 연결을 설정하는 데 드는 비용을 방지하기 위해 기본적으로 모든 [지원되는 Node.js 런타임](#nodejs-supported-runtimes)에서 연결 유지 기능이 활성화됩니다. 연결 유지는 SDK를 사용하여 여러 API를 호출하는 Lambda 함수의 요청 시간을 줄일 수 있습니다.

연결 유지를 비활성화하려면 **AWS SDK for JavaScript 3.x Developer Guide의 [Reusing connections with keep-alive in Node.js](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/node-reusing-connections.html)를 참조하세요. 연결 유지 사용에 대한 자세한 내용은 AWS Developer Tools Blog의 [HTTP keep-alive is on by default in modular AWS SDK for JavaScript](https://aws.amazon.com/blogs/developer/http-keep-alive-is-on-by-default-in-modular-aws-sdk-for-javascript/)를 참조하세요.

## CA 인증서 로딩
<a name="nodejs-certificate-loading"></a>

Node.js 18까지의 Node.js 런타임 버전에서, Lambda는 Amazon 전용 CA(인증 기관) 인증서를 자동으로 로딩하여 다른 AWS 서비스와 상호 작용하는 함수를 더 쉽게 생성할 수 있습니다. 예를 들어, Lambda에는 Amazon RDS 데이터베이스에 설치된 [서버 ID 인증서](https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/UsingWithRDS.SSL.html)를 검증하는 데 필요한 Amazon RDS 인증서가 포함되어 있습니다. 이 동작은 콜드 스타트 동안 성능에 영향을 미칠 수 있습니다.

Node.js 20부터 Lambda는 더 이상 기본적으로 추가 CA 인증서를 로딩하지 않습니다. Node.js 20 런타임에는 `/var/runtime/ca-cert.pem`에 위치한 모든 Amazon CA 인증서가 있는 인증서 파일이 들어 있습니다. Node.js 18 및 이전 런타임에서 동일한 동작을 복원하려면 `NODE_EXTRA_CA_CERTS` [환경 변수](configuration-envvars.md)를 `/var/runtime/ca-cert.pem`에 설정하십시오.

최적의 성능을 위해 필요한 인증서만 배포 패키지와 함께 번들로 묶고 `NODE_EXTRA_CA_CERTS` 환경 변수를 통해 로딩하는 것이 좋습니다. 인증서 파일은 PEM 형식으로 된 하나 이상의 신뢰할 수 있는 루트 또는 중간 CA 인증서로 구성되어야 합니다. 예를 들어, RDS의 경우 코드 옆에 필수 인증서를 `certificates/rds.pem`으로 포함합니다. 그런 다음 `NODE_EXTRA_CA_CERTS`를 `/var/task/certificates/rds.pem`에 설정하여 인증서를 로딩합니다.

## 실험 단계 Node.js 기능
<a name="nodejs-experimental-features"></a>

업스트림 Node.js 언어 릴리스는 기본적으로 일부 실험 기능을 활성화합니다. Lambda는 런타임 안정성과 일관된 성능을 보장하기 위해 이러한 기능을 비활성화합니다. 다음 표에는 Lambda가 비활성화하는 실험 기능이 나열되어 있습니다.


| 실험 기능 | 지원되는 Node.js 버전 | Lambda에서 적용하는 Node.js 플래그 | 재활성화할 Lambda 플래그 | 
| --- | --- | --- | --- | 
|  ES 모듈에서 요구 사항을 사용하여 모듈 가져오기 지원  |  Node.js 20, Node.js 22  |  `--no-experimental-require-module`  |  `--experimental-require-module`  | 
|  ES 모듈과 CommonJS 모듈 자동 감지 지원  |  Node.js 22  |  `--no-experimental-detect-module`  |  `--experimental-detect-module`  | 

비활성화된 실험 기능을 활성화하려면 `NODE_OPTIONS` 환경 변수에서 다시 활성화 플래그를 설정합니다. 예를 들어 ES 모듈 지원 필요를 활성화하려면 `NODE_OPTIONS`를 `--experimental-require-module`로 설정합니다. Lambda는 이 재정의를 감지하고 해당 비활성화 플래그를 제거합니다.

**중요**  
 실험 기능을 사용하면 불안정 및 성능 문제가 발생할 수 있습니다. 이러한 기능은 향후 Node.js 버전에서 변경되거나 제거될 수 있습니다. 실험 기능을 사용하는 함수는 Lambda 서비스 수준 계약(SLA) 또는 AWS Support 대상이 아닙니다.

# Node.js에서 Lambda 함수 핸들러 정의
<a name="nodejs-handler"></a>

Lambda 함수의 *핸들러*는 이벤트를 처리하는 함수 코드의 메서드입니다. 함수가 간접 호출되면 Lambda는 핸들러 메서드를 실행합니다. 함수는 핸들러가 응답을 반환하거나 종료하거나 제한 시간이 초과될 때까지 실행됩니다.

이 페이지에서는 프로젝트 설정, 이름 지정 규칙, 모범 사례를 포함하여 Node.js에서 Lambda 함수 핸들러를 사용하는 방법을 설명합니다. 이 페이지에는 주문에 대한 정보를 가져와서 텍스트 파일 영수증을 생성하고 해당 파일을 Amazon Simple Storage Service(Amazon S3) 버킷에 넣는 Node.js Lambda 함수의 예제도 포함되어 있습니다. 함수를 작성한 후 배포하는 방법에 대한 자세한 내용은 [.zip 파일 아카이브를 사용하여 Node.js Lambda 함수 배포](nodejs-package.md) 또는 [컨테이너 이미지를 사용하여 Node.js Lambda 함수 배포](nodejs-image.md) 섹션을 참조하세요.

**Topics**
+ [

## Node.js 핸들러 프로젝트 설정
](#nodejs-handler-setup)
+ [

## 예제 Node.js Lambda 함수 코드
](#nodejs-example-code)
+ [

## CommonJS 및 ES 모듈
](#nodejs-commonjs-es-modules)
+ [

## Node.js 초기화
](#nodejs-initialization)
+ [

## 핸들러 이름 지정 규칙
](#nodejs-handler-naming)
+ [

## 입력 이벤트 객체 정의 및 액세스
](#nodejs-example-input)
+ [

## Node.js 함수에 유효한 핸들러 패턴
](#nodejs-handler-signatures)
+ [

## 핸들러에서 SDK for JavaScript v3 사용
](#nodejs-example-sdk-usage)
+ [

## 환경 변수에 액세스
](#nodejs-example-envvars)
+ [

## 전역 상태 사용
](#nodejs-handler-state)
+ [

## Node.js Lambda 함수의 코드 모범 사례
](#nodejs-best-practices)

## Node.js 핸들러 프로젝트 설정
<a name="nodejs-handler-setup"></a>

Node.js Lambda 프로젝트를 초기화하는 방법에는 여러 가지가 있습니다. 예를 들어 `npm`을 사용하여 표준 Node.js 프로젝트를 생성하거나, [AWS SAM 애플리케이션](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/using-sam-cli-init.html#using-sam-cli-init-new)을 생성하거나, [AWS CDK 애플리케이션](lambda-cdk-tutorial.md#lambda-cdk-step-1)을 생성할 수 있습니다.

`npm`을 사용하여 프로젝트를 생성하려면 다음을 수행하세요.

```
npm init
```

이 명령은 프로젝트를 초기화하고 프로젝트의 메타데이터와 종속성을 관리하는 `package.json` 파일을 생성합니다.

함수 코드는 `.js` 또는 `.mjs` JavaScript 파일에 있습니다. 다음 예제에서는 ES 모듈 핸들러를 사용하기 때문에 이 파일의 이름을 `index.mjs`로 지정합니다. Lambda는 ES 모듈과 CommonJS 핸들러 모두 지원합니다. 자세한 내용은 [CommonJS 및 ES 모듈](#nodejs-commonjs-es-modules) 섹션을 참조하세요.

일반적인 Node.js Lambda 함수 프로젝트는 다음과 같은 일반적인 구조를 따릅니다.

```
/project-root
  ├── index.mjs — Contains main handler
  ├── package.json — Project metadata and dependencies
  ├── package-lock.json — Dependency lock file
  └── node_modules/ — Installed dependencies
```

## 예제 Node.js Lambda 함수 코드
<a name="nodejs-example-code"></a>

다음 예제 Lambda 함수 코드는 주문에 대한 정보를 입력으로 가져와서 텍스트 파일 영수증을 생성하고 해당 파일을 Amazon S3 버킷에 넣습니다.

**Example index.mjs Lambda 함수**  

```
import { S3Client, PutObjectCommand } from '@aws-sdk/client-s3';

// Initialize the S3 client outside the handler for reuse
const s3Client = new S3Client();

/**
 * Lambda handler for processing orders and storing receipts in S3.
 * @param {Object} event - Input event containing order details
 * @param {string} event.order_id - The unique identifier for the order
 * @param {number} event.amount - The order amount
 * @param {string} event.item - The item purchased
 * @returns {Promise<string>} Success message
 */
export const handler = async(event) => {
    try {
        // Access environment variables
        const bucketName = process.env.RECEIPT_BUCKET;
        if (!bucketName) {
            throw new Error('RECEIPT_BUCKET environment variable is not set');
        }

        // Create the receipt content and key destination
        const receiptContent = `OrderID: ${event.order_id}\nAmount: $${event.amount.toFixed(2)}\nItem: ${event.item}`;
        const key = `receipts/${event.order_id}.txt`;

        // Upload the receipt to S3
        await uploadReceiptToS3(bucketName, key, receiptContent);

        console.log(`Successfully processed order ${event.order_id} and stored receipt in S3 bucket ${bucketName}`);
        return 'Success';
    } catch (error) {
        console.error(`Failed to process order: ${error.message}`);
        throw error;
    }
};

/**
 * Helper function to upload receipt to S3
 * @param {string} bucketName - The S3 bucket name
 * @param {string} key - The S3 object key
 * @param {string} receiptContent - The content to upload
 * @returns {Promise<void>}
 */
async function uploadReceiptToS3(bucketName, key, receiptContent) {
    try {
        const command = new PutObjectCommand({
            Bucket: bucketName,
            Key: key,
            Body: receiptContent
        });

        await s3Client.send(command);
    } catch (error) {
        throw new Error(`Failed to upload receipt to S3: ${error.message}`);
    }
}
```

`index.mjs` 파일은 다음 코드 섹션을 포함하고 있습니다.
+ `import` 블록: 이 블록을 사용하여 [AWS SDK 클라이언트](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/the-request-object.html) 등 Lambda 함수에 필요한 라이브러리를 포함할 수 있습니다.
+ `const s3Client` 선언: 핸들러 함수 외부에서 [Amazon S3 클라이언트](https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/client/s3/)를 초기화합니다. 그러면 [초기화 단계](lambda-runtime-environment.md#runtimes-lifecycle-ib)에서 Lambda가 이 코드를 실행하고 클라이언트는 [여러 간접 호출에서 재사용](lambda-runtime-environment.md#execution-environment-reuse)할 수 있도록 보존됩니다.
+ JSDoc 주석 블록: [JSDoc 주석](https://jsdoc.app/about-getting-started)을 사용하여 핸들러의 입력 및 출력 유형을 정의합니다.
+ `export const handler`: Lambda가 간접적으로 호출하는 주요 핸들러 함수입니다. 함수를 배포할 때 [Handler](https://docs.aws.amazon.com/lambda/latest/api/API_CreateFunction.html#lambda-CreateFunction-request-Handler) 속성에 `index.handler`를 지정합니다. `Handler` 속성 값은 파일 이름과 내보낸 핸들러 메서드의 이름이며, 점으로 구분됩니다.
+ `uploadReceiptToS3` 함수: 기본 핸들러 함수에서 참조하는 도우미 함수입니다.

이 함수가 제대로 작동하려면 [실행 역할](lambda-intro-execution-role.md)이 `s3:PutObject` 작업을 허용해야 합니다. 또한 `RECEIPT_BUCKET` 환경 변수를 정의해야 합니다. 성공적으로 간접 호출되면 Amazon S3 버킷은 영수증 파일을 포함합니다.

## CommonJS 및 ES 모듈
<a name="nodejs-commonjs-es-modules"></a>

Node.js는 CommonJS와 ECMAScript 모듈(ES 모듈)이라는 2가지 모듈 시스템을 지원합니다. Lambda에서는 [실행 환경 초기화](#nodejs-initialization) 도중 비동기식 태스크를 완료할 수 있는 최상위 레벨 대기를 지원하므로 ES 모듈 사용이 권장됩니다.

Node.js는 파일 확장자가 `.cjs`인 파일을 CommonJS 모듈로 취급하는 반면 `.mjs` 확장자는 ES 모듈을 나타냅니다. 기본적으로 Node.js는 파일 확장자가 `.js`인 파일을 CommonJS 모듈로 취급합니다. 함수의 `package.json` 파일에서 `type`을 `module`로 지정하여 `.js` 파일을 ES 모듈로 처리하도록 Node.js를 구성할 수 있습니다. `NODE_OPTIONS` 환경 변수에 `—experimental-detect-module` 플래그를 추가하여 `.js` 파일을 CommonJS 또는 ES 모듈로 처리해야 하는지 여부를 자동으로 감지하도록 Node.js를 Lambda에서 구성할 수 있습니다. 자세한 내용은 [실험 단계 Node.js 실험 기능](lambda-nodejs.md#nodejs-experimental-features)을 참조하세요.

다음 예제에서는 ES 모듈과 CommonJS 모듈을 모두 사용하여 작성된 함수 핸들러를 보여줍니다. 이 페이지의 나머지 예제에서는 모두 ES 모듈을 사용합니다.

------
#### [ ES module example ]

**Example - ES 모듈 핸들러**  

```
const url = "https://aws.amazon.com/";

export const handler = async(event) => {
    try {
        const res = await fetch(url);
        console.info("status", res.status);
        return res.status;
    }
    catch (e) {
        console.error(e);
        return 500;
    }
};
```

------
#### [ CommonJS module example ]

**Example - CommonJS 모듈 핸들러**  

```
const https = require("https");
let url = "https://aws.amazon.com/";

exports.handler = async function (event) {
  let statusCode;
  await new Promise(function (resolve, reject) {
    https.get(url, (res) => {
        statusCode = res.statusCode;
        resolve(statusCode);
      }).on("error", (e) => {
        reject(Error(e));
      });
  });
  console.log(statusCode);
  return statusCode;
};
```

------

## Node.js 초기화
<a name="nodejs-initialization"></a>

Node.js는 이벤트 루프를 사용하는 효율적인 비동기 작업을 지원하는 비차단 I/O 모델을 사용합니다. 예를 들어 Node.js가 네트워크를 직접 호출할 때 함수는 네트워크 응답을 차단하지 않고 다른 작업을 계속 처리합니다. 네트워크 응답이 수신되면 콜백 대기열에 배치됩니다. 대기열의 태스크는 현재 태스크가 완료되면 처리됩니다.

Lambda에서는 실행 환경 초기화 도중 시작된 비동기식 태스크가 초기화 중에 완료되도록 최상위 레벨 대기 사용이 권장됩니다. 초기화 중에 완료되지 않은 비동기식 태스크는 일반적으로 첫 번째 함수 간접 호출 중에 실행됩니다. 이 경우 예상하지 못한 동작 또는 오류가 발생할 수 있습니다. 예를 들어 함수 초기화로 네트워크를 직접 호출하고 AWS Parameter Store에서 파라미터를 가져올 수 있습니다. 초기화 도중 이 태스크가 완료되지 않으면 간접 호출 중에 값이 null일 수 있습니다. 또한 초기화와 간접 호출 간에 지연이 발생하여 시간에 민감한 작업에서 오류가 트리거될 수 있습니다. 특히 AWS 서비스 직접 호출은 시간에 민감한 요청 서명을 사용할 수 있습니다. 초기화 단계 중에 직접 호출이 완료되지 않으면 서비스 호출에 실패합니다. 초기화 중에 태스크를 완료하면 일반적으로 콜드 스타트 성능이 향상되고 프로비저닝된 동시성을 사용할 때 첫 번째 간접 호출 성능이 향상됩니다. 자세한 내용과 예제는 [AWS Lambda에서 Node.js ES 모듈 및 최상위 레벨 대기](https://aws.amazon.com/blogs/compute/using-node-js-es-modules-and-top-level-await-in-aws-lambda)를 참조하세요.

## 핸들러 이름 지정 규칙
<a name="nodejs-handler-naming"></a>

함수를 구성할 때 [핸들러](https://docs.aws.amazon.com/lambda/latest/api/API_CreateFunction.html#lambda-CreateFunction-request-Handler) 설정 값은 파일 이름과 내보낸 핸들러 메서드의 이름이며, 점으로 구분됩니다. 콘솔에서 생성된 함수의 기본값은 예를 들어, 이 가이드에서는 `index.handler`입니다. 이는 `index.js` 또는 `index.mjs` 파일에서 내보낸 `handler` 메서드를 나타냅니다.

콘솔에서 다른 파일 이름 또는 함수 핸들러 이름을 사용하여 함수를 생성하는 경우 기본 핸들러 이름을 편집해야 합니다.

**함수 핸들러 이름 변경(콘솔)**

1. Lambda 콘솔의 [함수](https://console.aws.amazon.com/lambda/home#/functions) 페이지를 열고 함수를 선택합니다.

1. **Code**(코드) 탭을 선택합니다.

1. 아래로 스크롤하여 **런타임 설정** 창으로 이동한 다음 **편집**을 선택합니다.

1. **핸들러**에서 함수 핸들러의 새 이름을 입력합니다.

1. **저장**을 선택합니다.

## 입력 이벤트 객체 정의 및 액세스
<a name="nodejs-example-input"></a>

JSON은 Lambda 함수의 가장 일반적인 표준 입력 형식입니다. 이 예제에서 함수는 다음과 유사한 입력을 예상합니다.

```
{
    "order_id": "12345",
    "amount": 199.99,
    "item": "Wireless Headphones"
}
```

Node.js에서 Lambda 함수로 작업할 때 JSDoc 주석을 사용하여 입력 이벤트의 예상되는 셰이프를 정의할 수 있습니다. 이 예제에서는 핸들러의 JSDoc 주석에 입력 구조를 정의합니다.

```
/**
 * Lambda handler for processing orders and storing receipts in S3.
 * @param {Object} event - Input event containing order details
 * @param {string} event.order_id - The unique identifier for the order
 * @param {number} event.amount - The order amount
 * @param {string} event.item - The item purchased
 * @returns {Promise<string>} Success message
 */
```

JSDoc 주석에 이러한 유형을 정의한 후 코드에서 직접 이벤트 객체의 필드에 액세스할 수 있습니다. 예를 들어 `event.order_id`는 원래 입력에서 `order_id`의 값을 검색합니다.

## Node.js 함수에 유효한 핸들러 패턴
<a name="nodejs-handler-signatures"></a>

[콜백](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/using-a-callback-function.html)을 사용하는 대신 [async/await](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/using-async-await.html)를 사용하여 함수 핸들러를 선언하는 것이 좋습니다. async/await는 중첩된 콜백이나 체인 프라미스 없이 비동기 코드를 작성할 수 있는 간결하고 읽기 쉬운 방법입니다. 비동기/대기를 사용하면 비동기 및 비차단 상태를 유지하면서 동기 코드처럼 읽는 코드를 작성할 수 있습니다.

### 비동기 함수 핸들러(권장)
<a name="nodejs-handler-async"></a>

`async` 키워드는 함수를 비동기로 표시하고 `await` 키워드는 `Promise`이 해결될 때까지 함수 실행을 일시 중지합니다. 핸들러에 사용할 수 있는 인수는 다음과 같습니다.
+ `event`: 함수에 전달된 입력 데이터가 들어 있습니다.
+ `context`: 간접 호출, 함수 및 실행 환경에 대한 정보가 들어 있습니다. 자세한 내용은 [Lambda 컨텍스트 객체를 사용하여 Node.js 함수 정보 검색](nodejs-context.md) 섹션을 참조하세요.

다음은 async/await 패턴에 유효한 서명입니다.

```
export const handler = async (event) => { };
```

```
export const handler = async (event, context) => { };
```

### 동기 함수 핸들러
<a name="nodejs-handler-synchronous"></a>

함수가 비동기식 태스크를 수행하지 않는 경우 다음 함수 서명 중 하나를 사용하여 동기식 함수 핸들러를 사용할 수 있습니다.

```
export const handler = (event) => { };
```

```
export const handler = (event, context) => { };
```

### 응답 스트리밍 함수 핸들러
<a name="nodejs-handler-response-streaming"></a>

Lambda는 Node.js를 사용한 응답 스트리밍을 지원합니다. 응답 스트리밍 함수 핸들러는 `awslambda.streamifyResponse()` 데코레이터를 사용하고 `event`, `responseStream`, `context`라는 3가지 파라미터를 사용합니다. 함수 서명은 다음과 같습니다.

```
export const handler = awslambda.streamifyResponse(async (event, responseStream, context) => { });
```

자세한 내용은 [Lambda 함수에 대한 응답 스트리밍](configuration-response-streaming.md) 섹션을 참조하세요.

### 콜백 기반 함수 핸들러
<a name="nodejs-handler-callback"></a>

**참고**  
콜백 기반 함수 핸들러는 Node.js 22까지만 지원됩니다. Node.js 24부터 비동기식 태스크는 비동기 함수 핸들러를 사용하여 구현해야 합니다.

콜백 기반 함수 핸들러는 이벤트, 컨텍스트 및 콜백 인수를 사용해야 합니다. 예제:

```
export const handler = (event, context, callback) => { };
```

콜백 함수는 `Error`와 JSON 직렬화가 가능한 응답을 예상합니다. [이벤트 루프](https://nodejs.org/en/docs/guides/event-loop-timers-and-nexttick/)가 비어 있거나 함수 시간이 초과될 때까지 함수가 계속 실행됩니다. 응답은 모든 이벤트 루프 작업이 완료될 때까지 간접 호출자에게 전송되지 않습니다. 함수 제한 시간을 초과하면, 대신 오류가 반환됩니다. [context.callbackWaitsForEmptyEventLoop](nodejs-context.md)를 false로 설정하여 즉시 응답을 전송하도록 런타임을 구성할 수 있습니다.

**Example – callback으로 HTTP 요청**  
다음 예제 함수는 URL을 확인하고 상태 코드를 간접 호출자에게 반환합니다.  

```
import https from "https";
let url = "https://aws.amazon.com/";

export const handler = (event, context, callback) => {
  https.get(url, (res) => {
    callback(null, res.statusCode);
  }).on("error", (e) => {
    callback(Error(e));
  });
};
```

## 핸들러에서 SDK for JavaScript v3 사용
<a name="nodejs-example-sdk-usage"></a>

종종 Lambda 함수를 사용하여 다른 AWS 리소스와 상호 작용하거나 업데이트하는 경우가 있습니다. 이러한 리소스와 상호 작용하는 가장 간단한 방법은 AWS SDK for JavaScript를 사용하는 것입니다. [지원되는 모든 Lambda Node.js 런타임](lambda-nodejs.md#nodejs-supported-runtimes)에는 [SDK for JavaScript 버전 3](https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/introduction/)가 포함되어 있습니다. 그러나 배포 패키지에 필요한 AWS SDK 클라이언트를 포함하는 것이 좋습니다. 이렇게 하면 향후 Lambda 런타임 업데이트 중 [이전 버전과의 호환성](runtimes-update.md#runtime-update-compatibility)이 극대화됩니다. Lambda 콘솔 코드 편집기를 사용하거나 AWS CloudFormation 템플릿에서 인라인 코드를 사용하는 경우와 같이 추가 패키지를 포함할 수 없는 경우에만 런타임 제공 SDK를 사용하세요.

함수에 SDK 종속성을 추가하려면 필요한 특정 SDK 클라이언트에 `npm install` 명령을 사용하세요. 예제 코드에서는 [Amazon S3 클라이언트](https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/client/s3/)를 사용했습니다. `package.json` 파일이 포함된 디렉터리에서 다음 명령을 실행하여 이러한 종속성을 추가합니다.

```
npm install @aws-sdk/client-s3
```

예제 함수와 같이 함수 코드에서 필요한 클라이언트와 명령을 가져옵니다.

```
import { S3Client, PutObjectCommand } from '@aws-sdk/client-s3';
```

그런 다음 [Amazon S3 클라이언트](https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/client/s3/)를 초기화합니다.

```
const s3Client = new S3Client();
```

이 예제에서는 함수를 간접적으로 호출할 때마다 초기화할 필요가 없도록 기본 핸들러 함수에서 Amazon S3 클라이언트를 초기화했습니다. SDK 클라이언트를 초기화한 후 이를 사용하여 해당 AWS 서비스에 대한 API 직접 호출을 수행할 수 있습니다. 예제 코드는 다음과 같이 Amazon S3 [PutObject](https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/client/s3/command/PutObjectCommand/) API 작업을 직접적으로 호출합니다.

```
const command = new PutObjectCommand({
    Bucket: bucketName,
    Key: key,
    Body: receiptContent
});
```

## 환경 변수에 액세스
<a name="nodejs-example-envvars"></a>

핸들러 코드에서 `process.env`를 사용하여 모든 [환경 변수](configuration-envvars.md)를 참조할 수 있습니다. 이 예제에서는 다음 코드 줄을 사용하여 정의된 `RECEIPT_BUCKET` 환경 변수를 참조합니다.

```
// Access environment variables
const bucketName = process.env.RECEIPT_BUCKET;
if (!bucketName) {
    throw new Error('RECEIPT_BUCKET environment variable is not set');
}
```

## 전역 상태 사용
<a name="nodejs-handler-state"></a>

Lambda는 함수를 처음 간접적으로 호출하기 전 [초기화 단계](lambda-runtime-environment.md#runtimes-lifecycle-ib)에서 정적 코드를 실행합니다. 초기화 중에 생성된 리소스는 간접 호출 간의 메모리에 남아 있으므로 함수를 호출할 때마다 메모리를 생성할 필요가 없습니다.

예제 코드에서 S3 클라이언트 초기화 코드는 핸들러 외부에 있습니다. 런타임은 함수가 첫 번째 이벤트를 처리하기 전에 클라이언트를 초기화하며, 클라이언트는 모든 간접 호출에서 재사용할 수 있는 상태로 유지됩니다.

## Node.js Lambda 함수의 코드 모범 사례
<a name="nodejs-best-practices"></a>

Lambda 함수를 빌드할 때 다음 지침을 따르세요.
+ **핵심 로직에서 Lambda 핸들러를 분리합니다.** 이를 통해 단위 테스트를 수행할 수 있는 더 많은 함수를 만들 수 있습니다.
+ **함수 배포 패키지의 종속성을 제어합니다.** AWS Lambda 실행 환경에는 여러 라이브러리가 포함되어 있습니다. Node.js 및 Python 런타임의 경우, 여기에는 AWS SDK가 포함됩니다. 최신 기능 및 보안 업데이트를 활성화하려면 Lambda가 주기적으로 이러한 라이브러리를 업데이트해야 합니다. 이러한 업데이트는 Lambda 함수의 동작에 사소한 변화를 가져올 수 있습니다. 함수가 사용하는 종속성을 완전히 제어하려면 모든 종속성을 배포 패키지로 패키징하세요.
+ **종속성의 복잡성을 최소화합니다.** [실행 환경](lambda-runtime-environment.md) 시작 시 빠르게 로드되는 더 단순한 프레임워크가 권장됩니다.
+ **배포 패키지 크기를 런타임 필요에 따라 최소화합니다.** 이렇게 하면 호출 전에 배포 패키지를 다운로드하고 압축을 풀 때 걸리는 시간이 단축됩니다.

**실행 환경 재사용을 활용하여 함수 성능을 향상시킵니다.** 함수 핸들러 외부에서 SDK 클라이언트 및 데이터베이스 연결을 초기화하고 정적 자산을 `/tmp` 디렉토리에 로컬로 캐시합니다. 동일한 함수 인스턴스에서 처리하는 후속 간접 호출은 이러한 리소스를 재사용할 수 있습니다. 이를 통해 함수 실행 시간을 줄여 비용을 절감합니다.

호출에서 발생할 수 있는 데이터 유출을 방지하려면 실행 환경을 사용하여 사용자 데이터, 이벤트 또는 보안과 관련된 기타 정보를 저장하지 마세요. 함수가 핸들러 내부 메모리에 저장할 수 없는 변경 가능한 상태에 의존하는 경우 각 사용자에 대해 별도의 함수 또는 별도의 함수 버전을 생성하는 것이 좋습니다.

**연결 유지 지시문을 사용하여 지속적인 연결을 유지하세요.** Lambda는 시간이 지남에 따라 유휴 연결을 제거합니다. 함수를 호출할 때 유휴 연결을 재사용하려고 하면 연결 오류가 발생합니다. 지속적인 연결을 유지하려면 런타임과 관련된 연결 유지 지시문을 사용하세요. 예를 들어, [Node.js에서 연결 유지를 이용해 연결 재사용](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/node-reusing-connections.html)을 참조하세요.

** [환경 변수](configuration-envvars.md)를 사용하여 함수에 운영 파라미터를 전달합니다.** 예를 들어, Amazon S3 버킷에 기록하는 경우 기록하고 있는 버킷 이름을 하드 코딩하는 대신 환경 변수로 구성합니다.

Lambda 함수에서 함수가 자기 자신을 간접적으로 간접 호출하거나 함수를 다시 간접적으로 간접 호출할 수 있는 프로세스를 시작하는 **재귀적 간접 호출을 사용하지 마세요**. 리커시브 코드를 사용할 경우, 의도하지 않은 함수 호출이 증가하고 비용이 상승할 수 있습니다. 의도치 않게 간접 호출이 대량으로 발생하는 경우 함수의 예약된 동시성을 즉시 `0`으로 설정하여 코드를 업데이트하는 동안 해당 함수에 대한 모든 간접 호출을 제한합니다.

Lambda 함수 코드에는 **문서화되지 않은 비공개 API를 사용하지 마세요.** AWS Lambda 관리형 런타임의 경우, Lambda는 주기적으로 보안 및 기능 업데이트를 Lambda의 내부 API에 적용합니다. 이러한 내부 API 업데이트는 이전 버전과 호환되지 않으므로 함수가 이러한 비공개 API에 종속성을 갖는 경우 호출 실패와 같은 의도하지 않은 결과를 초래할 수 있습니다. 공개적으로 사용 가능한 API의 목록은 [API 레퍼런스](https://docs.aws.amazon.com/lambda/latest/api/welcome.html)를 참조하세요.

**멱등성 코드를 작성합니다.** 함수에 멱등성 코드를 작성하면 중복 이벤트가 동일한 방식으로 처리됩니다. 코드는 이벤트를 올바르게 검증하고 중복 이벤트를 정상적으로 처리해야 합니다. 자세한 내용은 [멱등성 Lambda 함수를 만들려면 어떻게 해야 합니까?](https://aws.amazon.com/premiumsupport/knowledge-center/lambda-function-idempotent/) 단원을 참조하십시오.

# .zip 파일 아카이브를 사용하여 Node.js Lambda 함수 배포
<a name="nodejs-package"></a>

 AWS Lambda 함수의 코드는 코드가 의존하는 추가 패키지 및 모듈과 함께 함수의 핸들러 코드를 포함하는 .js 또는 .mjs 파일로 구성됩니다. Lambda에 이 함수 코드를 배포하려면 *배포 패키지*를 사용합니다. 이 패키지는 .zip 파일 아카이브 또는 컨테이너 이미지일 수 있습니다. Node.js에서 컨테이너 이미지를 사용하는 방법에 대한 자세한 내용은 [컨테이너 이미지를 사용하여 Node.js Lambda 함수 배포](https://docs.aws.amazon.com/lambda/latest/dg/nodejs-image.html)를 참조하세요.

 배포 패키지를 .zip 파일 아카이브로 생성하려면 명령줄 도구의 기본 제공 .zip 파일 아카이브 유틸리티 또는 [7zip](https://www.7-zip.org/download.html)과 같은 기타 .zip 파일 유틸리티를 사용합니다. 다음 섹션에 표시된 예제에서는 Linux 또는 MacOS 환경에서 명령줄 `zip` 도구를 사용한다고 가정합니다. Windows에서 동일한 명령을 사용하려면 [Windows Subsystem for Linux를 설치](https://docs.microsoft.com/en-us/windows/wsl/install-win10)하여 Ubuntu 및 Bash의 Windows 통합 버전을 가져옵니다.

 Lambda는 POSIX 파일 권한을 사용하므로 .zip 파일 아카이브를 생성하기 전에 [배포 패키지 폴더에 대한 권한을 설정](https://aws.amazon.com/premiumsupport/knowledge-center/lambda-deployment-package-errors/)해야 할 수 있습니다.

**Topics**
+ [

## Node.js의 런타임 종속 항목
](#nodejs-package-dependencies)
+ [

## 종속 항목이 없는 .zip 배포 패키지 생성
](#nodejs-package-create-no-dependencies)
+ [

## 종속 항목이 있는 .zip 배포 패키지 생성
](#nodejs-package-create-dependencies)
+ [

## 종속 항목을 위한 Node.js 계층 생성
](#nodejs-package-dependencies-layers)
+ [

## 종속 항목 검색 경로 및 런타임 포함 라이브러리
](#nodejs-package-searchpath)
+ [

## .zip 파일을 사용하여 Node.js Lambda 함수 생성 및 업데이트
](#nodejs-package-create-update)

## Node.js의 런타임 종속 항목
<a name="nodejs-package-dependencies"></a>

 Node.js 런타임을 사용하는 Lambda 함수의 경우 종속 항목은 모든 Node.js 모듈일 수 있습니다. Node.js 런타임에는 여러 공통 라이브러리와 AWS SDK for JavaScript의 버전이 포함되어 있습니다. [지원되는 모든 Node.js 런타임](lambda-nodejs.md#nodejs-supported-runtimes)에는 SDK 버전 3가 포함되어 있습니다. SDK 버전 2를 사용하려면 .zip 파일 배포 패키지에 SDK를 추가하세요. 사용 중인 런타임에 포함된 SDK 버전을 찾으려면 [런타임에 포함된 SDK 버전](lambda-nodejs.md#nodejs-sdk-included) 섹션을 참조하세요.

 Lambda는 최신 기능 및 보안 업그레이드를 포함하도록 Node.js 런타임에서 SDK 라이브러리를 주기적으로 업데이트합니다. Lambda는 런타임에 포함된 다른 라이브러리에도 보안 패치와 업데이트를 적용합니다. 패키지의 종속 항목을 완벽하게 제어하려면 런타임에 포함된 종속 항목의 원하는 버전을 배포 패키지에 추가하면 됩니다. 예를 들어 JavaScript용 SDK의 특정 버전을 사용하려는 경우 .zip 파일에 종속 항목으로 포함할 수 있습니다. .zip 파일에 런타임 포함 종속 항목을 추가하는 방법에 대한 자세한 내용은 [종속 항목 검색 경로 및 런타임 포함 라이브러리](#nodejs-package-searchpath) 단원을 참조하세요.

 [AWS Shared Responsibility Model](lambda-runtimes.md#runtimes-shared-responsibility)에서는 사용자가 함수의 배포 패키지에 있는 모든 종속 항목을 관리해야 합니다. 여기에는 업데이트 및 보안 패치 적용이 포함됩니다. 함수의 배포 패키지에서 종속 항목을 업데이트하려면 먼저 새 .zip 파일을 생성한 다음 Lambda에 업로드합니다. 자세한 내용은 [종속 항목이 있는 .zip 배포 패키지 생성](#nodejs-package-create-dependencies) 및 [.zip 파일을 사용하여 Node.js Lambda 함수 생성 및 업데이트](#nodejs-package-create-update) 섹션을 참조하세요.

## 종속 항목이 없는 .zip 배포 패키지 생성
<a name="nodejs-package-create-no-dependencies"></a>

 함수 코드에 Lambda 런타임에 포함된 라이브러리를 제외하고 종속 항목이 없는 경우 .zip 파일에는 함수의 핸들러 코드가 포함된 `index.js` 또는 `index.mjs` 파일만 포함됩니다. 선호하는 zip 유틸리티를 사용하여 루트에 `index.js` 또는 `index.mjs` 파일이 있는 .zip 파일을 생성합니다. 핸들러 코드가 포함된 파일이 .zip 파일의 루트에 없는 경우 Lambda가 코드를 실행할 수 없습니다.

 .zip 파일을 배포하여 새 Lambda 함수를 생성하거나 기존 함수를 업데이트하는 방법을 알아보려면 [.zip 파일을 사용하여 Node.js Lambda 함수 생성 및 업데이트](#nodejs-package-create-update) 섹션을 참조하세요.

## 종속 항목이 있는 .zip 배포 패키지 생성
<a name="nodejs-package-create-dependencies"></a>

함수 코드가 Lambda Node.js 런타임에 포함되지 않은 패키지 또는 모듈에 종속되어 있는 경우, 함수 코드와 함께 이러한 종속 항목을 .zip 파일에 추가하거나 [Lambda 계층](chapter-layers.md)을 사용할 수 있습니다. 이 섹션의 지침에서는 .zip 배포 패키지에 종속 항목을 포함하는 방법을 보여줍니다. 계층에 종속 항목을 포함하는 방법에 대한 지침은 [종속 항목을 위한 Node.js 계층 생성](#nodejs-package-dependencies-layers) 섹션을 참조하세요.

다음 예제 CLI 명령은 함수의 핸들러 코드와 해당 종속 항목이 포함된 `index.js` 또는 `index.mjs` 파일이 포함된 `my_deployment_package.zip`이라는 이름의 .zip 파일을 생성합니다. 이 예제에서는 npm 패키지 관리자를 사용하여 종속 항목을 설치합니다.

**배포 패키지를 만드는 방법**

1. `index.js` 또는 `index.mjs` 소스 코드 파일이 포함된 프로젝트 디렉터리로 이동합니다. 이 예에서 디렉터리 이름은 `my_function`입니다.

   ```
   cd my_function
   ```

1. `npm install` 명령을 사용하여 함수의 필수 라이브러리를 `node_modules` 디렉터리에 설치합니다. 이 예제에서는 AWS X-Ray SDK for Node.js를 설치합니다.

   ```
   npm install aws-xray-sdk
   ```

   그러면 다음과 유사한 폴더 구조가 생성됩니다.

   ```
   ~/my_function
   ├── index.mjs
   └── node_modules
       ├── async
       ├── async-listener
       ├── atomic-batcher
       ├── aws-sdk
       ├── aws-xray-sdk
       ├── aws-xray-sdk-core
   ```

   배포 패키지에 직접 만든 사용자 지정 모듈을 추가할 수도 있습니다. `node_modules` 아래에 모듈 이름으로 디렉터리를 만들고 사용자 지정 작성 패키지를 저장합니다.

1. 루트에 프로젝트 폴더의 콘텐츠가 포함된 .zip 파일을 만듭니다. `r` (재귀) 옵션을 사용하여 zip이 하위 폴더를 압축하는지 확인합니다.

   ```
   zip -r my_deployment_package.zip .
   ```

## 종속 항목을 위한 Node.js 계층 생성
<a name="nodejs-package-dependencies-layers"></a>

이 섹션의 지침은 계층에 종속 항목을 포함하는 방법을 보여줍니다. 배포 패키지에 종속 항목을 포함하는 방법에 대한 지침은 [종속 항목이 있는 .zip 배포 패키지 생성](#nodejs-package-create-dependencies) 섹션을 참조하세요.

함수에 계층을 추가하면 Lambda는 계층 콘텐츠를 해당 실행 환경의 `/opt` 디렉터리로 추출합니다. 각 Lambda 런타임에 대해 `PATH` 변수에는 `/opt` 디렉터리 내의 특정 폴더 경로가 이미 포함되어 있습니다. Lambda가 계층 콘텐츠를 가져오도록 하려면 계층 .zip 파일의 종속성이 다음 폴더 경로 중 하나에 있어야 합니다.
+ `nodejs/node_modules`
+ `nodejs/node18/node_modules (NODE_PATH)`
+ `nodejs/node20/node_modules (NODE_PATH)`
+ `nodejs/node22/node_modules (NODE_PATH)`

예를 들어, 계층.zip 파일 구조는 다음과 같을 수 있습니다.

```
xray-sdk.zip
└ nodejs/node_modules/aws-xray-sdk
```

또한 Lambda는 `/opt/lib` 디렉터리의 모든 라이브러리와 `/opt/bin` 디렉터리의 모든 바이너리를 자동으로 감지합니다. Lambda가 계층 콘텐츠를 제대로 찾을 수 있도록 다음 구조로 계층을 생성할 수도 있습니다.

```
custom-layer.zip
└ lib
    | lib_1
    | lib_2
└ bin
    | bin_1
    | bin_2
```

계층을 패키징한 후 [Lambda에서 계층 생성 및 삭제](creating-deleting-layers.md) 및 [함수에 계층 추가](adding-layers.md)을 참조하여 계층 설정을 완료합니다.

## 종속 항목 검색 경로 및 런타임 포함 라이브러리
<a name="nodejs-package-searchpath"></a>

Node.js 런타임에는 여러 공통 라이브러리와 AWS SDK for JavaScript의 버전이 포함되어 있습니다. 런타임에 포함된 라이브러리의 다른 버전을 사용하려면 함수와 함께 번들링하거나 배포 패키지에 종속 항목으로 추가하면 됩니다. 예를 들어 다른 버전의 SDK를 .zip 배포 패키지에 추가하여 사용할 수 있습니다. 함수의 [Lambda 계층](chapter-layers.md)에 포함할 수도 있습니다.

코드에서 `import` 또는 `require` 문을 사용하면 Node.js 런타임은 모듈을 찾을 때까지 `NODE_PATH` 경로의 디렉터리를 검색합니다. 기본적으로 런타임에서 검색하는 첫 번째 위치는.zip 배포 패키지가 압축 해제되고 탑재되는 디렉터리입니다(`/var/task`). 배포 패키지에 런타임 포함 라이브러리 버전을 포함하는 경우 이 버전이 런타임에 포함된 버전보다 우선합니다. 배포 패키지의 종속 항목도 계층의 종속 항목보다 우선합니다.

계층에 종속 항목을 추가하면 Lambda는 이 종속 항목을 `/opt/nodejs/nodexx/node_modules`로 추출합니다. 여기서 `nodexx`는 사용 중인 런타임 버전을 나타냅니다. 검색 경로에서 이 디렉터리는 런타임 포함 라이브러리()가 있는 디렉터리보다 우선합니다`/var/lang/lib/node_modules` 따라서 함수 계층의 라이브러리는 런타임에 포함된 버전보다 우선합니다.

다음 코드 줄을 추가하면 Lambda 함수에 대한 전체 검색 경로를 확인할 수 있습니다.

```
console.log(process.env.NODE_PATH)
```

.zip 패키지 내의 별도 폴더에 종속 항목을 추가할 수도 있습니다. 예를 들어 .zip 패키지의 `common`이라는 폴더에 사용자 지정 모듈을 추가할 수 있습니다. .zip 패키지를 압축 해제하고 탑재하면 `/var/task` 디렉터리 내에 이 폴더가 배치됩니다. 코드에서 .zip 배포 패키지의 폴더에 있는 종속 항목을 사용하려면 CJS 또는 ESM 모듈 해결 방법을 사용하는지 여부에 따라 `import { } from` 또는 `const { } = require()` 문을 사용합니다. 예제:

```
import { myModule } from './common'
```

코드를 `esbuild`, `rollup` 등으로 번들링하는 경우 함수에서 사용하는 종속 항목이 하나 이상의 파일에 함께 번들링됩니다. 가급적 이 방법을 사용하여 종속 항목을 제공하는 것이 좋습니다. 코드를 번들링하면 배포 패키지에 종속 항목을 추가할 때보다 I/O 작업이 줄어들어 성능이 향상됩니다.

## .zip 파일을 사용하여 Node.js Lambda 함수 생성 및 업데이트
<a name="nodejs-package-create-update"></a>

 .zip 배포 패키지를 생성한 후 이를 사용하여 새 Lambda 함수를 생성하거나 기존 함수를 업데이트할 수 있습니다. Lambda 콘솔, AWS Command Line Interface 및 Lambda API를 사용하여 .zip 패키지를 배포할 수 있습니다. AWS Serverless Application Model(AWS SAM) 및 CloudFormation을 사용하여 Lambda 함수를 생성하고 업데이트할 수도 있습니다.

Lambda용 .zip 배포 패키지의 최대 크기는 250MB(압축 해제됨)입니다. 이 제한은 Lambda 계층을 포함하여 업로드하는 모든 파일의 합산 크기에 적용됩니다.

Lambda 런타임은 배포 패키지의 파일을 읽을 수 있는 권한이 필요합니다. Linux 권한 8진수 표기법에서는 Lambda에 실행 불가능한 파일(rw-r--r--)에 대한 644개의 권한과 디렉터리 및 실행 파일에 대한 755개의 권한(rwxr-xr-x)이 필요합니다.

Linux 및 MacOS에서는 `chmod` 명령을 사용하여 배포 패키지의 파일 및 디렉터리에 대한 파일 권한을 변경합니다. 예를 들어 실행 불가능한 파일에 올바른 권한을 부여하려면 다음 명령을 실행합니다.

```
chmod 644 <filepath>
```

Windows에서 파일 권한을 변경하려면 Microsoft Windows 설명서의 [Set, View, Change, or Remove Permissions on an Object](https://learn.microsoft.com/en-us/previous-versions/windows/it-pro/windows-server-2008-R2-and-2008/cc731667(v=ws.10))를 참조하세요.

**참고**  
배포 패키지의 디렉터리에 액세스하는 데 필요한 권한을 Lambda에 부여하지 않으면 Lambda는 해당 디렉터리에 대한 권한을 755(rwxr-xr-x)로 설정합니다.

### 콘솔을 사용하여.zip 파일로 함수 생성 및 업데이트
<a name="nodejs-package-create-console"></a>

 새 함수를 생성하려면 먼저 콘솔에서 함수를 생성한 다음.zip 아카이브를 업로드해야 합니다. 기존 함수를 업데이트하려면 함수에 대한 페이지를 연 다음 동일한 절차에 따라 업데이트된 .zip 파일을 추가합니다.

 .zip 파일이 50MB 미만인 경우 로컬 컴퓨터에서 직접 파일을 업로드하여 함수를 생성하거나 업데이트할 수 있습니다. 50MB보다 큰 .zip 파일의 경우 먼저 패키지를 Amazon S3 버킷에 업로드해야 합니다. AWS Management Console을 사용하여 Amazon S3 버킷에 파일을 업로드하는 방법에 대한 지침은 [Amazon S3 시작하기](https://docs.aws.amazon.com/AmazonS3/latest/userguide/GetStartedWithS3.html)를 참조하세요. AWS CLI를 사용하여 파일을 업로드하려면 **AWS CLI 사용 설명서의 [객체 이동](https://docs.aws.amazon.com/cli/latest/userguide/cli-services-s3-commands.html#using-s3-commands-managing-objects-move)을 참조하세요.

**참고**  
기존 함수의 [배포 패키지 유형](https://docs.aws.amazon.com/lambda/latest/api/API_CreateFunction.html#lambda-CreateFunction-request-PackageType)(.zip 또는 컨테이너 이미지)은 변경할 수 없습니다. 예를 들어 .zip 파일 아카이브를 사용하도록 컨테이너 이미지 함수를 변환할 수는 없습니다. 새로운 함수를 생성해야 합니다.

**새 함수 생성(콘솔)**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)를 열고 **함수 생성**을 선택합니다.

1. **새로 작성**을 선택합니다.

1. **기본 정보**에서 다음과 같이 합니다.

   1. **함수 이름**에 함수 이름을 입력합니다.

   1. **런타임**에서 사용할 런타임을 선택합니다.

   1. (선택 사항) **아키텍처**에서 함수에 대한 명령 세트 아키텍처를 선택합니다. 기본 아키텍처는 x86\$164입니다. 함수에 대한 .zip 배포 패키지가 선택한 명령 세트 아키텍처와 호환되는지 확인합니다.

1. (선택 사항) **권한(Permissions)**에서 **기본 실행 역할 변경(Change default execution role)**을 확장합니다. 새로운 **실행 역할**을 생성하거나 기존 실행 역할을 사용할 수 있습니다.

1. **함수 생성**을 선택합니다. Lambda에서 선택한 런타임을 사용하여 기본 'Hello World' 함수를 생성합니다.

**로컬 시스템에서 .zip 아카이브 업로드(콘솔)**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)에서.zip 파일을 업로드할 함수를 선택합니다.

1. **코드** 탭을 선택합니다.

1. **코드 소스** 창에서 **에서 업로드**를 선택합니다.

1. **.zip 파일**을 선택합니다.

1. .zip 파일을 업로드하려면 다음을 수행합니다.

   1. **업로드**를 선택한 다음 파일 선택기에서.zip 파일을 선택합니다.

   1. **Open**을 선택합니다.

   1. **저장**을 선택합니다.

**Amazon S3 버킷에서.zip 아카이브 업로드(콘솔)**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)에서 새 .zip 파일을 업로드할 함수를 선택합니다.

1. **코드** 탭을 선택합니다.

1. **코드 소스** 창에서 **에서 업로드**를 선택합니다.

1. **Amazon S3 위치**를 선택합니다.

1. .zip 파일의 Amazon S3 링크 URL을 붙여 넣고 **저장**을 선택합니다.

### 콘솔 코드 편집기를 사용하여.zip 파일 함수 업데이트
<a name="nodejs-package-console-edit"></a>

 .zip 배포 패키지를 사용하는 일부 함수의 경우 Lambda 콘솔의 기본 제공 코드 편집기를 사용하여 함수 코드를 직접 업데이트할 수 있습니다. 이 기능을 사용하려면 함수가 다음 조건을 충족해야 합니다.
+ 함수에서 해석된 언어 런타임(Python, Node.js 또는 Ruby) 중 하나를 사용해야 합니다.
+ 함수의 배포 패키지가 50MB(압축 해제)보다 작아야 합니다.

컨테이너 이미지 배포 패키지가 있는 함수의 함수 코드는 콘솔에서 직접 편집할 수 없습니다.

**콘솔 코드 편집기를 사용하여 함수 코드 업데이트**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)를 열고 함수를 선택합니다.

1. **코드** 탭을 선택합니다.

1. **코드 소스** 창에서 소스 코드 파일을 선택하고 통합 코드 편집기에서 편집합니다.

1. **배포** 섹션에서 **배포**를 선택하여 함수의 코드를 업데이트하세요.  
![\[\]](http://docs.aws.amazon.com/ko_kr/lambda/latest/dg/images/getting-started-tutorial/deploy-console.png)

### AWS CLI를 사용하여.zip 파일로 함수 생성 및 업데이트
<a name="nodejs-package-create-cli"></a>

 [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html)를 사용하여 새 함수를 생성하거나.zip 파일로 기존 함수를 업데이트할 수 있습니다. [create-function](https://docs.aws.amazon.com/cli/latest/reference/lambda/create-function.html) 및 [update-function-code](https://docs.aws.amazon.com/cli/latest/reference/lambda/create-function.html) 명령을 사용하여 .zip 패키지를 배포합니다. .zip 파일이 50MB보다 작은 경우 로컬 빌드 시스템의 파일 위치에서 .zip 패키지를 업로드할 수 있습니다. 더 큰 파일의 경우 Amazon S3 버킷에서 .zip 패키지를 업로드해야 합니다. AWS CLI를 사용하여 Amazon S3 버킷에 파일을 업로드하는 방법에 대한 지침은 **AWS CLI 사용 설명서의 [객체 이동](https://docs.aws.amazon.com/cli/latest/userguide/cli-services-s3-commands.html#using-s3-commands-managing-objects-move)을 참조하세요.

**참고**  
AWS CLI를 사용하여 Amazon S3 버킷에서 .zip 파일을 업로드하는 경우 버킷은 함수와 동일한 AWS 리전에 있어야 합니다.

 AWS CLI에서 .zip 파일을 사용하여 새 함수를 생성하려면 다음을 지정해야 합니다.
+ 함수의 이름(`--function-name`)
+ 함수의 런타임(`--runtime`)
+ 함수의 [실행 역할](https://docs.aws.amazon.com/lambda/latest/dg/lambda-intro-execution-role.html)(`--role`)의 Amazon 리소스 이름(ARN)
+ 함수 코드에 있는 핸들러 메서드의 이름(`--handler`)

 .zip 파일의 위치도 지정해야 합니다. .zip 파일이 로컬 빌드 시스템의 폴더에 있는 경우 다음 예제 명령과 같이 `--zip-file` 옵션을 사용하여 파일 경로를 지정합니다.

```
aws lambda create-function --function-name myFunction \
--runtime nodejs24.x --handler index.handler \
--role arn:aws:iam::111122223333:role/service-role/my-lambda-role \
--zip-file fileb://myFunction.zip
```

 Amazon S3 버킷에서 .zip 파일의 위치를 지정하려면 다음 예제 명령과 같이 `--code` 옵션을 사용합니다. 버전이 지정된 객체에만 `S3ObjectVersion` 파라미터를 사용해야 합니다.

```
aws lambda create-function --function-name myFunction \
--runtime nodejs24.x --handler index.handler \
--role arn:aws:iam::111122223333:role/service-role/my-lambda-role \
--code S3Bucket=amzn-s3-demo-bucket,S3Key=myFileName.zip,S3ObjectVersion=myObjectVersion
```

 CLI를 사용하여 기존 함수를 업데이트하려면 `--function-name` 파라미터를 사용하여 함수 이름을 지정합니다. 함수 코드를 업데이트하는 데 사용할.zip 파일의 위치도 지정해야 합니다. .zip 파일이 로컬 빌드 시스템의 폴더에 있는 경우 다음 예제 명령과 같이 `--zip-file` 옵션을 사용하여 파일 경로를 지정합니다.

```
aws lambda update-function-code --function-name myFunction \
--zip-file fileb://myFunction.zip
```

 Amazon S3 버킷에서 .zip 파일의 위치를 지정하려면 다음 예제 명령과 같이 `--s3-bucket` 및 `--s3-key` 옵션을 사용합니다. 버전이 지정된 객체에만 `--s3-object-version` 파라미터를 사용해야 합니다.

```
aws lambda update-function-code --function-name myFunction \
--s3-bucket amzn-s3-demo-bucket --s3-key myFileName.zip --s3-object-version myObject Version
```

### Lambda API를 사용하여.zip 파일로 함수 생성 및 업데이트
<a name="nodejs-package-create-api"></a>

 .zip 파일 아카이브를 사용하여 함수를 생성하고 업데이트하려면 다음 API 작업을 사용합니다.
+ [CreateFunction](https://docs.aws.amazon.com/lambda/latest/api/API_CreateFunction.html)
+ [UpdateFunctionCode](https://docs.aws.amazon.com/lambda/latest/api/API_UpdateFunctionCode.html)

### AWS SAM을 사용하여.zip 파일로 함수 생성 및 업데이트
<a name="nodejs-package-create-sam"></a>

 AWS Serverless Application Model(AWS SAM)은 AWS에서 서버리스 애플리케이션을 빌드하고 실행하는 프로세스를 간소화하는 데 도움이 되는 도구 키트입니다. YAML 또는 JSON 템플릿에서 애플리케이션의 리소스를 정의하고 AWS SAM Command Line Interface(AWS SAM CLI)를 사용하여 애플리케이션을 빌드, 패키징 및 배포합니다. AWS SAM 템플릿에서 Lambda 함수를 빌드하면 AWS SAM은 함수 코드와 사용자가 지정하는 종속 항목을 사용하여 .zip 배포 패키지 또는 컨테이너 이미지를 자동으로 생성합니다. AWS SAM을 사용하여 Lambda 함수를 빌드하고 배포하는 방법에 대해 자세히 알아보려면 **AWS Serverless Application Model 개발자 안내서의 [Getting started with AWS SAM](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/serverless-getting-started.html)을 참조하세요.

AWS SAM을 사용하여 기존 .zip 파일 아카이브로 Lambda 함수를 생성할 수도 있습니다. AWS SAM을 사용하여 Lambda 함수를 생성하려면 Amazon S3 버킷 또는 빌드 시스템의 로컬 폴더에 .zip 파일을 저장할 수 있습니다. AWS CLI를 사용하여 Amazon S3 버킷에 파일을 업로드하는 방법에 대한 지침은 **AWS CLI 사용 설명서의 [객체 이동](https://docs.aws.amazon.com/cli/latest/userguide/cli-services-s3-commands.html#using-s3-commands-managing-objects-move)을 참조하세요.

 AWS SAM 템플릿에서 `AWS::Serverless::Function` 리소스는 Lambda 함수를 지정합니다. 이 리소스에서 다음 속성을 설정하여 .zip 파일 아카이브로 함수를 생성합니다.
+ `PackageType` - `Zip`으로 설정됨
+ `CodeUri` - 함수 코드의 Amazon S3 URI, 로컬 폴더 경로 또는 [FunctionCode](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-property-function-functioncode.html) 객체로 설정됨
+ `Runtime` - 선택한 런타임으로 설정됨

 AWS SAM을 사용하면 .zip 파일이 50MB보다 큰 경우 Amazon S3 버킷에 먼저 파일을 업로드할 필요가 없습니다. AWS SAM은 로컬 빌드 시스템의 위치에서 허용되는 최대 크기 250MB(압축 해제)까지 .zip 패키지를 업로드할 수 있습니다.

 AWS SAM에서 .zip 파일을 사용하여 함수를 배포하는 방법에 대해 자세히 알아보려면 **AWS SAM 개발자 안내서의 [AWS::Serverless::Function](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-resource-function.html)을 참조하세요.

### CloudFormation을 사용하여.zip 파일로 함수 생성 및 업데이트
<a name="nodejs-package-create-cfn"></a>

 CloudFormation을 사용하여 .zip 파일 아카이브로 Lambda 함수를 생성할 수 있습니다. .zip 파일에서 Lambda 함수를 생성하려면 먼저 Amazon S3 버킷에 파일을 업로드해야 합니다. AWS CLI를 사용하여 Amazon S3 버킷에 파일을 업로드하는 방법에 대한 지침은 **AWS CLI 사용 설명서의 [객체 이동](https://docs.aws.amazon.com/cli/latest/userguide/cli-services-s3-commands.html#using-s3-commands-managing-objects-move)을 참조하세요.

CloudFormation 템플릿에서 `AWS::Lambda::Function` 리소스는 Lambda 함수를 지정합니다. 이 리소스에서 다음 속성을 설정하여 .zip 파일 아카이브로 함수를 생성합니다.
+ `PackageType` - `Zip`으로 설정됨
+ `Code` - `S3Bucket` 및 `S3Key` 필드에 Amazon S3 버킷 이름과 .zip 파일 이름을 입력합니다.
+ `Runtime` - 선택한 런타임으로 설정됨

 CloudFormation에서 생성하는 .zip 파일은 4MB를 초과할 수 없습니다. CloudFormation에서 .zip 파일을 사용하여 함수를 배포하는 방법에 대해 자세히 알아보려면 **CloudFormation 사용 설명서의 [AWS::Lambda::Function](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-lambda-function.html)을 참조하세요.

# 컨테이너 이미지를 사용하여 Node.js Lambda 함수 배포
<a name="nodejs-image"></a>

Node.js Lambda 함수의 컨테이너 이미지를 빌드하는 세 가지 방법이 있습니다.
+ [Node.js용 AWS 기본 이미지 사용](#nodejs-image-instructions)

  [AWS 기본 이미지](images-create.md#runtimes-images-lp)에는 언어 런타임, Lambda와 함수 코드 간의 상호 작용을 관리하는 런타임 인터페이스 클라이언트 및 로컬 테스트를 위한 런타임 인터페이스 에뮬레이터가 미리 로드되어 있습니다.
+ [AWS OS 전용 기본 이미지 사용](images-create.md#runtimes-images-provided)

  [AWS OS 전용 기본 이미지](https://gallery.ecr.aws/lambda/provided)는 Amazon Linux 배포판 및 [런타임 인터페이스 에뮬레이터](https://github.com/aws/aws-lambda-runtime-interface-emulator/)를 포함합니다. 이러한 이미지는 일반적으로 [Go](go-image.md#go-image-provided) 및 [Rust](lambda-rust.md)와 같은 컴파일된 언어의 컨테이너 이미지와 Lambda가 기본 이미지를 제공하지 않는 언어 또는 언어 버전(예: Node.js 19)의 컨테이너 이미지를 생성하는 데 사용됩니다. OS 전용 기본 이미지를 사용하여 [사용자 지정 런타임](runtimes-custom.md)을 구현할 수도 있습니다. 이미지가 Lambda와 호환되도록 하려면 [Node.js용 런타임 인터페이스 클라이언트](#nodejs-image-clients)를 이미지에 포함해야 합니다.
+ [비AWS 기본 이미지 사용](#nodejs-image-clients)

  Alpine Linux, Debian 등의 다른 컨테이너 레지스트리의 대체 기본 이미지를 사용할 수 있습니다. 조직에서 생성한 사용자 지정 이미지를 사용할 수도 있습니다. 이미지가 Lambda와 호환되도록 하려면 [Node.js용 런타임 인터페이스 클라이언트](#nodejs-image-clients)를 이미지에 포함해야 합니다.

**작은 정보**  
Lambda 컨테이너 함수가 활성 상태가 되는 데 걸리는 시간을 줄이려면 Docker 설명서의 [다단계 빌드 사용](https://docs.docker.com/build/building/multi-stage/)을 참조하세요. 효율적인 컨테이너 이미지를 빌드하려면 [Dockerfile 작성 모범 사례](https://docs.docker.com/develop/develop-images/dockerfile_best-practices/)를 따르세요.

이 페이지에서는 Lambda용 컨테이너 이미지를 빌드, 테스트 및 배포하는 방법을 설명합니다.

**Topics**
+ [

## Node.js용 AWS 기본 이미지
](#nodejs-image-base)
+ [

## Node.js용 AWS 기본 이미지 사용
](#nodejs-image-instructions)
+ [

## 런타임 인터페이스 클라이언트에서 대체 기본 이미지 사용
](#nodejs-image-clients)

## Node.js용 AWS 기본 이미지
<a name="nodejs-image-base"></a>

AWS는 Node.js에 대한 다음과 같은 기본 이미지를 제공합니다.


| 태그 | 런타임 | 운영 체제 | Dockerfile | 사용 중단 | 
| --- | --- | --- | --- | --- | 
| 24 | Node.js 24 | Amazon Linux 2023 | [GitHub의 Node.js 24용 Dockerfile](https://github.com/aws/aws-lambda-base-images/blob/nodejs24.x/Dockerfile.nodejs24.x) |   2028년 4월 30일   | 
| 22 | Node.js 22 | Amazon Linux 2023 | [GitHub에서 Node.js 22에 대한 Dockerfile](https://github.com/aws/aws-lambda-base-images/blob/nodejs22.x/Dockerfile.nodejs22.x) |   2027년 4월 30일   | 
| 20 | Node.js 20 | Amazon Linux 2023 | [GitHub의 Node.js 20용 Dockerfile](https://github.com/aws/aws-lambda-base-images/blob/nodejs20.x/Dockerfile.nodejs20.x) |   2026년 4월 30일   | 

Amazon ECR 리포지토리: [gallery.ecr.aws/lambda/nodejs](https://gallery.ecr.aws/lambda/nodejs)

Node.js 20 이상의 기본 이미지는 [Amazon Linux 2023 최소 컨테이너 이미지](https://docs.aws.amazon.com/linux/al2023/ug/minimal-container.html)를 기반으로 합니다. 이전 기본 이미지는 Amazon Linux 2를 사용합니다. AL2023은 작은 배포 공간과 `glibc`와 같이 업데이트된 라이브러리 버전을 포함하여 Amazon Linux 2에 비해 여러 가지 이점을 제공합니다.

AL2023 기반 이미지는 `microdnf`(`dnf` 심볼릭 링크)를 Amazon Linux 2에서 기본 패키지 관리자인 `yum` 대신 패키지 관리자로 사용합니다. `microdnf`는 `dnf`의 독립 실행형 구현입니다. AL2023 기반 이미지에 포함된 패키지 목록의 경우 [Comparing packages installed on Amazon Linux 2023 Container Images](https://docs.aws.amazon.com/linux/al2023/ug/al2023-container-image-types.html)의 **Minimal Container** 열을 참조하세요. AL2023과 Amazon Linux 2의 차이점에 대한 자세한 내용은 AWS 컴퓨팅 블로그의 [Introducing the Amazon Linux 2023 runtime for AWS Lambda](https://aws.amazon.com/blogs/compute/introducing-the-amazon-linux-2023-runtime-for-aws-lambda/)를 참조하세요.

**참고**  
AWS Serverless Application Model(AWS SAM)을 포함하여 AL2023 기반 이미지를 로컬에서 실행하려면 Docker 버전 20.10.10 이상을 사용해야 합니다.

## Node.js용 AWS 기본 이미지 사용
<a name="nodejs-image-instructions"></a>

### 사전 조건
<a name="nodejs-image-prerequisites"></a>

이 섹션의 단계를 완료하려면 다음이 필요합니다.
+ [AWS CLI 버전 2](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html)
+ [Docker](https://docs.docker.com/get-docker)(최소 버전 25.0.0)
+ Docker [buildx 플러그인](https://github.com/docker/buildx/blob/master/README.md)
+ Node.js

### 기본 이미지에서 이미지 생성
<a name="nodejs-image-create"></a>

**Node.js용 AWS 기본 이미지에서 컨테이너 이미지 생성**

1. 프로젝트에 대한 디렉터리를 생성하고 해당 디렉터리로 전환합니다.

   ```
   mkdir example
   cd example
   ```

1. `npm`을 사용하여 새 Node.js 프로젝트를 생성합니다. 대화형 환경에서 제공되는 기본 옵션을 수락하려면 `Enter`을 누릅니다.

   ```
   npm init
   ```

1. `index.js`라는 파일을 새로 생성합니다. 테스트를 위해 다음 샘플 함수 코드를 파일에 추가하거나 자체 샘플 함수 코드를 사용할 수 있습니다.  
**Example CommonJS 핸들러**  

   ```
   exports.handler = async (event) => {
       const response = {
           statusCode: 200,
           body: JSON.stringify('Hello from Lambda!'),
       };
       return response;
   };
   ```

1. 함수가 AWS SDK for JavaScript 외의 다른 라이브러리를 사용하는 경우 [npm](https://www.npmjs.com/)을 사용하여 패키지에 해당 라이브러리를 추가합니다.

1. 다음 구성으로 새 Dockerfile을 생성합니다.
   + `FROM` 속성을 [기본 이미지의 URI](https://gallery.ecr.aws/lambda/nodejs)로 설정합니다.
   + COPY 명령을 사용하여 함수 코드와 런타임 종속성을 [Lambda 정의 환경 변수](configuration-envvars.md#configuration-envvars-runtime)인 `{LAMBDA_TASK_ROOT}`에 복사합니다.
   + `CMD` 인수를 Lambda 함수 핸들러로 설정합니다.

   참고로 Dockerfile 예제에는 [USER 지침](https://docs.docker.com/reference/dockerfile/#user)이 포함되어 있지 않습니다. Lambda에 컨테이너 이미지를 배포할 때 Lambda는 권한이 최소 권한인 기본 Linux 사용자를 자동으로 정의합니다. 이는 `USER` 지침이 제공되지 않을 때 `root` 사용자에게 기본 설정이 적용되는 표준 Docker 동작과는 다릅니다.  
**Example Dockerfile**  

   ```
   FROM public.ecr.aws/lambda/nodejs:22
   
   # 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" ]
   ```

1. [docker build](https://docs.docker.com/engine/reference/commandline/build/) 명령으로 도커 이미지를 빌드합니다. 다음 예제에서는 이미지 이름을 `docker-image`로 지정하고 `test` [태그](https://docs.docker.com/engine/reference/commandline/build/#tag)를 지정합니다. 이미지를 Lambda와 호환되게 만들려면 `--provenance=false` 옵션을 사용해야 합니다.

   ```
   docker buildx build --platform linux/amd64 --provenance=false -t docker-image:test .
   ```
**참고**  
이 명령은 빌드 머신의 아키텍처에 관계없이 컨테이너가 Lambda 실행 환경과 호환되는지 확인하기 위해 `--platform linux/amd64` 옵션을 지정합니다. ARM64 명령 세트 아키텍처를 사용하여 Lambda 함수를 생성하려는 경우 `--platform linux/arm64` 옵션을 대신 사용하도록 명령을 변경해야 합니다.

### (선택 사항) 로컬에서 이미지 테스트
<a name="nodejs-image-test"></a>

1. **docker run** 명령을 사용하여 Docker 이미지를 시작합니다. 이 예제에서 `docker-image`는 이미지 이름이고 `test`는 태그입니다.

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

   이 명령은 이미지를 컨테이너로 실행하고 `localhost:9000/2015-03-31/functions/function/invocations`에 로컬 엔드포인트를 생성합니다.
**참고**  
ARM64 명령 세트 아키텍처를 위한 도커 이미지를 빌드한 경우 `--platform linux/arm64` 옵션을 `--platform linux/amd64` 대신 사용해야 합니다.

1. 새 터미널 창에서 로컬 엔드포인트에 이벤트를 게시합니다.

------
#### [ Linux/macOS ]

   Linux 및 macOS에서 다음 `curl` 명령을 실행합니다.

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

   이 명령은 빈 이벤트와 함께 함수를 간접 호출하고 응답을 반환합니다. 샘플 함수 코드가 아닌 자체 함수 코드를 사용하는 경우 JSON 페이로드로 함수를 간접 호출할 수 있습니다. 예제:

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

------
#### [ PowerShell ]

   PowerShell에서 다음 `Invoke-WebRequest` 명령을 실행합니다.

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

   이 명령은 빈 이벤트와 함께 함수를 간접 호출하고 응답을 반환합니다. 샘플 함수 코드가 아닌 자체 함수 코드를 사용하는 경우 JSON 페이로드로 함수를 간접 호출할 수 있습니다. 예제:

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

------

1. 컨테이너 ID를 가져옵니다.

   ```
   docker ps
   ```

1. [docker kill](https://docs.docker.com/engine/reference/commandline/kill/) 명령을 사용하여 컨테이너를 중지합니다. 이 명령에서 `3766c4ab331c`를 이전 단계의 컨테이너 ID로 바꿉니다.

   ```
   docker kill 3766c4ab331c
   ```

### 이미지 배포
<a name="nodejs-image-deploy"></a>

**Amazon ECR에 이미지 배포 및 Lambda 함수 생성**

1. [get-login-password](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ecr/get-login-password.html) 명령을 실행하여 Amazon ECR 레지스트리에 대해 Docker CLI를 인증합니다.
   + `--region` 값을 Amazon ECR 리포지토리를 생성하려는 AWS 리전으로 설정합니다.
   + `111122223333`를 사용자의 AWS 계정 ID로 바꿉니다.

   ```
   aws ecr get-login-password --region us-east-1 | docker login --username AWS --password-stdin 111122223333.dkr.ecr.us-east-1.amazonaws.com
   ```

1. [create-repository](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ecr/create-repository.html) 명령을 사용하여 Amazon ECR에 리포지토리를 생성합니다.

   ```
   aws ecr create-repository --repository-name hello-world --region us-east-1 --image-scanning-configuration scanOnPush=true --image-tag-mutability MUTABLE
   ```
**참고**  
Amazon ECR 리포지토리는 Lambda 함수와 동일한 AWS 리전 내에 있어야 합니다.

   성공하면 다음과 같은 응답이 표시됩니다.

   ```
   {
       "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"
           }
       }
   }
   ```

1. 이전 단계의 출력에서 `repositoryUri`를 복사합니다.

1. [docker tag](https://docs.docker.com/engine/reference/commandline/tag/) 명령을 실행하여 로컬 이미지를 Amazon ECR 리포지토리에 최신 버전으로 태깅합니다. 이 명령에서:
   + `docker-image:test`는 Docker 이미지의 이름과 [태그](https://docs.docker.com/engine/reference/commandline/build/#tag)입니다. `docker build` 명령에서 지정한 이미지 이름 및 태그입니다.
   + `<ECRrepositoryUri>`를 복사한 `repositoryUri`로 바꿉니다. URI 끝에 `:latest`를 포함해야 합니다.

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

   예제:

   ```
   docker tag docker-image:test 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
   ```

1. [docker push](https://docs.docker.com/engine/reference/commandline/push/) 명령을 실행하여 Amazon ECR 리포지토리에 로컬 이미지를 배포합니다. 리포지토리 URI 끝에 `:latest`를 포함해야 합니다.

   ```
   docker push 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
   ```

1. 함수에 대한 실행 역할이 아직 없는 경우 하나 [생성](lambda-intro-execution-role.md#permissions-executionrole-api)합니다. 다음 단계에서는 역할의 Amazon 리소스 이름(ARN)이 필요합니다.

1. Lambda 함수를 생성합니다. `ImageUri`의 경우 이전의 리포지토리 URI를 지정합니다. URI 끝에 `:latest`를 포함해야 합니다.

   ```
   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
   ```
**참고**  
이미지가 Lambda 함수와 동일한 리전에 있는 한 다른 AWS 계정의 이미지를 사용하여 함수를 생성할 수 있습니다. 자세한 내용은 [Amazon ECR 교차 계정 권한](images-create.md#configuration-images-xaccount-permissions) 섹션을 참조하세요.

1. 함수를 간접 호출합니다.

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

   다음과 같은 응답이 표시되어야 합니다.

   ```
   {
     "ExecutedVersion": "$LATEST", 
     "StatusCode": 200
   }
   ```

1. 함수의 출력을 보려면 `response.json` 파일을 확인합니다.

함수 코드를 업데이트하려면 이미지를 다시 빌드하고 Amazon ECR 리포지토리에 새 이미지를 업로드한 다음 [update-function-code](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/update-function-code.html) 명령을 사용하여 이미지를 Lambda 함수에 배포해야 합니다.

Lambda는 이미지 태그를 특정 이미지 다이제스트로 확인합니다. 즉, 함수를 배포하는 데 사용된 이미지 태그가 Amazon ECR의 새 이미지로 가리키는 경우 Lambda는 새 이미지를 사용하도록 함수를 자동으로 업데이트하지 않습니다.

새 이미지를 동일한 Lambda 함수에 배포하려면 Amazon ECR의 이미지 태그가 동일하게 유지되더라도 [update-function-code](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/update-function-code.html) 명령을 사용해야 합니다. 다음 예제에서 `--publish` 옵션은 업데이트된 컨테이너 이미지를 사용하여 새 버전의 함수를 생성합니다.

```
aws lambda update-function-code \
  --function-name hello-world \
  --image-uri 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest \
  --publish
```

## 런타임 인터페이스 클라이언트에서 대체 기본 이미지 사용
<a name="nodejs-image-clients"></a>

[OS 전용 기본 이미지](images-create.md#runtimes-images-provided)나 대체 기본 이미지를 사용하는 경우 이미지에 런타임 인터페이스 클라이언트를 포함해야 합니다. 런타임 인터페이스 클라이언트는 Lambda와 함수 코드 간의 상호 작용을 관리하는 [런타임 API](runtimes-api.md)을 확장합니다.

npm 패키지 관리자를 사용하여 [Node.js 런타임 인터페이스 클라이언트](https://www.npmjs.com/package/aws-lambda-ric)를 설치합니다.

```
npm install aws-lambda-ric
```

GitHub에서 [Node.js 런타임 인터페이스 클라이언트](https://github.com/aws/aws-lambda-nodejs-runtime-interface-client)를 다운로드할 수도 있습니다.

다음 예제에서는 비 AWS 기본 이미지를 사용하여 Node.js용 컨테이너 이미지를 빌드하는 방법을 보여줍니다. 예제 Dockerfile에서는 `bookworm` 기본 이미지를 사용합니다. Dockerfile에는 런타임 인터페이스 클라이언트가 포함되어 있습니다.

### 사전 조건
<a name="nodejs-alt-prerequisites"></a>

이 섹션의 단계를 완료하려면 다음이 필요합니다.
+ [AWS CLI 버전 2](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html)
+ [Docker](https://docs.docker.com/get-docker)(최소 버전 25.0.0)
+ Docker [buildx 플러그인](https://github.com/docker/buildx/blob/master/README.md)
+ Node.js

### 대체 기본 이미지에서 이미지 생성
<a name="nodejs-alt-create"></a>

**비 AWS 기본 이미지에서 컨테이너 이미지 생성**

1. 프로젝트에 대한 디렉터리를 생성하고 해당 디렉터리로 전환합니다.

   ```
   mkdir example
   cd example
   ```

1. `npm`을 사용하여 새 Node.js 프로젝트를 생성합니다. 대화형 환경에서 제공되는 기본 옵션을 수락하려면 `Enter`을 누릅니다.

   ```
   npm init
   ```

1. `index.js`라는 파일을 새로 생성합니다. 테스트를 위해 다음 샘플 함수 코드를 파일에 추가하거나 자체 샘플 함수 코드를 사용할 수 있습니다.  
**Example CommonJS 핸들러**  

   ```
   exports.handler = async (event) => {
       const response = {
           statusCode: 200,
           body: JSON.stringify('Hello from Lambda!'),
       };
       return response;
   };
   ```

1. 새 Dockerfile을 생성합니다. 다음 Dockerfile은 [AWS 기본 이미지](images-create.md#runtimes-images-lp) 대신 `bookworm` 기본 이미지를 사용합니다. Dockerfile에는 이미지가 Lambda와 호환되도록 하는 [런타임 인터페이스 클라이언트](https://www.npmjs.com/package/aws-lambda-ric)가 포함되어 있습니다. Dockerfile은 [다단계 빌드](https://docs.docker.com/develop/develop-images/dockerfile_best-practices/#use-multi-stage-builds)를 사용합니다. 첫 번째 단계에서는 함수의 종속 항목이 설치되는 표준 Node.js 환경인 빌드 이미지를 생성합니다. 두 번째 단계에서는 함수 코드와 해당 종속 항목을 포함하는 더 슬림한 이미지를 생성합니다. 이렇게 하면 최종 이미지 크기가 줄어듭니다.
   + `FROM` 속성을 기본 이미지 식별자로 설정합니다.
   + `COPY` 명령을 사용하여 함수 코드와 런타임 종속 항목을 복사합니다.
   + Docker 컨테이너가 시작될 때 실행할 모듈로 `ENTRYPOINT`를 설정합니다. 이 경우 모듈은 런타임 인터페이스 클라이언트입니다.
   + `CMD` 인수를 Lambda 함수 핸들러로 설정합니다.

   참고로 Dockerfile 예제에는 [USER 지침](https://docs.docker.com/reference/dockerfile/#user)이 포함되어 있지 않습니다. Lambda에 컨테이너 이미지를 배포할 때 Lambda는 권한이 최소 권한인 기본 Linux 사용자를 자동으로 정의합니다. 이는 `USER` 지침이 제공되지 않을 때 `root` 사용자에게 기본 설정이 적용되는 표준 Docker 동작과는 다릅니다.  
**Example Dockerfile**  

   ```
   # Define custom function directory
   ARG FUNCTION_DIR="/function"
   
   FROM node:20-bookworm 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-bookworm-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"]
   ```

1. [docker build](https://docs.docker.com/engine/reference/commandline/build/) 명령으로 도커 이미지를 빌드합니다. 다음 예제에서는 이미지 이름을 `docker-image`로 지정하고 `test` [태그](https://docs.docker.com/engine/reference/commandline/build/#tag)를 지정합니다. 이미지를 Lambda와 호환되게 만들려면 `--provenance=false` 옵션을 사용해야 합니다.

   ```
   docker buildx build --platform linux/amd64 --provenance=false -t docker-image:test .
   ```
**참고**  
이 명령은 빌드 머신의 아키텍처에 관계없이 컨테이너가 Lambda 실행 환경과 호환되는지 확인하기 위해 `--platform linux/amd64` 옵션을 지정합니다. ARM64 명령 세트 아키텍처를 사용하여 Lambda 함수를 생성하려는 경우 `--platform linux/arm64` 옵션을 대신 사용하도록 명령을 변경해야 합니다.

### (선택 사항) 로컬에서 이미지 테스트
<a name="nodejs-alt-test"></a>

[런타임 인터페이스 에뮬레이터](https://github.com/aws/aws-lambda-runtime-interface-emulator/)를 사용하여 이미지를 로컬로 테스트합니다. [에뮬레이터를 이미지에 빌드](https://github.com/aws/aws-lambda-runtime-interface-emulator/?tab=readme-ov-file#build-rie-into-your-base-image)하거나 다음 절차를 사용하여 로컬 시스템에 설치할 수 있습니다.

**로컬 시스템에 런타임 인터페이스 에뮬레이터 설치 및 실행**

1. 프로젝트 디렉터리에서 다음 명령을 실행하여 GitHub에서 런타임 인터페이스 에뮬레이터(x86-64 아키텍처)를 다운로드하고 로컬 시스템에 설치합니다.

------
#### [ 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
   ```

   arm64 에뮬레이터를 설치하려면 이전 명령의 GitHub 리포지토리 URL을 다음과 같이 바꿉니다.

   ```
   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
   ```

   arm64 에뮬레이터를 설치하려면 `$downloadLink`을(를) 다음과 같이 바꿉니다.

   ```
   https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie-arm64
   ```

------

1. **docker run** 명령을 사용하여 Docker 이미지를 시작합니다. 다음 사항에 유의하세요.
   + `docker-image`는 이미지 이름이고 `test`는 태그입니다.
   + `/usr/local/bin/npx aws-lambda-ric index.handler`는 Docker 파일의 `CMD` 다음에 오는 `ENTRYPOINT`입니다.

------
#### [ 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
   ```

------

   이 명령은 이미지를 컨테이너로 실행하고 `localhost:9000/2015-03-31/functions/function/invocations`에 로컬 엔드포인트를 생성합니다.
**참고**  
ARM64 명령 세트 아키텍처를 위한 도커 이미지를 빌드한 경우 `--platform linux/arm64` 옵션을 `--platform linux/amd64` 대신 사용해야 합니다.

1. 로컬 엔드포인트에 이벤트를 게시합니다.

------
#### [ Linux/macOS ]

   Linux 및 macOS에서 다음 `curl` 명령을 실행합니다.

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

   이 명령은 빈 이벤트와 함께 함수를 간접 호출하고 응답을 반환합니다. 샘플 함수 코드가 아닌 자체 함수 코드를 사용하는 경우 JSON 페이로드로 함수를 간접 호출할 수 있습니다. 예제:

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

------
#### [ PowerShell ]

   PowerShell에서 다음 `Invoke-WebRequest` 명령을 실행합니다.

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

   이 명령은 빈 이벤트와 함께 함수를 간접 호출하고 응답을 반환합니다. 샘플 함수 코드가 아닌 자체 함수 코드를 사용하는 경우 JSON 페이로드로 함수를 간접 호출할 수 있습니다. 예제:

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

------

1. 컨테이너 ID를 가져옵니다.

   ```
   docker ps
   ```

1. [docker kill](https://docs.docker.com/engine/reference/commandline/kill/) 명령을 사용하여 컨테이너를 중지합니다. 이 명령에서 `3766c4ab331c`를 이전 단계의 컨테이너 ID로 바꿉니다.

   ```
   docker kill 3766c4ab331c
   ```

### 이미지 배포
<a name="nodejs-alt-deploy"></a>

**Amazon ECR에 이미지 배포 및 Lambda 함수 생성**

1. [get-login-password](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ecr/get-login-password.html) 명령을 실행하여 Amazon ECR 레지스트리에 대해 Docker CLI를 인증합니다.
   + `--region` 값을 Amazon ECR 리포지토리를 생성하려는 AWS 리전으로 설정합니다.
   + `111122223333`를 사용자의 AWS 계정 ID로 바꿉니다.

   ```
   aws ecr get-login-password --region us-east-1 | docker login --username AWS --password-stdin 111122223333.dkr.ecr.us-east-1.amazonaws.com
   ```

1. [create-repository](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/ecr/create-repository.html) 명령을 사용하여 Amazon ECR에 리포지토리를 생성합니다.

   ```
   aws ecr create-repository --repository-name hello-world --region us-east-1 --image-scanning-configuration scanOnPush=true --image-tag-mutability MUTABLE
   ```
**참고**  
Amazon ECR 리포지토리는 Lambda 함수와 동일한 AWS 리전 내에 있어야 합니다.

   성공하면 다음과 같은 응답이 표시됩니다.

   ```
   {
       "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"
           }
       }
   }
   ```

1. 이전 단계의 출력에서 `repositoryUri`를 복사합니다.

1. [docker tag](https://docs.docker.com/engine/reference/commandline/tag/) 명령을 실행하여 로컬 이미지를 Amazon ECR 리포지토리에 최신 버전으로 태깅합니다. 이 명령에서:
   + `docker-image:test`는 Docker 이미지의 이름과 [태그](https://docs.docker.com/engine/reference/commandline/build/#tag)입니다. `docker build` 명령에서 지정한 이미지 이름 및 태그입니다.
   + `<ECRrepositoryUri>`를 복사한 `repositoryUri`로 바꿉니다. URI 끝에 `:latest`를 포함해야 합니다.

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

   예제:

   ```
   docker tag docker-image:test 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
   ```

1. [docker push](https://docs.docker.com/engine/reference/commandline/push/) 명령을 실행하여 Amazon ECR 리포지토리에 로컬 이미지를 배포합니다. 리포지토리 URI 끝에 `:latest`를 포함해야 합니다.

   ```
   docker push 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest
   ```

1. 함수에 대한 실행 역할이 아직 없는 경우 하나 [생성](lambda-intro-execution-role.md#permissions-executionrole-api)합니다. 다음 단계에서는 역할의 Amazon 리소스 이름(ARN)이 필요합니다.

1. Lambda 함수를 생성합니다. `ImageUri`의 경우 이전의 리포지토리 URI를 지정합니다. URI 끝에 `:latest`를 포함해야 합니다.

   ```
   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
   ```
**참고**  
이미지가 Lambda 함수와 동일한 리전에 있는 한 다른 AWS 계정의 이미지를 사용하여 함수를 생성할 수 있습니다. 자세한 내용은 [Amazon ECR 교차 계정 권한](images-create.md#configuration-images-xaccount-permissions) 섹션을 참조하세요.

1. 함수를 간접 호출합니다.

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

   다음과 같은 응답이 표시되어야 합니다.

   ```
   {
     "ExecutedVersion": "$LATEST", 
     "StatusCode": 200
   }
   ```

1. 함수의 출력을 보려면 `response.json` 파일을 확인합니다.

함수 코드를 업데이트하려면 이미지를 다시 빌드하고 Amazon ECR 리포지토리에 새 이미지를 업로드한 다음 [update-function-code](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/update-function-code.html) 명령을 사용하여 이미지를 Lambda 함수에 배포해야 합니다.

Lambda는 이미지 태그를 특정 이미지 다이제스트로 확인합니다. 즉, 함수를 배포하는 데 사용된 이미지 태그가 Amazon ECR의 새 이미지로 가리키는 경우 Lambda는 새 이미지를 사용하도록 함수를 자동으로 업데이트하지 않습니다.

새 이미지를 동일한 Lambda 함수에 배포하려면 Amazon ECR의 이미지 태그가 동일하게 유지되더라도 [update-function-code](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/update-function-code.html) 명령을 사용해야 합니다. 다음 예제에서 `--publish` 옵션은 업데이트된 컨테이너 이미지를 사용하여 새 버전의 함수를 생성합니다.

```
aws lambda update-function-code \
  --function-name hello-world \
  --image-uri 111122223333.dkr.ecr.us-east-1.amazonaws.com/hello-world:latest \
  --publish
```

# Node.js Lambda 함수를 위한 계층 작업
<a name="nodejs-layers"></a>

[Lambda 계층](chapter-layers.md)을 사용하여 여러 함수에서 재사용하려는 코드와 종속성을 패키징합니다. 계층에는 일반적으로 라이브러리 종속 항목, [사용자 지정 런타임](runtimes-custom.md) 또는 구성 파일이 포함됩니다. 계층을 생성하려면 세 가지 일반적인 단계를 거칩니다.

1. 계층 콘텐츠를 패키징합니다. 즉, 함수에 사용하려는 종속성이 포함된 .zip 파일 아카이브를 생성합니다.

1. Lambda에서 계층을 생성합니다.

1. 계층을 함수에 추가합니다.

**Topics**
+ [

## 계층 콘텐츠 패키징
](#nodejs-layers-package)
+ [

## Lambda에서 계층 생성
](#publishing-layer)
+ [

## 함수에 계층 추가
](#nodejs-layer-adding)
+ [

## 샘플 애플리케이션
](#nodejs-layer-sample-app)

## 계층 콘텐츠 패키징
<a name="nodejs-layers-package"></a>

계층을 생성하려면 다음 요구 사항을 충족하는 .zip 파일 아카이브로 패키지를 번들링합니다.
+ Lambda 함수에 사용하려는 것과 동일한 Node.js 버전을 사용하여 계층을 빌드합니다. 예를 들어, Node.js 24를 사용하여 계층을 빌드하는 경우 함수에 Node.js 24 런타임을 사용합니다.
+ 계층의 .zip 파일은 다음 디렉터리 구조 중 하나를 사용해야 합니다.
  + `nodejs/node_modules`
  + `nodejs/nodeX/node_modules`(여기서 *X*는 Node.js 버전(예: `node22`))

  자세한 내용은 [각 Lambda 런타임에 대한 계층 경로](packaging-layers.md#packaging-layers-paths) 섹션을 참조하세요.
+ 계층의 패키지는 Linux와 호환되어야 합니다. Lambda 함수는 Amazon Linux에서 실행됩니다.

`npm`을 사용하여 설치한 타사 Node.js 라이브러리(`axios`, `lodash` 등)나 자체 JavaScript 모듈을 포함하는 계층을 생성할 수 있습니다.

### 타사 종속성
<a name="nodejs-layers-third-party-dependencies"></a>

**npm 패키지를 사용하여 계층을 생성하려면 다음을 수행하세요.**

1. 필요한 디렉터리 구조를 생성하고 해당 디렉터리에 패키지를 직접 설치합니다.

   ```
   mkdir -p nodejs
   npm install --prefix nodejs lodash axios
   ```

   이 명령은 Lambda에 필요한 구조인 `nodejs/node_modules` 디렉터리에 패키지를 직접 설치합니다.
**참고**  
네이티브 종속성 또는 바이너리 구성 요소(예: [sharp](https://www.npmjs.com/package/sharp) 또는 [bcrypt](https://www.npmjs.com/package/bcrypt))가 있는 패키지의 경우 Lambda Linux 환경 및 함수의 [아키텍처](foundation-arch.md)와 호환되는지 확인합니다. `--platform` 플래그를 사용해야 할 수 있습니다.  

   ```
   npm install --prefix nodejs --platform=linux --arch=x64 sharp
   ```
보다 복잡한 네이티브 종속성의 경우 Lambda 런타임과 일치하는 Linux 환경에서 컴파일해야 할 수 있습니다. 이 용도로 Docker를 사용할 수 있습니다.

1. 계층 콘텐츠를 .zip 파일로 압축합니다.

------
#### [ Linux/macOS ]

   ```
   zip -r layer.zip nodejs/
   ```

------
#### [ PowerShell ]

   ```
   Compress-Archive -Path .\nodejs -DestinationPath .\layer.zip
   ```

------

   .zip 파일의 디렉터리 구조는 다음과 같아야 합니다.

   ```
   nodejs/
   ├── package.json
   ├── package-lock.json
   └── node_modules/
       ├── lodash/
       ├── axios/
       └── (dependencies of the other packages)
   ```
**참고**  
파일의 루트 수준에 `nodejs` 디렉터리가 포함되어 있고 그 안에 `node_modules`가 있는지 확인하세요. 이 구조는 Lambda가 패키지를 찾아서 가져올 수 있도록 합니다.
`nodejs/` 디렉터리의 `package.json` 및 `package-lock.json` 파일은 npm의 종속성 관리를 위해 사용되지만 Lambda의 계층 기능에는 필요하지 않습니다. 설치된 각 패키지에는 Lambda가 패키지를 가져오는 방식을 정의하는 자체 `package.json` 파일이 이미 포함되어 있습니다.

### 사용자 지정 JavaScript 모듈
<a name="custom-nodejs-modules"></a>

**자체 코드를 사용하여 계층을 생성하려면 다음을 수행하세요.**

1. 계층에 필요한 디렉터리 구조를 생성합니다.

   ```
   mkdir -p nodejs/node_modules/validator
   cd nodejs/node_modules/validator
   ```

1. 사용자 지정 모듈에 대한 `package.json` 파일을 생성하여 해당 모듈을 가져오는 방법을 정의합니다.  
**Example nodejs/node\$1modules/validator/package.json**  

   ```
   {
     "name": "validator",
     "version": "1.0.0",
     "type": "module",
     "main": "index.mjs"
   }
   ```

1. JavaScript 모듈 파일을 생성합니다.  
**Example nodejs/node\$1modules/validator/index.mjs**  

   ```
   export function validateOrder(orderData) {
     // Validates an order and returns formatted data
     const requiredFields = ['productId', 'quantity'];
     
     // Check required fields
     const missingFields = requiredFields.filter(field => !(field in orderData));
     if (missingFields.length > 0) {
       throw new Error(`Missing required fields: ${missingFields.join(', ')}`);
     }
     
     // Validate quantity
     const quantity = orderData.quantity;
     if (!Number.isInteger(quantity) || quantity < 1) {
       throw new Error('Quantity must be a positive integer');
     }
     
     // Format and return the validated data
     return {
       productId: String(orderData.productId),
       quantity: quantity,
       shippingPriority: orderData.priority || 'standard'
     };
   }
   
   export function formatResponse(statusCode, body) {
     // Formats the API response
     return {
       statusCode: statusCode,
       body: JSON.stringify(body)
     };
   }
   ```

1. 계층 콘텐츠를 .zip 파일로 압축합니다.

------
#### [ Linux/macOS ]

   ```
   zip -r layer.zip nodejs/
   ```

------
#### [ PowerShell ]

   ```
   Compress-Archive -Path .\nodejs -DestinationPath .\layer.zip
   ```

------

   .zip 파일의 디렉터리 구조는 다음과 같아야 합니다.

   ```
   nodejs/              
   └── node_modules/
       └── validator/
           ├── package.json
           └── index.mjs
   ```

1. 함수에서 모듈을 가져와서 사용합니다. 예제:

   ```
   import { validateOrder, formatResponse } from 'validator';
   
   export const handler = async (event) => {
     try {
       // Parse the order data from the event body
       const orderData = JSON.parse(event.body || '{}');
       
       // Validate and format the order
       const validatedOrder = validateOrder(orderData);
       
       return formatResponse(200, {
         message: 'Order validated successfully',
         order: validatedOrder
       });
     } catch (error) {
       if (error instanceof Error && error.message.includes('Missing required fields')) {
         return formatResponse(400, {
           error: error.message
         });
       }
       
       return formatResponse(500, {
         error: 'Internal server error'
       });
     }
   };
   ```

   다음 [테스트 이벤트](testing-functions.md#invoke-with-event)를 사용하여 함수를 간접적으로 호출할 수 있습니다.

   ```
   {
       "body": "{\"productId\": \"ABC123\", \"quantity\": 2, \"priority\": \"express\"}"
   }
   ```

   예상 응답:

   ```
   {
     "statusCode": 200,
     "body": "{\"message\":\"Order validated successfully\",\"order\":{\"productId\":\"ABC123\",\"quantity\":2,\"shippingPriority\":\"express\"}}"
   }
   ```

## Lambda에서 계층 생성
<a name="publishing-layer"></a>

AWS CLI 또는 Lambda 콘솔을 사용하여 계층을 게시할 수 있습니다.

------
#### [ AWS CLI ]

[publish-layer-version](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/publish-layer-version.html) AWS CLI 명령을 실행하여 Lambda 계층을 생성합니다.

```
aws lambda publish-layer-version --layer-name my-layer --zip-file fileb://layer.zip --compatible-runtimes nodejs24.x
```

[호환되는 런타임](https://docs.aws.amazon.com/lambda/latest/api/API_PublishLayerVersion.html#lambda-PublishLayerVersion-request-CompatibleRuntimes) 파라미터는 선택 사항입니다. 지정된 경우 Lambda는 이 파라미터를 사용하여 Lambda 콘솔에서 계층을 필터링합니다.

------
#### [ Console ]

**계층을 생성하려면(콘솔)**

1. Lambda 콘솔의 [계층 페이지](https://console.aws.amazon.com/lambda/home#/layers)를 엽니다.

1. **계층 생성**을 선택합니다.

1. **.zip 파일 업로드를** 선택한 다음 이전에 생성한 .zip 아카이브를 업로드합니다.

1. (선택 사항) **호환되는 런타임**에서 계층을 빌드하는 데 사용한 Node.js 버전에 해당하는 Node.js 런타임을 선택합니다.

1. **생성(Create)**을 선택합니다.

------

## 함수에 계층 추가
<a name="nodejs-layer-adding"></a>

------
#### [ AWS CLI ]

함수에 계층을 연결하려면 [update-function-configuration](https://awscli.amazonaws.com/v2/documentation/api/latest/reference/lambda/update-function-configuration.html) AWS CLI 명령을 실행합니다. `--layers` 파라미터의 경우 계층 ARN을 사용합니다. ARN은 버전을 지정해야 합니다(예: `arn:aws:lambda:us-east-1:123456789012:layer:my-layer:1`). 자세한 내용은 [계층 및 계층 버전](chapter-layers.md#lambda-layer-versions) 섹션을 참조하세요.

```
aws lambda update-function-configuration --function-name my-function --cli-binary-format raw-in-base64-out --layers "arn:aws:lambda:us-east-1:123456789012:layer:my-layer:1"
```

**cli-binary-format** 옵션은 AWS CLI 버전 2를 사용할 때 필요합니다. 이 설정을 기본 설정으로 지정하려면 `aws configure set cli-binary-format raw-in-base64-out`을(를) 실행하세요. 자세한 내용은 *AWS Command Line Interface 사용 설명서 버전 2*에서 [AWS CLI 지원 글로벌 명령줄 옵션](https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-options.html#cli-configure-options-list)을 참조하세요.

------
#### [ Console ]

**함수에 계층을 추가하려면 다음을 수행하세요.**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)를 엽니다.

1. 함수를 선택합니다.

1. 아래로 스크롤하여 **계층** 섹션으로 이동하고 **계층 추가**를 선택하세요.

1. **계층 선택**에서 **사용자 지정 계층**을 선택하고 계층을 선택합니다.
**참고**  
계층을 생성할 때 [호환되는 런타임](https://docs.aws.amazon.com/lambda/latest/api/API_PublishLayerVersion.html#lambda-PublishLayerVersion-request-CompatibleRuntimes)을 추가하지 않은 경우 여기에 계층이 나열되지 않습니다. 대신 계층 ARN을 지정할 수 있습니다.

1. **추가**를 선택합니다.

------

## 샘플 애플리케이션
<a name="nodejs-layer-sample-app"></a>

Lambda 계층을 사용하는 방법의 자세한 예는 AWS Lambda Developer Guide GitHub 리포지토리의 [layer-nodejs](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/layer-nodejs) 샘플 애플리케이션을 참조하세요. 이 애플리케이션에는 [lodash](https://www.npmjs.com/package/lodash) 라이브러리가 있는 계층이 포함되어 있습니다. 계층을 생성한 후 해당 함수를 배포하고 간접적으로 호출하여 계층이 예상대로 작동하는지 확인할 수 있습니다.

# Lambda 컨텍스트 객체를 사용하여 Node.js 함수 정보 검색
<a name="nodejs-context"></a>

Lambda는 함수를 실행할 때 컨텍스트 객체를 [핸들러](nodejs-handler.md)에 전달합니다. 이 객체는 호출, 함수 및 실행 환경에 관한 정보를 제공하는 메서드 및 속성들을 제공합니다.

**컨텍스트 메서드**
+ `getRemainingTimeInMillis()` – 실행 시간이 초과되기까지 남은 시간(밀리초)을 반환합니다.

**컨텍스트 속성**
+ `functionName` – Lambda 함수의 이름입니다.
+ `functionVersion` – 함수의 [버전](configuration-versions.md)입니다.
+ `invokedFunctionArn` – 함수를 간접 호출할 때 사용하는 Amazon 리소스 이름(ARN)입니다. 간접 호출자가 버전 번호 또는 별칭을 지정했는지 여부를 나타냅니다.
+ `memoryLimitInMB` – 함수에 할당된 메모리의 양입니다.
+ `awsRequestId` – 호출 요청의 식별자입니다.
+ `logGroupName` – 함수에 대한 로그 그룹입니다.
+ `logStreamName` – 함수 인스턴스에 대한 로그 스트림입니다.
+ `identity` – (모바일 앱) 요청을 승인한 Amazon Cognito 자격 증명에 대한 정보입니다.
  + `cognitoIdentityId`— 인증된 Amazon Cognito ID입니다.
  + `cognitoIdentityPoolId` – 호출에 대한 권한을 부여한 Amazon Cognito ID 풀입니다.
+ `clientContext` – (모바일 앱) 클라이언트 애플리케이션이 Lambda에게 제공한 클라이언트 컨텍스트입니다.
  + `client.installation_id`
  + `client.app_title`
  + `client.app_version_name`
  + `client.app_version_code`
  + `client.app_package_name`
  + `env.platform_version`
  + `env.platform`
  + `env.make`
  + `env.model`
  + `env.locale`
  + `custom` – 클라이언트 애플리케이션에 의해 지정되는 사용자 지정 값입니다.
+ `callbackWaitsForEmptyEventLoop` - 기본값(`true`), 콜백 기반 함수 핸들러를 사용하는 경우 Lambda는 함수 간접 호출을 종료하기 전에 콜백이 실행된 후 이벤트 루프가 비어 있을 때까지 기다립니다. `false`로 설정하면 응답을 보내고 이벤트 루프가 비어 있을 때까지 기다리는 대신 콜백이 실행된 직후 간접 호출을 종료합니다. 대기 중인 이벤트는 다음 번 간접 호출 중에 계속 실행됩니다. Lambda는 Node.js 22 이전 버전의 런타임에 대해서만 콜백 기반 함수 핸들러를 지원합니다.

다음 예제 함수는 컨텍스트 정보를 로깅하고 로그의 위치를 반환합니다.

**Example index.js 파일**  

```
exports.handler = async function(event, context) {
  console.log('Remaining time: ', context.getRemainingTimeInMillis())
  console.log('Function name: ', context.functionName)
  return context.logStreamName
}
```

# Node.js Lambda 함수 로깅 및 모니터링
<a name="nodejs-logging"></a>

AWS Lambda는 자동으로 Lambda 함수를 모니터링하고 로그를 Amazon CloudWatch로 보냅니다. Lambda 함수는 함수의 각 인스턴스에 대한 CloudWatch Logs 로그 그룹 및 로그 스트림과 함께 제공됩니다. Lambda 런타임 환경은 각 호출에 관한 세부 정보를 로그 스트림에 전송하며, 함수 코드에서 로그 및 그 외 출력을 중계합니다. 자세한 내용은 [CloudWatch Logs로 Lambda 함수 로그 전송](monitoring-cloudwatchlogs.md) 섹션을 참조하세요.

이 페이지에서는 AWS Command Line Interface, Lambda 콘솔 또는 CloudWatch 콘솔을 사용하여 Lambda 함수 코드의 로그 출력하고 액세스 로그를 생성하는 방법에 대해 설명합니다.

**Topics**
+ [

## 로그를 반환하는 함수 생성
](#node-logging-output)
+ [

## Node.js에서 Lambda 고급 로깅 제어 사용
](#node-js-logging-advanced)
+ [

## Lambda 콘솔에서 로그 보기
](#nodejs-logging-console)
+ [

## CloudWatch 콘솔에서 로그 보기
](#nodejs-logging-cwconsole)
+ [

## AWS Command Line Interface(AWS CLI)(을)를 사용하여 로그 보기
](#nodejs-logging-cli)
+ [

## 로그 삭제
](#nodejs-logging-delete)

## 로그를 반환하는 함수 생성
<a name="node-logging-output"></a>

함수 코드의 로그를 출력하려면, [콘솔 객체](https://developer.mozilla.org/en-US/docs/Web/API/Console)에서 메서드를 사용하거나, `stdout` 또는 `stderr`에 쓰는 로깅 라이브러리를 사용합니다. 다음 예제는 환경 변수의 값과 이벤트 객체를 로깅합니다.

**참고**  
입력을 로깅할 때 입력 검증 및 출력 인코딩과 같은 기술을 사용하는 것이 좋습니다. 입력 데이터를 직접 로깅하는 경우 공격자가 해당 코드를 사용해서 변조를 감지하기 어렵게 만들고, 로그 항목을 위조하거나, 로그 모니터를 우회할 수 있습니다. 자세한 내용은 *Common Weakness Enumeration*의 [Improper Output Neutralization for Logs](https://cwe.mitre.org/data/definitions/117.html)를 참조하세요.

**Example index.js 파일 - 로깅**  

```
exports.handler = async function(event, context) {
  console.log("ENVIRONMENT VARIABLES\n" + JSON.stringify(process.env, null, 2))
  console.info("EVENT\n" + JSON.stringify(event, null, 2))
  console.warn("Event not processed.")
  return context.logStreamName
}
```

**Example 로그 형식**  

```
START RequestId: c793869b-ee49-115b-a5b6-4fd21e8dedac Version: $LATEST
2019-06-07T19:11:20.562Z	c793869b-ee49-115b-a5b6-4fd21e8dedac	INFO	ENVIRONMENT VARIABLES
{
  "AWS_LAMBDA_FUNCTION_VERSION": "$LATEST",
  "AWS_LAMBDA_LOG_GROUP_NAME": "/aws/lambda/my-function",
  "AWS_LAMBDA_LOG_STREAM_NAME": "2019/06/07/[$LATEST]e6f4a0c4241adcd70c262d34c0bbc85c",
  "AWS_EXECUTION_ENV": "AWS_Lambda_nodejs12.x",
  "AWS_LAMBDA_FUNCTION_NAME": "my-function",
  "PATH": "/var/lang/bin:/usr/local/bin:/usr/bin/:/bin:/opt/bin",
  "NODE_PATH": "/opt/nodejs/node10/node_modules:/opt/nodejs/node_modules:/var/runtime/node_modules",
  ...
}
2019-06-07T19:11:20.563Z	c793869b-ee49-115b-a5b6-4fd21e8dedac	INFO	EVENT
{
  "key": "value"
}
2019-06-07T19:11:20.564Z	c793869b-ee49-115b-a5b6-4fd21e8dedac	WARN	Event not processed.
END RequestId: c793869b-ee49-115b-a5b6-4fd21e8dedac
REPORT RequestId: c793869b-ee49-115b-a5b6-4fd21e8dedac	Duration: 128.83 ms	Billed Duration: 296 ms	Memory Size: 128 MB	Max Memory Used: 74 MB	Init Duration: 166.62 ms	XRAY TraceId: 1-5d9d007f-0a8c7fd02xmpl480aed55ef0	SegmentId: 3d752xmpl1bbe37e	Sampled: true
```

Node.js 런타임은 각 호출에 대해 `START`, `END` 및 `REPORT` 라인을 로그합니다. 함수에 의해 로그된 각 항목에는 타임스탬프, 요청 ID, 로그 수준을 추가합니다. 보고서 행은 다음과 같은 세부 정보를 제공합니다.

**REPORT 행 데이터 필드**
+ **RequestId** – 호출의 고유한 요청 ID입니다.
+ **지속시간** – 함수의 핸들러 메서드가 이벤트를 처리하는 데 걸린 시간입니다.
+ **청구 기간** – 호출에 대해 청구된 시간입니다.
+ **메모리 크기** - 함수에 할당된 메모리 양입니다.
+ **사용된 최대 메모리** – 함수에서 사용한 메모리 양입니다. 간접 호출이 실행 환경을 공유하는 경우 Lambda는 모든 간접 호출에서 사용된 최대 메모리를 보고합니다. 이 동작으로 인해 보고된 값이 예상보다 높을 수 있습니다.
+ **초기화 기간** – 제공된 첫 번째 요청의 경우 런타임이 핸들러 메서드 외부에서 함수를 로드하고 코드를 실행하는 데 걸린 시간입니다.
+ **XRAY TraceId** – 추적된 요청의 경우 [AWS X-Ray 추적 ID](services-xray.md)입니다.
+ **SegmentId** - 추적된 요청의 경우 X-Ray 세그먼트 ID입니다.
+ **샘플링 완료(Sampled)** – 추적된 요청의 경우 샘플링 결과입니다.

Lambda 콘솔, CloudWatch Logs 콘솔 또는 명령줄에서 로그를 볼 수 있습니다.

## Node.js에서 Lambda 고급 로깅 제어 사용
<a name="node-js-logging-advanced"></a>

함수의 로그를 캡처, 처리 및 사용하는 방법을 더 잘 제어할 수 있도록 지원되는 Node.js 런타임에 대한 다음의 로깅 옵션을 구성할 수 있습니다.
+ **로그 형식** - 함수 로그의 경우 일반 텍스트와 구조화된 JSON 형식 중에서 선택
+ **로그 수준** - JSON 형식의 로그의 경우, Lambda가 Amazon CloudWatch로 전송하는 로그의 세부 수준(ERROR, DEBUG 또는 INFO 등)을 선택
+ **로그 그룹** - 함수가 로그를 보내는 CloudWatch 로그 그룹을 선택

이러한 로깅 옵션에 대한 자세한 내용과 이를 사용하도록 함수를 구성하는 방법에 대한 지침은 [Lambda 함수에 대한 고급 로깅 제어 구성](monitoring-logs.md#monitoring-cloudwatchlogs-advanced)을 참조하세요.

Node.js Lambda 함수에서 로그 형식 및 로그 수준 옵션을 사용하려면 다음 섹션의 지침을 참조하세요.

### Node.js에서 구조화된 JSON 로그 사용
<a name="nodejs-logging-advanced-JSON"></a>

함수의 로그 형식으로 JSON을 선택하면 Lambda는 `console.trace`, `console.debug`, `console.log`, `console.info`, `console.error` 및 `console.warn`의 콘솔 메서드를 사용gksms 로그 출력을 구조화된 JSON으로 CloudWatch에 전송합니다. 각 JSON 로그 객체에는 다음 키가 있는 4개의 키 값 페어가 포함되어 있습니다.
+ `"timestamp"` - 로그 메시지가 생성된 시간
+ `"level"` - 메시지에 할당된 로그 수준
+ `"message"` - 로그 메시지의 내용
+ `"requestId"` - 함수 간접 호출의 고유한 요청 ID

함수에서 사용하는 로깅 방법에 따라 이 JSON 객체에 추가 키 페어가 포함될 수도 있습니다. 예를 들어 함수가 `console` 메서드를 통해 여러 인수를 사용하여 오류 객체를 기록하는 경우 JSON 객체에는 키 `errorMessage`, `errorType`, `stackTrace`와 함께 추가 키 값 페어가 포함됩니다.

코드에서 이미 AWS Lambda용 Powertools 같은 다른 로깅 라이브러리를 사용하여 JSON 구조화된 로그를 생성하는 경우에는 변경할 필요가 없습니다. Lambda는 이미 JSON으로 인코딩된 로그를 이중 인코딩하지 않으므로 함수의 애플리케이션 로그는 이전과 같이 계속 캡처됩니다.

AWS Lambda용 Powertools 로깅 패키지를 사용하여 Node.js 런타임에서 JSON 구조의 로그를 생성하는 방법에 대한 자세한 내용은 [TypeScript Lambda 함수 로깅 및 모니터링](typescript-logging.md)을 참조하세요.

#### JSON 형식의 로그 출력 예제
<a name="nodejs-logging-examples"></a>

다음 예제는 함수의 로그 형식을 JSON으로 설정할 때 단일 및 다중 인수를 포함한 `console` 메서드를 사용하여 생성된 다양한 로그 출력이 CloudWatch Logs에 캡처되는 방법을 보여줍니다.

첫 번째 예제에서는 `console.error` 메서드를 사용하여 간단한 문자열을 출력합니다.

**Example Node.js 로깅 코드**  

```
export const handler = async (event) => {
  console.error("This is a warning message");
  ...
}
```

**Example JSON 로그 레코드**  

```
{
    "timestamp":"2025-11-01T00:21:51.358Z",
    "level":"ERROR",
    "message":"This is a warning message",
    "requestId":"93f25699-2cbf-4976-8f94-336a0aa98c6f"
}
```

`console` 메서드와 함께 단일 또는 다중 인수를 사용하여 더 복잡한 구조의 로그 메시지를 출력할 수도 있습니다. 다음 예제에서는 `console.log`를 사용하여 단일 인수를 사용하여 두 개의 키 값 페어를 출력합니다. Lambda가 CloudWatch Logs로 전송하는 JSON 객체의 `"message"` 필드는 문자열 필드가 아닙니다.

**Example Node.js 로깅 코드**  

```
export const handler = async (event) => {
  console.log({data: 12.3, flag: false});
  ...
}
```

**Example JSON 로그 레코드**  

```
{
    "timestamp": "2025-12-08T23:21:04.664Z",
    "level": "INFO",
    "requestId": "405a4537-9226-4216-ac59-64381ec8654a",
    "message": {
        "data": 12.3,
        "flag": false
    }
}
```

다음 예제에서는 `console.log` 메서드를 다시 사용하여 로그 출력을 생성합니다. 이번에는 메서드가 두 개의 인수, 즉 두 개의 키 값 페어를 포함하는 맵과 식별 문자열을 사용합니다. 이 경우에는 두 개의 인수를 제공했으므로 Lambda는 `"message"` 필드를 문자열 필드로 설정합니다.

**Example Node.js 로깅 코드**  

```
export const handler = async (event) => {
  console.log('Some object - ', {data: 12.3, flag: false});
  ...
}
```

**Example JSON 로그 레코드**  

```
{
    "timestamp": "2025-12-08T23:21:04.664Z",
    "level": "INFO",
    "requestId": "405a4537-9226-4216-ac59-64381ec8654a",
    "message": "Some object -  { data: 12.3, flag: false }"
}
```

Lambda는 `console.log` 로그 수준 INFO를 사용하여 생성된 출력을 할당합니다.

마지막 예제에서는 `console` 메서드를 사용하여 오류 객체를 CloudWatch Logs에 출력하는 방법을 보여줍니다. 여러 인수를 사용하여 오류 객체를 기록하는 경우 Lambda는 `errorMessage`, `errorType`, `stackTrace` 필드를 로그 출력에 추가합니다.

**Example Node.js 로깅 코드**  

```
export const handler = async (event) => {
  let e1 = new ReferenceError("some reference error");
  let e2 = new SyntaxError("some syntax error");
  console.log(e1);
  console.log("errors logged - ", e1, e2);
};
```

**Example JSON 로그 레코드**  

```
{
    "timestamp": "2025-12-08T23:21:04.632Z",
    "level": "INFO",
    "requestId": "405a4537-9226-4216-ac59-64381ec8654a",
    "message": {
        "errorType": "ReferenceError",
        "errorMessage": "some reference error",
        "stackTrace": [
            "ReferenceError: some reference error",
            "    at Runtime.handler (file:///var/task/index.mjs:3:12)",
            "    at Runtime.handleOnceNonStreaming (file:///var/runtime/index.mjs:1173:29)"
        ]
    }
}

{
    "timestamp": "2025-12-08T23:21:04.646Z",
    "level": "INFO",
    "requestId": "405a4537-9226-4216-ac59-64381ec8654a",
    "message": "errors logged -  ReferenceError: some reference error\n    at Runtime.handler (file:///var/task/index.mjs:3:12)\n    at Runtime.handleOnceNonStreaming 
    (file:///var/runtime/index.mjs:1173:29) SyntaxError: some syntax error\n    at Runtime.handler (file:///var/task/index.mjs:4:12)\n    at Runtime.handleOnceNonStreaming 
    (file:///var/runtime/index.mjs:1173:29)",
    "errorType": "ReferenceError",
    "errorMessage": "some reference error",
    "stackTrace": [
        "ReferenceError: some reference error",
        "    at Runtime.handler (file:///var/task/index.mjs:3:12)",
        "    at Runtime.handleOnceNonStreaming (file:///var/runtime/index.mjs:1173:29)"
    ]
}
```

여러 오류 유형을 로깅하는 경우 `console` 메서드에 제공된 첫 번째 오류 유형에서 추가 필드 `errorMessage`, `errorType`, `stackTrace`가 추출됩니다.

### 구조화된 JSON 로그가 포함된 임베디드 메트릭 형식(EMF) 클라이언트 라이브러리 사용
<a name="nodejs-logging-advanced-emf"></a>

AWS는 [임베디드 지표 형식 로그](https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/CloudWatch_Embedded_Metric_Format_Libraries.html)(EMF)를 생성하는 데 사용할 수 있는 오픈 소스 클라이언트 라이브러리를 제공합니다. 이러한 라이브러리를 사용하는 기존 함수를 소유하고 있고 함수의 로그 형식을 JSON으로 변경하면 CloudWatch가 코드에서 내보내는 지표를 더 이상 인식하지 못할 수 있습니다.

현재 코드에서 `console.log`를 사용하거나 또는 AWS Lambda용 Powertools(TypeScript)를 사용하여 직접 EMF 로그를 내보내는 경우에도 함수의 로그 형식을 JSON으로 변경하면 CloudWatch에서 해당 로그를 구문분석할 수 없습니다.

**중요**  
CloudWatch에서 함수의 EMF 로그를 계속해서 적절하게 구문분석하려면 [EMF](https://www.npmjs.com/package/aws-embedded-metrics) 및 [AWS Lambda용 Powertools](https://github.com/aws-powertools/powertools-lambda-typescript) 라이브러리를 최신 버전으로 업데이트합니다. 또한 JSON 로그 형식으로 전환하는 경우 테스트를 수행하여 함수에 내장된 지표와의 호환성을 확인하는 것이 좋습니다. `console.log`를 사용하여 직접 EMF 로그를 내보내는 코드의 경우 다음 코드 예제에서 표시된 것처럼 해당 메트릭을 직접 `stdout`로 출력하도록 코드를 변경합니다.

**Example 임베디드 메트릭을 `stdout`로 방출하는 코드**  

```
process.stdout.write(JSON.stringify(
    {
        "_aws": {
            "Timestamp": Date.now(),
            "CloudWatchMetrics": [{
                "Namespace": "lambda-function-metrics",
                "Dimensions": [["functionVersion"]],
                "Metrics": [{
                    "Name": "time",
                    "Unit": "Milliseconds",
                    "StorageResolution": 60
                }]
            }]
        },
        "functionVersion": "$LATEST",
        "time": 100,
        "requestId": context.awsRequestId
    }
) + "\n")
```

### Node.js에서 로그 수준 필터링 사용
<a name="nodejs-logging-advanced-level"></a>

AWS Lambda에서 애플리케이션 로그를 로그 수준에 따라 필터링하려면 함수에서 JSON 형식의 로그를 사용해야 합니다. 다음 두 가지 방법으로 이 작업을 달성할 수 있습니다.
+ 표준 콘솔 메서드를 사용하여 로그 출력을 생성하고 JSON 로그 형식을 사용하도록 함수를 구성합니다. AWS Lambda은 그런 다음 [Node.js에서 구조화된 JSON 로그 사용](#nodejs-logging-advanced-JSON)에서 설명하는 JSON 객체의 “레벨” 키 값 쌍을 사용하여 로그 출력을 필터링합니다. 함수의 로그 형식을 구성하는 방법을 알아보려면 [Lambda 함수에 대한 고급 로깅 제어 구성](monitoring-logs.md#monitoring-cloudwatchlogs-advanced)를 참조하세요.
+ 다른 로깅 라이브러리 또는 메서드를 사용하여 로그 출력 수준을 정의하는 “레벨” 키 값 쌍이 포함된 JSON 구조화된 로그를 코드에 만들 수 있습니다. 예를 들어 AWS Lambda용 Powertools를 사용하여 코드로부터 JSON 구조화된 로그 출력을 생성할 수 있습니다. Powertools를 Node.js 런타임과 함께 사용하는 방법에 대한 자세한 내용은 [TypeScript Lambda 함수 로깅 및 모니터링](typescript-logging.md)을 참조하세요.

  Lambda가 함수 로그를 필터링하려면 JSON 로그 출력에 `"timestamp"` 키 값 쌍도 포함해야 합니다. 시간은 유효한 [RFC 3339](https://www.ietf.org/rfc/rfc3339.txt) 타임스탬프 형식으로 지정해야 합니다. 유효한 타임스탬프를 제공하지 않으면 Lambda는 로그에 레벨 INFO를 할당하고 타임스탬프를 추가합니다.

로그 수준 필터링을 사용하도록 함수를 구성할 때는 다음 옵션 중에서 AWS Lambda이 CloudWatch 로그로 전송하기를 원하는 로그 수준을 선택합니다.


| 로그 수준 | 표준 사용량 | 
| --- | --- | 
| TRACE(최대 세부 정보) | 코드 실행 경로를 추적하는 데 사용되는 가장 세밀한 정보 | 
| DEBUG | 시스템 디버깅에 대한 세부 정보 | 
| INFO | 함수의 정상 작동을 기록하는 메시지 | 
| WARN | 해결되지 않을 경우 예상치 못한 동작으로 이어질 수 있는 잠재적 오류에 대한 메시지 | 
| 오류 | 코드가 예상대로 작동하지 못하게 하는 문제에 대한 메시지 | 
| FATAL(최소 세부 정보) | 응용 프로그램 작동을 중지시키는 심각한 오류에 대한 메시지 | 

Lambda는 선택한 수준 이하의 로그만 Cloudwatch로 전송합니다. 예를 들어 로그 수준을 WARN으로 구성하면 Lambda는 WARN, ERROR 및 FATAL에 해당하는 로그를 전송합니다.

## Lambda 콘솔에서 로그 보기
<a name="nodejs-logging-console"></a>

Lambda 함수를 간접 호출한 후 Lambda 콘솔을 사용하여 로그 출력을 볼 수 있습니다.

포함된 **코드** 편집기에서 코드를 테스트할 수 있는 경우 **실행 결과**에서 로그를 찾을 수 있습니다. 콘솔 테스트 기능을 사용하여 함수를 간접적으로 간접 호출하면 **세부 정보** 섹션에서 **로그 출력**을 찾을 수 있습니다.

## CloudWatch 콘솔에서 로그 보기
<a name="nodejs-logging-cwconsole"></a>

Amazon CloudWatch 콘솔을 사용하여 모든 Lambda 함수 호출에 대한 로그를 볼 수 있습니다.

**CloudWatch 콘솔에서 로그를 보려면**

1. CloudWatch 콘솔에서 [로그 그룹 페이지](https://console.aws.amazon.com/cloudwatch/home?#logs:)를 엽니다.

1. 함수(**/aws/lambda/*your-function-name***)에 대한 로그 그룹을 선택합니다.

1. 로그 스트림을 선택합니다.

각 로그 스트림은 [함수의 인스턴스](lambda-runtime-environment.md)에 해당합니다. 로그 스트림은 Lambda 함수를 업데이트할 때, 그리고 동시 호출을 처리하기 위해 추가 인스턴스가 생성될 때 나타납니다. 특정 호출에 대한 로그를 찾으려면 AWS X-Ray로 함수를 계측하는 것이 좋습니다. X-Ray는 요청 및 로그 스트림에 대한 세부 정보를 기록합니다.

## AWS Command Line Interface(AWS CLI)(을)를 사용하여 로그 보기
<a name="nodejs-logging-cli"></a>

AWS CLI은(는) 명령줄 셸의 명령을 사용하여 AWS 서비스와 상호 작용할 수 있는 오픈 소스 도구입니다. 이 섹션의 단계를 완료하려면 [AWS CLI 버전 2](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html)가 필요합니다.

[AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-welcome.html)를 사용하면 `--log-type` 명령 옵션을 통해 호출에 대한 로그를 검색할 수 있습니다. 호출에서 base64로 인코딩된 로그를 최대 4KB까지 포함하는 `LogResult` 필드가 응답에 포함됩니다.

**Example 로그 ID 검색**  
다음 예제에서는 `LogResult`이라는 함수의 `my-function` 필드에서 *로그 ID*를 검색하는 방법을 보여줍니다.  

```
aws lambda invoke --function-name my-function out --log-type Tail
```
다음 결과가 표시됩니다:  

```
{
    "StatusCode": 200,
    "LogResult": "U1RBUlQgUmVxdWVzdElkOiA4N2QwNDRiOC1mMTU0LTExZTgtOGNkYS0yOTc0YzVlNGZiMjEgVmVyc2lvb...",
    "ExecutedVersion": "$LATEST"
}
```

**Example decode the logs**  
동일한 명령 프롬프트에서 `base64` 유틸리티를 사용하여 로그를 디코딩합니다. 다음 예제에서는 `my-function`에 대한 base64로 인코딩된 로그를 검색하는 방법을 보여줍니다.  

```
aws lambda invoke --function-name my-function out --log-type Tail \
--query 'LogResult' --output text --cli-binary-format raw-in-base64-out | base64 --decode
```
**cli-binary-format** 옵션은 AWS CLI 버전 2를 사용할 때 필요합니다. 이 설정을 기본 설정으로 지정하려면 `aws configure set cli-binary-format raw-in-base64-out`을(를) 실행하세요. 자세한 내용은 *AWS Command Line Interface 사용 설명서 버전 2*에서 [AWS CLI 지원 글로벌 명령줄 옵션](https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-options.html#cli-configure-options-list)을 참조하세요.  
다음 결과가 표시됩니다.  

```
START RequestId: 57f231fb-1730-4395-85cb-4f71bd2b87b8 Version: $LATEST
"AWS_SESSION_TOKEN": "AgoJb3JpZ2luX2VjELj...", "_X_AMZN_TRACE_ID": "Root=1-5d02e5ca-f5792818b6fe8368e5b51d50;Parent=191db58857df8395;Sampled=0"",ask/lib:/opt/lib",
END RequestId: 57f231fb-1730-4395-85cb-4f71bd2b87b8
REPORT RequestId: 57f231fb-1730-4395-85cb-4f71bd2b87b8  Duration: 79.67 ms      Billed Duration: 80 ms         Memory Size: 128 MB     Max Memory Used: 73 MB
```
`base64` 유틸리티는 Linux, macOS 및 [Ubuntu on Windows](https://docs.microsoft.com/en-us/windows/wsl/install-win10)에서 사용할 수 있습니다. macOS 사용자는 `base64 -D`를 사용해야 할 수도 있습니다.

**Example get-logs.sh 스크립트**  
동일한 명령 프롬프트에서 다음 스크립트를 사용하여 마지막 5개 로그 이벤트를 다운로드합니다. 이 스크립트는 `sed`를 사용하여 출력 파일에서 따옴표를 제거하고, 로그를 사용할 수 있는 시간을 허용하기 위해 15초 동안 대기합니다. 출력에는 Lambda의 응답과 `get-log-events` 명령의 출력이 포함됩니다.  
다음 코드 샘플의 내용을 복사하고 Lambda 프로젝트 디렉터리에 `get-logs.sh`로 저장합니다.  
**cli-binary-format** 옵션은 AWS CLI 버전 2를 사용할 때 필요합니다. 이 설정을 기본 설정으로 지정하려면 `aws configure set cli-binary-format raw-in-base64-out`을(를) 실행하세요. 자세한 내용은 *AWS Command Line Interface 사용 설명서 버전 2*에서 [AWS CLI 지원 글로벌 명령줄 옵션](https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-options.html#cli-configure-options-list)을 참조하세요.  

```
#!/bin/bash
aws lambda invoke --function-name my-function --cli-binary-format raw-in-base64-out --payload '{"key": "value"}' out
sed -i'' -e 's/"//g' out
sleep 15
aws logs get-log-events --log-group-name /aws/lambda/my-function --log-stream-name stream1 --limit 5
```

**Example macOS 및 Linux(전용)**  
동일한 명령 프롬프트에서 macOS 및 Linux 사용자는 스크립트가 실행 가능한지 확인하기 위해 다음 명령을 실행해야 할 수 있습니다.  

```
chmod -R 755 get-logs.sh
```

**Example 마지막 5개 로그 이벤트 검색**  
동일한 명령 프롬프트에서 다음 스크립트를 실행하여 마지막 5개 로그 이벤트를 가져옵니다.  

```
./get-logs.sh
```
다음 결과가 표시됩니다:  

```
{
    "StatusCode": 200,
    "ExecutedVersion": "$LATEST"
}
{
    "events": [
        {
            "timestamp": 1559763003171,
            "message": "START RequestId: 4ce9340a-b765-490f-ad8a-02ab3415e2bf Version: $LATEST\n",
            "ingestionTime": 1559763003309
        },
        {
            "timestamp": 1559763003173,
            "message": "2019-06-05T19:30:03.173Z\t4ce9340a-b765-490f-ad8a-02ab3415e2bf\tINFO\tENVIRONMENT VARIABLES\r{\r  \"AWS_LAMBDA_FUNCTION_VERSION\": \"$LATEST\",\r ...",
            "ingestionTime": 1559763018353
        },
        {
            "timestamp": 1559763003173,
            "message": "2019-06-05T19:30:03.173Z\t4ce9340a-b765-490f-ad8a-02ab3415e2bf\tINFO\tEVENT\r{\r  \"key\": \"value\"\r}\n",
            "ingestionTime": 1559763018353
        },
        {
            "timestamp": 1559763003218,
            "message": "END RequestId: 4ce9340a-b765-490f-ad8a-02ab3415e2bf\n",
            "ingestionTime": 1559763018353
        },
        {
            "timestamp": 1559763003218,
            "message": "REPORT RequestId: 4ce9340a-b765-490f-ad8a-02ab3415e2bf\tDuration: 26.73 ms\tBilled Duration: 27 ms \tMemory Size: 128 MB\tMax Memory Used: 75 MB\t\n",
            "ingestionTime": 1559763018353
        }
    ],
    "nextForwardToken": "f/34783877304859518393868359594929986069206639495374241795",
    "nextBackwardToken": "b/34783877303811383369537420289090800615709599058929582080"
}
```

## 로그 삭제
<a name="nodejs-logging-delete"></a>

함수를 삭제해도 로그 그룹이 자동으로 삭제되지 않습니다. 로그를 무기한 저장하지 않으려면 로그 그룹을 삭제하거나 로그가 자동으로 삭제되는 [보존 기간을 구성](https://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/Working-with-log-groups-and-streams.html#SettingLogRetention)하세요.

# AWS Lambda에서 Node.js 코드 계측
<a name="nodejs-tracing"></a>

Lambda는 AWS X-Ray와 통합되어 Lambda 애플리케이션을 추적, 디버깅 및 최적화할 수 있습니다. Lambda 함수와 기타 AWS 서비스를 포함할 수 있는 애플리케이션의 리소스를 탐색할 때 X-Ray를 사용하여 요청을 추적할 수 있습니다.

추적 데이터를 X-Ray로 전송하려면 다음 두 SDK 라이브러리 중 하나를 사용할 수 있습니다.
+ [AWS Distro for OpenTelemetry(ADOT)](https://aws.amazon.com/otel) - 안전하게 프로덕션 준비가 된 AWS에서 지원하는 OpenTelemetry(OTEL) SDK의 배포입니다.
+ [AWS X-Ray SDK for Node.js](https://docs.aws.amazon.com/xray/latest/devguide/xray-sdk-nodejs.html) — 추적 데이터를 생성하고 X-Ray에 전송하는 SDK입니다.

각 SDK는 텔레메트리 데이터를 X-Ray 서비스로 전송하는 방법을 제공합니다. X-Ray를 사용하여 애플리케이션의 성능 지표를 확인하고, 필터링하고, 인사이트를 얻어 문제와 최적화 기회를 식별할 수 있습니다.

**중요**  
X-Ray와 Powertools for AWS Lambda SDK는 AWS에서 제공하는 긴밀하게 통합된 계측 솔루션의 일부입니다. ADOT Lambda Layer는 일반적으로 더 많은 데이터를 수집하는 추적 계측기에 대한 전체 업계 표준의 일부이지만 모든 사용 사례에 적합하지는 않을 수 있습니다. 어떤 솔루션을 사용하든 X-Ray에서 엔드 투 엔드 추적 기능을 구현할 수 있습니다. 둘 중 하나를 선택하는 방법에 대해 자세히 알아보려면 [AWS Distro for Open Telemetry와 X-Ray SDK 중에서 선택하기](https://docs.aws.amazon.com/xray/latest/devguide/xray-instrumenting-your-app.html#xray-instrumenting-choosing)를 참조하세요.

**Topics**
+ [

## ADOT를 사용하여 Node.js 함수 계측
](#nodejs-adot)
+ [

## X-Ray SDK를 사용하여 Node.js 함수 계측
](#nodejs-xray-sdk)
+ [

## Lambda 콘솔을 사용하여 추적 활성화
](#nodejs-tracing-console)
+ [

## Lambda API를 사용하여 추적 활성화
](#nodejs-tracing-api)
+ [

## CloudFormation을 사용하여 추적 활성화
](#nodejs-tracing-cloudformation)
+ [

## X-Ray 추적 해석
](#nodejs-tracing-interpretation)
+ [

## 계층에 런타임 종속성 저장(X-Ray SDK)
](#nodejs-tracing-layers)

## ADOT를 사용하여 Node.js 함수 계측
<a name="nodejs-adot"></a>

ADOT는 OTel SDK를 사용하여 원격 측정 데이터를 수집하는 데 필요한 모든 것을 패키징할 수 있는 완전 관리형 Lambda [계층](chapter-layers.md)을 제공합니다. 이 계층을 사용하면 모든 함수 코드를 수정하지 않고도 Lambda 함수를 계측할 수 있습니다. 계층을 구성하여 OTel의 사용자 지정 초기화를 수행할 수도 있습니다. 자세한 내용은 ADOT 설명서의 [Lambda에서 ADOT 컬렉터에 대한 사용자 지정 구성](https://aws-otel.github.io/docs/getting-started/lambda#custom-configuration-for-the-adot-collector-on-lambda)을 참조하세요.

Node.js 런타임의 경우 **ADOT Node.js용 AWS 관리형 Lambda 계층**을 추가하여 함수를 자동으로 계측할 수 있습니다. 이 계층을 추가하는 방법에 대한 자세한 지침은 ADOT 설명서의 [AWS Distro for OpenTelemetry Lambda Support for JavaScript](https://aws-otel.github.io/docs/getting-started/lambda/lambda-js)를 참조하세요.

## X-Ray SDK를 사용하여 Node.js 함수 계측
<a name="nodejs-xray-sdk"></a>

Lambda 함수가 애플리케이션의 다른 리소스에 대해 수행하는 호출에 대한 세부 정보를 기록하려면 AWS X-Ray SDK for Node.js를 사용할 수도 있습니다. SDK를 가져오려면 애플리케이션의 종속성에 `aws-xray-sdk-core` 패키지를 추가합니다.

**Example [blank-nodejs/package.json](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-nodejs/package.json)**  

```
{
  "name": "blank-nodejs",
  "version": "1.0.0",
  "private": true,
  "devDependencies": {
    "jest": "29.7.0"
  },
  "dependencies": {
    "@aws-sdk/client-lambda": "3.345.0",
    "aws-xray-sdk-core": "3.5.3"
  },
  "scripts": {
    "test": "jest"
  }
}
```

[AWS SDK for JavaScript v3](https://docs.aws.amazon.com/sdk-for-javascript/v3/developer-guide/welcome.html)에서 AWS SDK 클라이언트를 계측하려면 `captureAWSv3Client` 메서드를 사용하여 클라이언트 인스턴스를 래핑합니다.

**Example [blank-nodejs/function/index.js](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-nodejs/function/index.js) – AWS SDK 클라이언트 추적**  

```
const AWSXRay = require('aws-xray-sdk-core');
const { LambdaClient, GetAccountSettingsCommand } = require('@aws-sdk/client-lambda');

// Create client outside of handler to reuse
const lambda = AWSXRay.captureAWSv3Client(new LambdaClient());

// Handler
exports.handler = async function(event, context) {
    event.Records.forEach(record => {
  ...
```

Lambda 런타임은 X-Ray SDK를 구성하는 몇 가지 환경 변수를 설정합니다. 예를 들어 Lambda는 X-Ray SDK에서 런타임 오류가 발생하지 않도록 `AWS_XRAY_CONTEXT_MISSING`을(를) `LOG_ERROR`로 설정합니다. 사용자 지정 컨텍스트 누락 전략을 설정하려면 값이 없도록 함수 구성에서 환경 변수를 재정의합니다. 그러면 컨텍스트 누락 전략을 프로그래밍 방식으로 설정할 수 있습니다.

**Example 초기화 코드 예제**  

```
const AWSXRay = require('aws-xray-sdk-core');

// Configure the context missing strategy to do nothing
AWSXRay.setContextMissingStrategy(() => {});
```

자세한 내용은 [Lambda 환경 변수 작업](configuration-envvars.md) 섹션을 참조하세요.

올바른 종속성을 추가하고 필요한 코드를 변경한 후 Lambda 콘솔 또는 API를 통해 함수의 구성에서 추적을 활성화합니다.

## Lambda 콘솔을 사용하여 추적 활성화
<a name="nodejs-tracing-console"></a>

콘솔을 사용하여 Lambda 함수에 대한 활성 추적을 전환하려면 다음 단계를 따르십시오.

**활성 추적 켜기**

1. Lambda 콘솔의 [함수 페이지](https://console.aws.amazon.com/lambda/home#/functions)를 엽니다.

1. 함수를 선택합니다.

1. **구성(Configuration)**을 선택한 다음 **모니터링 및 운영 도구(Monitoring and operations tools)**를 선택합니다.

1. **추가 모니터링 도구**에서 **편집**을 선택합니다.

1. **CloudWatch 애플리케이션 신호 및 AWS X-Ray**에서 **Lambda 서비스 트레이스**에 대해 **활성화**를 선택합니다.

1. **저장**을 선택합니다.

## Lambda API를 사용하여 추적 활성화
<a name="nodejs-tracing-api"></a>

AWS CLI 또는 AWS SDK를 사용하여 Lambda 함수에 대한 추적을 구성하고 다음 API 작업을 사용합니다.
+ [UpdateFunctionConfiguration](https://docs.aws.amazon.com/lambda/latest/api/API_UpdateFunctionConfiguration.html)
+ [GetFunctionConfiguration](https://docs.aws.amazon.com/lambda/latest/api/API_GetFunctionConfiguration.html)
+ [CreateFunction](https://docs.aws.amazon.com/lambda/latest/api/API_CreateFunction.html)

다음 예제 AWS CLI 명령은 **my-function**이라는 함수에 대한 활성 추적을 사용 설정합니다.

```
aws lambda update-function-configuration --function-name my-function \
--tracing-config Mode=Active
```

추적 모드는 함수 버전을 게시할 때 버전별 구성의 일부입니다. 게시된 버전에 대한 추적 모드는 변경할 수 없습니다.

## CloudFormation을 사용하여 추적 활성화
<a name="nodejs-tracing-cloudformation"></a>

CloudFormation 템플릿에서 `AWS::Lambda::Function` 리소스에 대한 추적을 활성화하려면 `TracingConfig` 속성을 사용합니다.

**Example [function-inline.yml](https://github.com/awsdocs/aws-lambda-developer-guide/blob/master/templates/function-inline.yml) – 추적 구성**  

```
Resources:
  function:
    Type: [AWS::Lambda::Function](https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-lambda-function.html)
    Properties:
      TracingConfig:
        Mode: Active
      ...
```

AWS Serverless Application Model(AWS SAM) `AWS::Serverless::Function` 리소스의 경우 `Tracing` 속성을 사용합니다.

**Example [template.yml](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-nodejs/template.yml) – 추적 구성**  

```
Resources:
  function:
    Type: [AWS::Serverless::Function](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-resource-function.html)
    Properties:
      Tracing: Active
      ...
```

## X-Ray 추적 해석
<a name="nodejs-tracing-interpretation"></a>

함수에 추적 데이터를 X-Ray로 업로드할 권한이 있어야 합니다. Lambda 콘솔에서 추적을 활성화하면 Lambda가 필요한 권한을 함수의 [실행 역할](lambda-intro-execution-role.md)에 추가합니다. 그렇지 않으면 실행 역할에 [AWSXRayDaemonWriteAccess](https://console.aws.amazon.com/iam/home#/policies/arn:aws:iam::aws:policy/AWSXRayDaemonWriteAccess) 정책을 추가합니다.

활성 추적을 구성하면 애플리케이션을 통해 특정 요청을 관찰할 수 있습니다. [ X-Ray 서비스 그래프](https://docs.aws.amazon.com/xray/latest/devguide/aws-xray.html#xray-concepts-servicegraph)는 애플리케이션 및 모든 구성 요소에 대한 정보를 보여줍니다. 다음 예제에서는 2개의 함수가 있는 애플리케이션을 보여줍니다. 기본 함수는 이벤트를 처리하고 때로는 오류를 반환합니다. 맨 위의 두 번째 함수는 첫 번째의 로그 그룹에 나타나는 오류를 처리하고 AWS SDK를 사용하여 X-Ray, Amazon Simple Storage Service(Amazon S3), Amazon CloudWatch Logs를 호출합니다.

![\[\]](http://docs.aws.amazon.com/ko_kr/lambda/latest/dg/images/sample-errorprocessor-servicemap.png)


X-Ray는 애플리케이션에 대한 모든 요청을 추적하지 않습니다. X-Ray는 모든 요청의 대표 샘플을 여전히 제공하면서 추적이 효율적으로 수행되도록 샘플링 알고리즘을 적용합니다. 샘플링 요율은 초당 요청이 1개이며 추가 요청의 5퍼센트입니다. 함수에 대해 X-Ray 샘플링 요율을 구성할 수 없습니다.

X-Ray에서 *추적*은 하나 이상의 *서비스*에서 처리되는 요청에 대한 정보를 기록합니다. Lambda는 각 추적에 대해 2개의 세그먼트를 기록하고, 이에 따라 서비스 그래프에 2개의 노드가 생성됩니다. 다음 이미지에서는 이 두 노드를 강조 표시합니다.

![\[\]](http://docs.aws.amazon.com/ko_kr/lambda/latest/dg/images/xray-servicemap-function.png)


왼쪽의 첫 번째 노드는 호출 요청을 수신하는 Lambda 서비스를 나타냅니다. 두 번째 노드는 특정 Lambda 함수를 나타냅니다. 다음 예에서는 이러한 2개의 세그먼트가 있는 추적을 보여줍니다. 둘 다 이름이 **my-function** 이지만 하나는 오리진이 `AWS::Lambda`이고 다른 하나는 오리진이 `AWS::Lambda::Function`입니다. `AWS::Lambda` 세그먼트에 오류가 표시되면 Lambda 서비스에 문제가 있는 것입니다. `AWS::Lambda::Function` 세그먼트에 오류가 표시되면 함수에 문제가 있는 것입니다.

![\[\]](http://docs.aws.amazon.com/ko_kr/lambda/latest/dg/images/V2_sandbox_images/my-function-2-v1.png)


이 예제에서는 3개의 하위 세그먼트를 표시하도록 `AWS::Lambda::Function` 세그먼트를 확장합니다.

**참고**  
AWS는 현재 Lambda 서비스에 대한 변경 사항을 구현하고 있습니다. 이러한 변경으로 인해, AWS 계정의 여러 Lambda 함수에서 내보내는 시스템 로그 메시지와 추적 세그먼트의 구조와 내용 간에 약간의 차이가 있을 수 있습니다.  
여기에 표시된 예제 트레이스는 이전 스타일의 함수 세그먼트를 보여줍니다. 이전 스타일 세그먼트와 새로운 스타일 세그먼트의 차이점은 다음 단락들에 설명되어 있습니다.  
이러한 변경 사항은 앞으로 몇 주 동안 구현되며, 중국 및 GovCloud 리전을 제외한 모든 AWS 리전의 모든 기능은 새로운 형식의 로그 메시지 및 추적 세그먼트를 사용하도록 전환됩니다.

이전 스타일의 함수 세그먼트에는 다음과 같은 하위 세그먼트가 포함됩니다.
+ **초기화** – 함수를 로드하고 [초기화 코드](foundation-progmodel.md)를 실행하는 데 소요된 시간을 나타냅니다. 이 하위 세그먼트는 함수의 각 인스턴스에서 처리하는 첫 번째 이벤트에 대해서만 표시됩니다.
+ **호출**— 핸들러 코드를 실행하는 데 소요된 시간을 나타냅니다.
+ **오버헤드** – Lambda 런타임이 다음 이벤트를 처리하기 위해 준비하는 데 소비하는 시간을 나타냅니다.

새로운 스타일의 함수 세그먼트에는 `Invocation` 하위 세그먼트가 포함되지 않습니다. 대신, 고객 하위 세그먼트는 함수 세그먼트에 직접 연결됩니다. 이전 스타일과 새로운 스타일의 함수 세그먼트의 구조에 대한 자세한 내용은 [X-Ray 추적 이해](services-xray.md#services-xray-traces)를 참조하세요.

HTTP 클라이언트를 계측하고, SQL 쿼리를 기록하고, 주석 및 메타데이터가 있는 사용자 지정 하위 세그먼트를 생성할 수도 있습니다. 자세한 내용은 *AWS X-Ray 개발자 안내서*의 [AWS X-Ray SDK for Node.js](https://docs.aws.amazon.com/xray/latest/devguide/xray-sdk-nodejs.html)를 참조하십시오.

**가격 책정**  
X-Ray 추적을 AWS 프리 티어의 일부로서 특정 한도까지 매월 무료로 사용할 수 있습니다. 해당 한도를 초과하면 추적 저장 및 검색에 대한 X-Ray 요금이 부과됩니다. 자세한 내용은 [AWS X-Ray 요금](https://aws.amazon.com/xray/pricing/)을 참조하십시오.

## 계층에 런타임 종속성 저장(X-Ray SDK)
<a name="nodejs-tracing-layers"></a>

X-Ray SDK를 사용하여 AWS SDK 클라이언트를 계측하는 경우 함수 코드와 배포 패키지가 상당히 커질 수 있습니다. 함수 코드를 업데이트할 때마다 런타임 종속성을 업로드하지 않으려면 X-Ray SDK를 [Lambda 계층](chapter-layers.md)에 패키징합니다.

다음 예제에서는 AWS X-Ray SDK for Node.js를 저장하는 `AWS::Serverless::LayerVersion` 리소스를 보여줍니다.

**Example [template.yml](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-nodejs/template.yml) – 종속성 계층**  

```
Resources:
  function:
    Type: [AWS::Serverless::Function](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-resource-function.html)
    Properties:
      CodeUri: function/.
      Tracing: Active
      Layers:
        - !Ref libs
      ...
  libs:
    Type: [AWS::Serverless::LayerVersion](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-resource-layerversion.html)
    Properties:
      LayerName: blank-nodejs-lib
      Description: Dependencies for the blank sample app.
      ContentUri: lib/.
      CompatibleRuntimes:
        - nodejs24.x
```

이 구성을 사용하면 런타임 종속성을 변경하는 경우 라이브러리 계층만 업데이트하면 됩니다. 함수 배포 패키지에는 코드만 포함되어 있으므로 이는 업로드 시간을 줄일 수 있습니다.

종속성 계층을 만들려면 배포 전에 계층 아카이브를 생성하기 위해 빌드를 변경해야 합니다. 사용 가능한 예제는 [blank-nodejs](https://github.com/awsdocs/aws-lambda-developer-guide/tree/main/sample-apps/blank-nodejs) 샘플 애플리케이션을 참조하세요.