チュートリアル: Amazon SQS での Lambda の使用 - AWS Lambda

チュートリアル: Amazon SQS での Lambda の使用

このチュートリアルでは、Amazon Simple Queue Service (Amazon SQS) キューからのメッセージを消費する Lambda 関数を作成します。Lambda 関数は、新しいメッセージがキューに追加されるたびに実行されます。この関数は、メッセージを Amazon CloudWatch Logs ストリームに書き込みます。次の図は、チュートリアルを完了するために使用する AWS リソースを示しています。

Amazon SQS メッセージ、Lambda 関数、および CloudWatch Logs ストリームを示す図

このチュートリアルを完了するには、次のステップを実行します。

  1. CloudWatch Logs にメッセージを書き込む Lambda 関数を作成します。

  2. Amazon SQS キューを作成します。

  3. Lambda イベントソースマッピングを作成します。イベントソースマッピングは Amazon SQS キューを読み取り、新しいメッセージが追加されたときに Lambda 関数を呼び出します。

  4. キューにメッセージを追加して設定をテストし、CloudWatch Logs で結果をモニタリングします。

前提条件

AWS アカウント がない場合は、以下のステップを実行して作成します。

AWS アカウントにサインアップするには
  1. https://portal.aws.amazon.com/billing/signup を開きます。

  2. オンラインの手順に従います。

    サインアップ手順の一環として、通話呼び出しを受け取り、電話キーパッドで検証コードを入力するように求められます。

    AWS アカウント にサインアップすると、AWS アカウントのルートユーザー が作成されます。ルートユーザーには、アカウントのすべてのAWS のサービスとリソースへのアクセス権があります。セキュリティのベストプラクティスとして、ユーザーに管理アクセスを割り当て、ルートユーザーのみを使用してルートユーザーアクセスが必要なタスクを実行してください。

サインアップ処理が完了すると、AWS からユーザーに確認メールが送信されます。https://aws.amazon.com/アカウント] をクリックして、いつでもアカウントの現在のアクティビティを表示し、アカウントを管理することができます。

AWS アカウント にサインアップしたら、AWS アカウントのルートユーザー をセキュリティで保護し、AWS IAM Identity Center を有効にして、管理ユーザーを作成します。これにより、日常的なタスクにルートユーザーを使用しないようにします。

AWS アカウントのルートユーザーをセキュリティで保護する
  1. ルートユーザー] を選択し、AWS アカウント のメールアドレスを入力して、アカウント所有者として AWS Management Console にサインインします。次のページでパスワードを入力します。

    ルートユーザーを使用してサインインする方法については、AWS サインイン ユーザーガイドルートユーザーとしてサインインするを参照してください。

  2. ルートユーザーの多要素認証 (MFA) を有効にします。

    手順については、「IAM ユーザーガイド」のAWS アカウント のルートユーザーの仮想 MFA デバイスを有効にする (コンソール)を参照してください。

管理アクセスを持つユーザーを作成する
  1. IAM アイデンティティセンターを有効にします。

    手順については、「AWS IAM Identity Center ユーザーガイド」の「AWS IAM Identity Center の有効化」を参照してください。

  2. IAM アイデンティティセンターで、ユーザーに管理アクセスを付与します。

    IAM アイデンティティセンターディレクトリ をアイデンティティソースとして使用するチュートリアルについては、「AWS IAM Identity Center ユーザーガイド」の「デフォルト IAM アイデンティティセンターディレクトリを使用したユーザーアクセスの設定」を参照してください。

管理アクセス権を持つユーザーとしてサインインする
  • IAM アイデンティティセンターのユーザーとしてサインインするには、IAM アイデンティティセンターのユーザーの作成時に E メールアドレスに送信されたサインイン URL を使用します。

    IAM Identity Center ユーザーを使用してサインインする方法については、AWS サインイン ユーザーガイドAWS アクセスポータルにサインインするを参照してください。

