概要
New Relicには、New Relic Flexと呼ばれる任意のメトリックデータを定期的に送信できる機能があります。この機能により、APMやInfrastructure等では送信できないメトリックデータをNew Relicに送信することができ、送信した任意のメトリックデータはダッシュボードによる監視やAlerts等と組み合わせる事ができます。
しかし、New Relic Flexを利用するためにはInfrastructure agentが動作するサーバーが必要であり、ECS Fargateのようなフルマネージドサービスでは使う事ができません。
この記事では、こうしたNew Relic Flexが使えない環境でも任意のメトリックデータを送信するための代替手段として、AWS Lambda (サーバーレス) とNew Relic REST APIを使った方法を紹介します。
関連記事の紹介
私が所属するチームでは、以前にMackerelからNew Relicに移行する際にNew Relic Flexを使った内容について別の記事にまとめています。当時はワークロードにEC2サーバーを採用していたため、New Relic Flexを利用できる状況でした。
MackerelのカスタムメトリックをNew Relicに移行する時はNew Relic Flexという機能がおすすめ - 弥生開発者ブログ
この記事は、上述した内容の続編にあたります。それぞれ独立して読める内容となっていますが、気になる方は両方の記事を読んでいただけれると嬉しいです
提案する方法について
New Relic Flexに代わり、Metric APIを利用します。また、Metric APIへのリクエストや送信メトリックデータの作成処理はAWSが提供するサーバーレスサービスのAWS Lambdaを利用します。
また、New Relicが提供するTelemetry SDKでは一部プログラミング言語でMetric APIのサポートがあり、APIリクエストを容易にできるようにサポートされています。この記事ではGo言語でTelemetry APIを利用して紹介します。
newrelic/newrelic-telemetry-sdk-go: Go library for sending telemetry data to New Relic
コード例
Telemetry SDKを使ってNew Relic Metric APIに対してメトリックデータを送信する関数の例です。このコード単体では動作しない点について注意してください。
import (
"context"
"os"
"time"
"github.com/newrelic/newrelic-telemetry-sdk-go/telemetry"
)
func RecordMetric(name string, value float64) {
h, _ := telemetry.NewHarvester(telemetry.ConfigAPIKey(os.Getenv("NEW_RELIC_INSERT_API_KEY")))
h.RecordMetric(telemetry.Count{
Name: name,
Value: value,
Timestamp: time.Now(),
})
h.HarvestNow(context.Background())
}
telemetry.Count
の他にも Gauge
と Summary
があります。送信したいメトリックデータの特性からどの型で送信するべきか判断してください。それぞれNew Relic側で対応する関数の違い等があります。
Query the Metric data type | New Relic Documentation
利用例
AWS EventBridgeでAWS Lambdaを定期的に実行します。
AWS Lambdaは、まずAppサーバーのAPIエンドポイントにリクエストを送信し、New Relicにメトリックデータとして送信したいデータをレスポンスとして受け取ります。
その後、New Relic Metric APIで送信できるようにデータを整形し、New Relic Metric APIにリクエストを送信します。New Relic Metric APIは受け取ったデータをNRQLからクエリできる形式でデータを保存します。
App ServerではNew Relicに送信したいデータをAPIエンドポイントとして公開して、AWS Lambda関数がデータを取得できるようにしています。これは /hearthエンドポントパターン と呼ばれています。
補足: /healthエンドポイントパターンについて
/hearthエンドポイントパターンについては、株式会社オライリー・ジャパンが出版する「入門 監視」という書籍で「7.3 healthエンドポイントパターン」という節の中で紹介されています。
App Serverは/healthエンドポイントパターンに従い、New Relicにメトリックデータとして送信したいデータをエンドポイントとして公開しています。
私が所属するチームでは、delayed jobやsidekiqといったバックグラウンドジョブのキュー毎のジョブ数を取得できるようにしています。AWS Lambda関数から取得できるようにエンドポイントを公開する事で、New Relicにジョブ数の監視ができるようになります。
まとめ
AWS LambdaでNew Relicに任意のメトリックデータを送信する方法と、私のチームでの利用例を紹介しました。
この方法の強みはサーバーレスな環境でメトリックデータをNew Relicで送信できる事であり、New Relic Flexが使う事が難しい環境で代替手段として採用できます。
技術的には新しいものは何も無かった内容でしたが、サーバーレスで任意のメトリックデータを送信したいんだよな〜と考えていた方の1つのアイデアとして知っていただけたら嬉しく思います。
おまけ
書いた後に知ったのですが、New Relic Flexをサーバーレスな環境で動かす事もできるんですね…
皆様の事情や状況に合わせて適切な方法を採用していただけたらと思います。