この記事は、Azure アドベントカレンダー 2019 の8日目の投稿です。
Azure には、アプリケーションの監視用に Application Insights(以下 AI ) があります。
AI は、ログの分析を行う Log Analytics と組み合わせることによって柔軟にログを扱うことが出来ます。
今回は、AI で収集したログを Log Analytics で集約し、Azure Monitor を使って Azure Functions にエラーメッセージを送る方法についてまとめます。
※今回は、AI とアプリケーションの繋ぎ込みなどは、扱わないのでそういった情報は、以下のようなところから調べてみましょう。
docs.microsoft.com
docs.microsoft.com
Log Analytics でログを分析する
Log Analytics でログ分析を行う場合は、基本的に SQL ライクな KQL という言語を使用してクエリを書きます。
Log Analytics のクエリエディタは、Azure ポータルの AI の画面から飛ぶことが出来ます。
AI の画面上部にある Log(Analytics) を選択します。
クエリエディタは、以下のような画面になります。
赤枠の中にクエリを書いていきます。
クエリを書いたら Run ボタンを押します。
ログは、以下の項目が検索できます。
- traces
- customEvents
- pageViews
- requests
- dependencies
- exceptions
- availabilityResults
- customMetrics
- performanceCounters
- browserTimings
自分が良く使う項目は、requests、dependencies、exceptions です。
requests は、アプリケーションに送られてくるリクエスト内容
dependencies は、DB、Web API などアプリケーション外にある依存関係
exceptions は、アプリケーション内で発生した例外が含まれます。
一番簡単なクエリは、以下です。
requests
これを実行すると、ログが表組されて表示されます。
条件分は、SQL のように書きます。
requests
| where resultCode == 404 or resultCode == 500
カラムの絞り込みは、以下のような感じ
requests
| where resultCode == 404 or resultCode == 500
| project resultCode , url , name
サマリーしたいときは、以下のような感じ
requests
| where resultCode == 404 or resultCode == 500
| project resultCode , url , name
| summarize count(resultCode) by resultCode, url, name
Log Analytics と Azure Monitor を組み合わせる
先ほど書いたクエリ結果をAzure Monitor と組み合わせてみます。
これは、Azure Monitor の画面から行います。
Azure Monitor のモニタルールは、ポータルの Azure Monitor > Alerts > New alert rule から進みます。
進むと以下のような画面になります。
Resource で監視対象の AI を指定します。
赤枠の中に Application Insights と入れると絞り込みがされます。
Condition は、リソースの状態を指定する項目です。
ここで Log Analytics のクエリを指定します。
Custom log search を指定します。
赤枠のSearch query にクエリを貼り付けます。
今回は、エラーが発生したら通知を行いたいので、閾値(Threshold value)は、0にします。(0を指定すると0回以上になるので、イベントが発生したら全て拾うことになります。)
時間の範囲は、デフォルト(5分)に設定します。
Actions は、アラートの発行先を指定する項目です。
今回は、Function App を指定します。
Create action group を選択します。
選択後、Action Type に Azure Functions を指定します。
次に出てくるウィンドウで、リソースグループを選択するとHttp Trigger が含まれている Function App が表示されるのでアラートを送りたい Function App を指定します。
最後に Alert Details で、Alert rule name を指定します。
これで、アラートが発生すると Function App のエンドポイントが呼び出されます。
Azure Functions でメッセージを受け取る
Function App が受け取るペイロードは、以下のような形式です。
{
"schemaId": "Microsoft.Insights/LogAlert",
"data": {
"SubscriptionId": "Your own subscription id",
"AlertRuleName": "Qiita-Monitoring-2019",
"SearchQuery": "requests\n| where resultCode == 404 or resultCode == 500\n| project resultCode , url , name \n| summarize count(resultCode) by resultCode, url, name",
"SearchIntervalStartTimeUtc": "2019-12-06T15:03:56",
"SearchIntervalEndtimeUtc": "2019-12-06T15:08:56",
"AlertThresholdOperator": "Greater Than",
"AlertThresholdValue": 0,
"ResultCount": 2,
"SearchIntervalInSeconds": 300,
"LinkToSearchResults": "https://portal.azure.com#@ef5d34b2-4e7d-468e-b184-b17e34c6be36/blade/Microsoft_OperationsManagementSuite_Workspace/AnalyticsBlade/initiator/AnalyticsShareLinkToQuery/isQueryEditorVisible/true/scope/%7B%22resources%22%3A%5B%7B%22resourceId%22%3A%22%2Fsubscriptions%2F30bc1c24-7c50-471e-97c4-b86a3d9cedb1%2FresourceGroups%2FQiita%2Fproviders%2Fmicrosoft.insights%2Fcomponents%2FQiita-Monitoring-2019%22%7D%5D%7D/query/requests%0A%7C%20where%20resultCode%20%3D%3D%20404%20or%20resultCode%20%3D%3D%20500%0A%7C%20project%20resultCode%20%2C%20url%20%2C%20name%20%0A%7C%20summarize%20count%28resultCode%29%20by%20resultCode%2C%20url%2C%20name/isQuerybase64Compressed/false/timespanInIsoFormat/2019-12-06T15%3a03%3a56.0000000Z%2f2019-12-06T15%3a08%3a56.0000000Z",
"Description": "",
"Severity": "3",
"SearchResult": {
"tables": [
{
"name": "PrimaryResult",
"columns": [
{
"name": "resultCode",
"type": "string"
},
{
"name": "url",
"type": "string"
},
{
"name": "name",
"type": "string"
},
{
"name": "count_resultCode",
"type": "long"
}
],
"rows": [
[
"500",
"https://localhost:44355/home/error500",
"GET /home/error500",
8
],
[
"404",
"https://localhost:44355/error",
"GET /error",
15
]
]
}
],
"dataSources": [
{
"resourceId": "/subscriptions/30bc1c24-7c50-471e-97c4-b86a3d9cedb1/resourcegroups/qiita/providers/microsoft.insights/components/qiita-monitoring-2019",
"tables": [
"requests"
]
}
]
},
"ApplicationId": "dcd854c3-e6a8-4f05-b58c-8272660d3427",
"AlertType": "Number of results"
}
}
columns が、テーブルのカラム名、rows が結果にリンクします
LinkToSearchResults の URL は、Log Analytics の クエリエディタに繋がります。
このペイロードを Slack に送るなどするとアプリのモニタリングがしやすいかと思います。
ペイロードを受け取る場合のC#の例を示します。
#r "Newtonsoft.Json"
using System.Net;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Primitives;
using Newtonsoft.Json;
public static async Task<IActionResult> Run(HttpRequest req, ILogger log)
{
string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
log.LogInformation(requestBody);
return (ActionResult)new OkObjectResult(requestBody);
}
Request Body に json が入ってくるので、それを加工して次の処理の送るといった感じで使用します。
Logic App に送るといったことも可能ですが、例えば Slack 通知などは、デフォルトの Slack コネクタだとリッチなメッセージが送れないので Function App が向いているかなという気がします。
まとめ
これらの学習には、Microsoft Learn がおすすめです。
docs.microsoft.com
アプリケーションの監視は、サービス運用の要なので、この機会に是非試してみましょう。