追加のユーザーにアクセス権を割り当てる
  1. IAM アイデンティティセンターで、最小特権のアクセス許可を適用するというベストプラクティスに従ったアクセス許可セットを作成します。

    手順については、「AWS IAM Identity Center ユーザーガイド」の「権限設定を作成する」を参照してください。

  2. グループにユーザーを割り当て、そのグループにシングルサインオンアクセス権を割り当てます。

    手順については、「AWS IAM Identity Center ユーザーガイド」の「グループの参加」を参照してください。

AWS Command Line Interface をまだインストールしていない場合は、「最新バージョンの AWS CLI のインストールまたは更新」にある手順に従ってインストールしてください。

このチュートリアルでは、コマンドを実行するためのコマンドラインターミナルまたはシェルが必要です。Linux および macOS では、任意のシェルとパッケージマネージャーを使用してください。

注記

Windows では、Lambda でよく使用される一部の Bash CLI コマンド (zip など) が、オペレーティングシステムの組み込みターミナルでサポートされていません。Ubuntu および Bash の Windows 統合バージョンを取得するには、Windows Subsystem for Linux をインストールします。

実行ロールを作成する

ステップ 1: 実行ロールを作成する

実行ロールとは、AWS サービスとリソースにアクセスする許可を Lambda 関数に付与する AWS Identity and Access Management (IAM) ロールです。関数が Amazon SQS から項目を読み取れるようにするには、AWSLambdaSQSQueueExecutionRole 許可ポリシーをアタッチします。

実行ロールを作成して Amazon SQS 許可ポリシーをアタッチする方法
  1. IAM コンソールのロールページを開きます。

  2. [ロールの作成] を選択します。

  3. [信頼できるエンティティタイプ] で、[AWS サービス] を選択します。

  4. [ユースケース] で、[Lambda] を選択します。

  5. [Next] を選択します。

  6. [許可ポリシー] 検索ボックスに AWSLambdaSQSQueueExecutionRole と入力します。

  7. AWSLambdaSQSQueueExecutionRole ポリシーを選択し、[Next] を選択します。

  8. [Role details] で [Role name] に lambda-sqs-role を入力してから、[Create role] を選択します。

ロールを作成したら、実行ロールの Amazon リソースネーム (ARN) を書き留めてください。これは、後のステップで必要になります。

関数を作成する

ステップ 2: Lambda 関数を作成する

Amazon SQS メッセージを処理する Lambda 関数を作成します。この関数コードは、Amazon SQS メッセージの本文を CloudWatch Logs に記録します。

このチュートリアルでは Node.js 18.x ランタイムを使用しますが、他のランタイム言語のサンプルコードも提供しています。次のボックスでタブを選択すると、関心のあるランタイムのコードが表示されます。このステップで使用する JavaScript コードは、[JavaScript] タブに表示されている最初のサンプルにあります。

.NET
AWS SDK for .NET
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

.NET を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 using Amazon.Lambda.Core; using Amazon.Lambda.SQSEvents; // Assembly attribute to enable the Lambda function's JSON input to be converted into a .NET class. [assembly: LambdaSerializer(typeof(Amazon.Lambda.Serialization.SystemTextJson.DefaultLambdaJsonSerializer))] namespace SqsIntegrationSampleCode { public async Task FunctionHandler(SQSEvent evnt, ILambdaContext context) { foreach (var message in evnt.Records) { await ProcessMessageAsync(message, context); } context.Logger.LogInformation("done"); } private async Task ProcessMessageAsync(SQSEvent.SQSMessage message, ILambdaContext context) { try { context.Logger.LogInformation($"Processed message {message.Body}"); // TODO: Do interesting work based on the new message await Task.CompletedTask; } catch (Exception e) { //You can use Dead Letter Queue to handle failures. By configuring a Lambda DLQ. context.Logger.LogError($"An error occurred"); throw; } } }
Go
SDK for Go V2
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

