21
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

ディップAdvent Calendar 2023

Day 8

New RelicでQOL爆上げした陰でLambdaがタイムアウトしていた話

Last updated at Posted at 2023-12-07

はじめに

この記事はディップ Advent Calendar 2023の8日目の投稿です。

皆さんはNew Relicを使っていますか?
ディップでは各プロダクトへのNew Relic導入を進めています。
New Relicは開発から運用、またセキュリティといったアプリケーションに関わる各種メトリクスやパフォーマンスを確認することができる非常に便利なプラットフォームです。
特にダッシュボードは以下のように高い自由度で作り込めるので 気がついたら半日過ぎているなんてこともザラ QOLが爆上がりします。

このようにとても便利なNew Relicですが、AWS Lambdaに統合した際にとある不具合に遭遇したため、その原因と対応方法を紹介したいと思います。

何が起きたのか

まず、不具合が発生した機能は以下のような構成でした。

elastisearch更新バッチアーキテクチャ.drawio.png
SQSをトリガーにLambdaを起動するオーソドックスな構成で、
ざっくりとした仕様は以下のようになっています。

  • SQS
    • 処理対象のIDをJSONのリストで受け取る
    • IDは最大1万件まで指定可能
  • Lambda
    • アプリケーションはGoで実装
    • SQSから受け取ったIDでPostgreSQLを検索し、取得したデータをElasticsearchへ登録する
    • タイムアウトは最大値の15分に設定
    • NewRelicへの情報送信は公式の拡張機能をLambdaLayerに設定することで実現

Lambdaがタイムアウトするようになった

LambdaにNew Relicを統合してしばらく経ったあと、SQSのキューにメッセージが溜まってしまっていることに気が付きます。
調査をしたところ、IDを1万件受け取った場合にLambdaがタイムアウトしていることが分かりました。

しばらく気づけなかった

タイムアウトのログはアプリケーションの範囲外で出力されているためNew Relicへは送信されておらず1、またアプリ自体は正常に終了していたため、発生にしばらく気がつけませんでした。

状況を整理すると

  • IDを1万件受け取るとLambdaがタイムアウトする
  • アプリ側で出力している終了ログは出ている
  • Lambda側(アプリの範囲外)でタイムアウトログが出力される
  • アプリ自体は正常に終了している
    • SQSのキューは減っていく
    • アプリでエラーが発生しないので通知が来ない
    • DLQも監視していたが、キュー自体は消費されるのでDLQが溜まらないため通知が来ない
  • タイムアウトするまでキューが消費されないので効率が著しく悪化している
    • アプリ自体は数分で終了するものの、15分経過するまで次のメッセージを処理できない状態

サポートケースの利用

New Relicは各種公式ドキュメントやサポートフォーラムなどトラブルシューティングに役立つリソースが充実しています。
契約にテクニカルサポートが含まれる場合はサポートケースを起票することでNew Relicのサポートエンジニアの方と直接やりとり2をすることができます。

今回の不具合については5000件や7000件では再現しなかったため、どこかに閾値があってうっすらとデータ量が関連してそうな感じがしているところまでは分かりました。
しかし原因究明には至らなかったため、NewRelicのテクニカルサポートを受けることにしました。

タイムアウトの原因

New Relicの方で調査いただいた結果、
New Relicへ送信するトランザクション情報に巨大なクエリを書き込み過ぎていたことが原因であることがわかりました。

アプリ内では複数テーブルに対してSQSから受けたIDをIN句に指定したSQLを発行しており、このクエリ文字列をNew Relicへ送信していたところ、New RelicのAgentが送信できるデータ量を超えてしまいLambda拡張機能がハングアップした、とのことでした。

対応

まず、アプリ側で以下対応を実施しました

  • トランザクション情報にクエリを書き込むのをやめた3
  • Lambdaが一度に受け取れるIDの件数を5000件に変更4
  • Lambda拡張機能を最新化

また、New Relic側でLambda拡張機能がハングアップする事象について修正対応していただきました。

NewRelicLambdaExtension(※1)のversion36以降で対応が反映されています

また、ハングアップする問題は修正いただきましたが送信できる容量は1MBまで(それを超えるとNew Relicに情報は送られず破棄される)という制限(※2)がついたためご注意ください

※1 東京リージョン(ap-northeast-1)のリソースです。
※2 version36時点の仕様です。最新仕様は公式を確認ください。
最新のバージョンは以下を参照してください。
https://layers.newrelic-external.com/

さいごに

およそ3ヶ月にわたり丁寧にサポートしていただいたNew Relicテクニカルサポートチームの皆さま、本当にありがとうございました!
これからもNew Relicをガンガン使い倒してもっともっとQOLを上げていきたいと思います。

この記事がどこかで同じ事象に悩まれている方のお役に立てれば幸いです。

  1. CloudWatch logをサブスクリプションするLambdaを構築すればアプリ外で出力されたログもNew Relicへ送信可能

  2. しかも日本語でOK

  3. 発行しているクエリはどれもシンプルなもので、かつ、リクエストで受けたIDはログに出しているため書き込みはそもそも不要という判断

  4. 今後の修正によって閾値を超えることがないように。念の為。

21
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
21
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?