优化日志搜索警报查询
本文介绍如何编写和转换日志搜索警报来获得最佳性能。 经过优化的查询可降低延迟并加载频繁运行的警报。
开始编写警报日志查询
警报查询开始于查询 Log Analytics 中指示问题的日志数据。 若要了解可以发现的内容,请参阅在 Azure Monitor Log Analytics 中使用查询。 还可以开始编写你自己的查询。
指示问题而非警报的查询
生成警报流是为了将指示问题的结果转换为警报。 例如,在如下查询中:
SecurityEvent
| where EventID == 4624
如果用户的意图是发出警报,那么当这个事件类型发生时,警报逻辑会将 count
追加到查询中。 运行的查询将如下所示:
SecurityEvent
| where EventID == 4624
| count
无需向查询添加警报逻辑,这样做甚至可能导致问题。 在以上示例中,如果在查询中包含 count
,将始终得到值 1,因为警报服务将执行 count
的 count
。
避免限制并采用运算符
在查询中使用 limit
和 take
可能会增加警报的延迟和负载,因为结果会随着时间的推移而产生不一致。 仅在需要时使用它们。
日志查询约束
Azure Monitor 中的日志查询以 table、search
或 union
运算符开头。
对日志搜索预警规则的查询应始终以表开始以定义明确的范围,从而提高查询性能和结果的相关性。 警报规则中的查询经常运行。 使用 search
和 union
会造成额外开销,并增加警报的延迟,因为它需要扫描多个表。 这些运算符还会降低警报服务优化查询的性能。
除了跨资源查询,我们不支持创建或修改使用 search
或 union
运算符的日志搜索预警规则。
例如,以下警报查询的范围限定为 SecurityEvent 表,并搜索特定的事件 ID。 这是查询必须处理的唯一的表。
SecurityEvent
| where EventID == 4624
使用跨资源查询的日志搜索预警规则不受此更改的影响,因为跨资源查询使用 union
类型,它将查询范围限制为特定资源。 以下示例将是一个有效的日志搜索警报查询:
union
app('00000000-0000-0000-0000-000000000001').requests,
app('00000000-0000-0000-0000-000000000002').requests,
workspace('00000000-0000-0000-0000-000000000003').Perf
注意
新的 scheduledQueryRules API 支持跨资源查询。
示例
以下示例包括使用 search
和 union
的日志查询。 它们提供了步骤,可用于修改这些查询以在警报规则中使用。
示例 1
你希望通过使用以下查询来创建一个日志搜索预警规则,该查询使用 search
检索性能信息:
search *
| where Type == 'Perf' and CounterName == '% Free Space'
| where CounterValue < 30
若要修改此查询,请首先使用以下查询来标识属性所属的表:
search * | where CounterName == '% Free Space' | summarize by $table
此查询结果将显示 CounterName 属性来自 Perf 表 。
使用此结果创建以下查询,可将该查询用于预警规则:
Perf | where CounterName == '% Free Space' | where CounterValue < 30
示例 2
你希望通过使用以下查询来创建一个日志搜索预警规则,该查询使用 search
检索性能信息:
search ObjectName =="Memory" and CounterName=="% Committed Bytes In Use"
| summarize Avg_Memory_Usage =avg(CounterValue) by Computer
| where Avg_Memory_Usage between(90 .. 95)
若要修改此查询,请首先使用以下查询来标识属性所属的表:
search ObjectName=="Memory" and CounterName=="% Committed Bytes In Use" | summarize by $table
此查询结果将显示 ObjectName 和 CounterName 属性来自 Perf 表。
使用此结果创建以下查询,可将该查询用于预警规则:
Perf | where ObjectName =="Memory" and CounterName=="% Committed Bytes In Use" | summarize Avg_Memory_Usage=avg(CounterValue) by Computer | where Avg_Memory_Usage between(90 .. 95)
示例 3
你希望通过使用以下查询来创建一个日志搜索预警规则,该查询同时使用 search
和 union
来检索性能信息:
search (ObjectName == "Processor" and CounterName == "% Idle Time" and InstanceName == "_Total")
| where Computer !in (
union *
| where CounterName == "% Processor Utility"
| summarize by Computer)
| summarize Avg_Idle_Time = avg(CounterValue) by Computer
若要修改此查询,请首先使用以下查询来标识查询第一部分中属性所属的表:
search (ObjectName == "Processor" and CounterName == "% Idle Time" and InstanceName == "_Total") | summarize by $table
此查询结果将显示所有这些属性来自 Perf 表。
将
union
与withsource
命令配合使用,确定哪个源表提供了每行:union withsource=table * | where CounterName == "% Processor Utility" | summarize by table
此查询结果将显示这些属性也来自 Perf 表。
使用这些结果创建以下查询,可将该查询用于预警规则:
Perf | where ObjectName == "Processor" and CounterName == "% Idle Time" and InstanceName == "_Total" | where Computer !in ( (Perf | where CounterName == "% Processor Utility" | summarize by Computer)) | summarize Avg_Idle_Time = avg(CounterValue) by Computer
示例 4
你希望通过使用以下查询来创建一个日志搜索预警规则,该查询联接两个 search
查询的结果:
search Type == 'SecurityEvent' and EventID == '4625'
| summarize by Computer, Hour = bin(TimeGenerated, 1h)
| join kind = leftouter (
search in (Heartbeat) OSType == 'Windows'
| summarize arg_max(TimeGenerated, Computer) by Computer , Hour = bin(TimeGenerated, 1h)
| project Hour , Computer
) on Hour
若要修改此查询,请首先使用以下查询来标识包含左侧联接中属性的表:
search Type == 'SecurityEvent' and EventID == '4625' | summarize by $table
结果指示左侧联接中的属性属于 SecurityEvent 表。
使用以下查询来标识包含右侧联接中属性的表:
search in (Heartbeat) OSType == 'Windows' | summarize by $table
结果指示右侧联接中的属性属于 Heartbeat 表。
使用这些结果创建以下查询,可将该查询用于预警规则:
SecurityEvent | where EventID == '4625' | summarize by Computer, Hour = bin(TimeGenerated, 1h) | join kind = leftouter ( Heartbeat | where OSType == 'Windows' | summarize arg_max(TimeGenerated, Computer) by Computer , Hour = bin(TimeGenerated, 1h) | project Hour , Computer ) on Hour