Go を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 package integration_sqs_to_lambda import ( "fmt" "github.com/aws/aws-lambda-go/events" "github.com/aws/aws-lambda-go/lambda" ) func handler(event events.SQSEvent) error { for _, record := range event.Records { err := processMessage(record) if err != nil { return err } } fmt.Println("done") return nil } func processMessage(record events.SQSMessage) error { fmt.Printf("Processed message %s\n", record.Body) // TODO: Do interesting work based on the new message return nil } func main() { lambda.Start(handler) }
Java
SDK for Java 2.x
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

Java を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 import com.amazonaws.services.lambda.runtime.Context; import com.amazonaws.services.lambda.runtime.RequestHandler; import com.amazonaws.services.lambda.runtime.events.SQSEvent; import com.amazonaws.services.lambda.runtime.events.SQSEvent.SQSMessage; public class Function implements RequestHandler<SQSEvent, Void> { @Override public Void handleRequest(SQSEvent sqsEvent, Context context) { for (SQSMessage msg : sqsEvent.getRecords()) { processMessage(msg, context); } context.getLogger().log("done"); return null; } private void processMessage(SQSMessage msg, Context context) { try { context.getLogger().log("Processed message " + msg.getBody()); // TODO: Do interesting work based on the new message } catch (Exception e) { context.getLogger().log("An error occurred"); throw e; } } }
JavaScript
SDK for JavaScript (v3)
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

JavaScript を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 exports.handler = async (event, context) => { for (const message of event.Records) { await processMessageAsync(message); } console.info("done"); }; async function processMessageAsync(message) { try { console.log(`Processed message ${message.body}`); // TODO: Do interesting work based on the new message await Promise.resolve(1); //Placeholder for actual async work } catch (err) { console.error("An error occurred"); throw err; } }

TypeScript を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 import { SQSEvent, Context, SQSHandler, SQSRecord } from "aws-lambda"; export const functionHandler: SQSHandler = async ( event: SQSEvent, context: Context ): Promise<void> => { for (const message of event.Records) { await processMessageAsync(message); } console.info("done"); }; async function processMessageAsync(message: SQSRecord): Promise<any> { try { console.log(`Processed message ${message.body}`); // TODO: Do interesting work based on the new message await Promise.resolve(1); //Placeholder for actual async work } catch (err) { console.error("An error occurred"); throw err; } }
PHP
SDK for PHP
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

PHP を使用した Lambda での SQS イベントの消費。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 <?php # using bref/bref and bref/logger for simplicity use Bref\Context\Context; use Bref\Event\InvalidLambdaEvent; use Bref\Event\Sqs\SqsEvent; use Bref\Event\Sqs\SqsHandler; use Bref\Logger\StderrLogger; require __DIR__ . '/vendor/autoload.php'; class Handler extends SqsHandler { private StderrLogger $logger; public function __construct(StderrLogger $logger) { $this->logger = $logger; } /** * @throws InvalidLambdaEvent */ public function handleSqs(SqsEvent $event, Context $context): void { foreach ($event->getRecords() as $record) { $body = $record->getBody(); // TODO: Do interesting work based on the new message } } } $logger = new StderrLogger(); return new Handler($logger);
Python
SDK for Python (Boto3)
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

Python を使用した Lambda での SQS イベントの消費。

# Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. # SPDX-License-Identifier: Apache-2.0 def lambda_handler(event, context): for message in event['Records']: process_message(message) print("done") def process_message(message): try: print(f"Processed message {message['body']}") # TODO: Do interesting work based on the new message except Exception as err: print("An error occurred") raise err
Ruby
SDK for Ruby
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

Ruby を使用した Lambda での SQS イベントの消費。

# Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. # SPDX-License-Identifier: Apache-2.0 def lambda_handler(event:, context:) event['Records'].each do |message| process_message(message) end puts "done" end def process_message(message) begin puts "Processed message #{message['body']}" # TODO: Do interesting work based on the new message rescue StandardError => err puts "An error occurred" raise err end end
Rust
SDK for Rust
注記

GitHub には、その他のリソースもあります。サーバーレスサンプルリポジトリで完全な例を検索し、設定および実行の方法を確認してください。

Rust を使用して Lambda で SQS イベントを消費します。

// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 use aws_lambda_events::event::sqs::SqsEvent; use lambda_runtime::{run, service_fn, Error, LambdaEvent}; async fn function_handler(event: LambdaEvent<SqsEvent>) -> Result<(), Error> { event.payload.records.iter().for_each(|record| { // process the record tracing::info!("Message body: {}", record.body.as_deref().unwrap_or_default()) }); Ok(()) } #[tokio::main] async fn main() -> Result<(), Error> { tracing_subscriber::fmt() .with_max_level(tracing::Level::INFO) // disable printing the name of the module in every log line. .with_target(false) // disabling time is handy because CloudWatch will add the ingestion time. .without_time() .init(); run(service_fn(function_handler)).await }
Node.js Lambda 関数を作成する方法
  1. プロジェクト用のディレクトリを作成し、そのディレクトリに切り替えます。

    mkdir sqs-tutorial cd sqs-tutorial
  2. サンプル JavaScript コードを index.js という名前の新しいファイルにコピーします。

  3. 以下の zip コマンドを使用して、デプロイパッケージを作成します。

    zip function.zip index.js
  4. create-function AWS CLI コマンドを使用して、Lambda 関数を作成します。roleパラメータには、前に作成した実行ロールの ARN を入力します。

    注記

    Lambda 関数と Amazon SQS キューは同じ AWS リージョンに存在する必要があります。

    aws lambda create-function --function-name ProcessSQSRecord \ --zip-file fileb://function.zip --handler index.handler --runtime nodejs18.x \ --role arn:aws:iam::111122223333:role/lambda-sqs-role

関数をテストする

ステップ 3: Lambda 関数をテストする

invoke AWS CLI コマンドおよびサンプルの Amazon SQS イベントを使用して、手動で Lambda 関数を呼び出します。

サンプルイベントで Lambda 関数を呼び出す方法
  1. 次の JSON をファイル名 input.json で保存します。この JSON は、Amazon SQS が Lambda 関数に送信する可能性のあるイベントをシミュレートするもので、"body" にはキューからの実際のメッセージが含まれます。この例では、メッセージは "test" です。

    例 Amazon SQS イベント

    これはテストイベントです。メッセージやアカウント番号を変更する必要はありません。

    { "Records": [ { "messageId": "059f36b4-87a3-44ab-83d2-661975830a7d", "receiptHandle": "AQEBwJnKyrHigUMZj6rYigCgxlaS3SLy0a...", "body": "test", "attributes": { "ApproximateReceiveCount": "1", "SentTimestamp": "1545082649183", "SenderId": "AIDAIENQZJOLO23YVJ4VO", "ApproximateFirstReceiveTimestamp": "1545082649185" }, "messageAttributes": {}, "md5OfBody": "098f6bcd4621d373cade4e832627b4f6", "eventSource": "aws:sqs", "eventSourceARN": "arn:aws:sqs:us-east-1:111122223333:my-queue", "awsRegion": "us-east-1" } ] }
  2. 次の invoke AWS CLI コマンドを実行します。このコマンドは、レスポンスで CloudWatch ログを返します。ログの取得の詳細については、「AWS CLI を使用したログへのアクセス」を参照してください。

    aws lambda invoke --function-name ProcessSQSRecord --payload file://input.json out --log-type Tail \ --query 'LogResult' --output text --cli-binary-format raw-in-base64-out | base64 --decode

    AWS CLI バージョン 2 を使用している場合、cli-binary-format オプションは必須です。これをデフォルト設定にするには、aws configure set cli-binary-format raw-in-base64-out を実行します。詳細については、バージョン 2 の AWS Command Line Interface ユーザーガイドの「AWS CLI でサポートされているグローバルコマンドラインオプション」を参照してください。

  3. レスポンス内にある INFO ログを探します。このログは Lambda 関数がメッセージ本文を記録する場所です。次のようなログが表示されます。

    2023-09-11T22:45:04.271Z 348529ce-2211-4222-9099-59d07d837b60 INFO Processed message test 2023-09-11T22:45:04.288Z 348529ce-2211-4222-9099-59d07d837b60 INFO done

Amazon SQS キュー を作成する

ステップ 4: Amazon SQS キューを作成する

Lambda 関数がイベントソースとして使用できる Amazon SQS キューを作成します。Lambda 関数と Amazon SQS キューは同じ AWS リージョンに存在する必要があります。

キューを作成するには
  1. Amazon SQS コンソール を開きます。

  2. [キューの作成] を選択します。

  3. キューの名前を入力します。その他のオプションはすべて、デフォルト設定のままにしておきます。

  4. [キューの作成]を選択します。

キューを作成したら、その ARN を書き留めます。こちらは、次のセクションでキューを Lambda 関数と関連付ける際に必要になります。

イベントソースを設定する

ステップ 5: イベントソースマッピングを設定する

イベントソースマッピングを作成して、Amazon SQS キューを Lambda 関数に接続します。イベントソースマッピングは Amazon SQS キューを読み取り、新しいメッセージが追加されたときに Lambda 関数を呼び出します。

Amazon SQS キューと Lambda 関数の間でマッピングを作成するには、create-event-source-mapping AWS CLI コマンドを使用します。例:

aws lambda create-event-source-mapping --function-name ProcessSQSRecord --batch-size 10 \ --event-source-arn arn:aws:sqs:us-east-1:111122223333:my-queue

イベントソースマッピングのリストを取得するには、list-event-source-mappings コマンドを使用します。例:

aws lambda list-event-source-mappings --function-name ProcessSQSRecord

テストメッセージを送信する

ステップ 6: テストメッセージを送信する
Amazon SQS メッセージを Lambda 関数に送信する方法
  1. Amazon SQS コンソール を開きます。

  2. 先ほど作成したキューを選択します。

  3. [メッセージの送信と受信] を選択します。

  4. メッセージ本文に、「これはテストメッセージです」などとテストメッセージを入力します。

  5. [メッセージの送信] を選択します。

Lambdaがキューにアップデートをポーリングします。新しいメッセージがあると、Lambda はキューからのこの新しいイベントデータを使用して関数を呼び出します。   関数ハンドラーが例外をスローせずに正常に戻った場合、Lambda はメッセージが正しく処理されたと見なし、キュー内の新しいメッセージの読み取りを開始します。メッセージが正常に処理された後、Lambdaはメッセージをキューから自動的に削除します。ハンドラーが例外をスローした場合、Lambda はメッセージの バッチが正常に処理されなかったと見なし、Lambdaは同じメッセージのバッチで関数を呼び出します。

CloudWatch のログを確認する

ステップ 6: テストメッセージを送信する
関数がメッセージを処理したことを確認する方法
  1. Lambda コンソールの [関数ページ] を開きます。

  2. ProcessSQSRecord 関数を選択します。

  3. [モニター] を選択します。

  4. [CloudWatch Logs を表示] を選択します。

  5. CloudWatch コンソールで、関数のログストリームを選択します。

  6. INFO ログを探します。このログは Lambda 関数がメッセージ本文を記録する場所です。Amazon SQS キューから送信したメッセージが表示されるはずです。例:

    2023-09-11T22:49:12.730Z b0c41e9c-0556-5a8b-af83-43e59efeec71 INFO Processed message this is a test message.

リソースのクリーンアップ

このチュートリアル用に作成したリソースは、保持しない場合は削除できます。使用しなくなった AWS リソースを削除することで、AWS アカウント アカウントに請求される料金の発生を防ぎます。

実行ロールを削除する
  1. IAM コンソールのロールページを開きます。

  2. 作成した実行ロールを選択します。

  3. [削除] を選択します。

  4. テキスト入力フィールドにロールの名前を入力し、[削除] を選択します。

Lambda 関数を削除するには
  1. Lambda コンソールの関数ページを開きます。

  2. 作成した関数を選択します。

  3. [アクション] で、[削除] を選択します。

  4. テキスト入力フィールドに delete と入力し、[Delete] (削除) を選択します。

Amazon SQS キューを削除するには
  1. AWS Management Console にサインインし、Amazon SQS コンソール (https://console.aws.amazon.com/sqs/) を開きます。

  2. 作成したキューを選択します。

  3. [削除] を選択します。

  4. テキスト入力フィールドに confirm を入力します。

  5. [削除] を選択します。