新版告警支持两个版本的内容模板语法。本文介绍新版内容模板语法。
概述
相对于旧版的内容模板语法,新版通过类似Python语法的方式,提供更加灵活且高级的自定义渲染逻辑,在定制通知内容(例如Markdown转义)、自定义内容样式等方面都做了优化,满足更多样化的定制内容需求。例如:
根据告警的严重度进行动态的内容渲染,不同严重度使用不同颜色的文字进行区分。
对告警的查询结果进行迭代渲染,在邮件中渲染为列表或者表格。
通过函数对某个字段进行BASE64编码和解码、对数值进行数学运算等。
新版的内容模板语法完全兼容旧版,并支持新旧版混合使用。但在不同版本的内容模板语法中使用告警属性时,其类型、取值和展示形式等存在差异,因此建议您不要混合使用新旧版本的内容模板语法。推荐您使用新版本的内容模板语法。
快速开始
通过新版内容模板定义通知内容的示例如下:
告警内容
{ "alert_id": "test-alert", "alert_name": "PV/UV Alert", "project": "project-1", "status": "firing", "severity": 6, "labels": { "app": "nginx", "host": "host-1" }, "results": [ { "project": "project-1", "logstore": "logstore-1", "query": "* | select count(*) as pv" }, { "project": "project-2", "logstore": "logstore-2", "query": "* | select count(distinct user_id) as uv" } ] }
内容模板配置
- Alert ID: {{ alert.alert_id }} - Alert Name: {{ alert.alert_name }} - Project: {{ alert.project }} - Status: {% if alert.status == "firing" %}FIRING{% else %}RESOLVED{% endif %} - Labels: {%- for key, val in alert.labels.items() %} - {{ key }}: {{ val }} {%- endfor %} - Query: {{ alert.results[0].query }}
输出结果
- Alert ID: test-alert - Alert Name: PV/UV Alert - Project: project-1 - Status: FIRING - Labels: - app: nginx - host: host-1 - Query: * | select count(*) as pv
基本语法
数据类型
内容模板语法类似于Python语法,支持如下数据类型。
数据类型 | 说明 |
数字 | 包含整数和浮点数。例如3、-1。 |
字符串 | 需要使用单引号('')或者双引号("")包裹。例如"foo"、'bar'。 当字符串中存在特殊字符时,需使用反斜线(\)进行转义。例如 |
布尔值 | True、False。 |
空值 | None。 |
列表 | 不同编程语言中的叫法不同,可以为列表、数组、Slice等。例如['foo', 'bar']。 |
字典 | 不同编程语言中的叫法不同,可以为字典、对象等。例如{'foo': 'bar'}。 |
分隔符
分隔符 | 使用场景 | 示例 |
| 在变量或表达式中使用。 |
|
| 用于控制语句。 |
|
| 用于注释,不会出现在通知内容中。 |
|
清除空字符
默认情况下,在分隔符内部,分隔符与表达式之间的空格会被忽略。例如{{ 23 }} < {{ 45 }}
等同于{{23}} < {{45}}
,渲染结果都为23 < 45
。但是分隔符外部的空字符(空格、Tab、换行等)会被保留,例如{{ 23 }} < {{ 45 }}
的渲染结果为23 < 45
,而不是23<45
。
当您需要删除多余的空字符时,可以使用清除空字符操作。在分隔符开始或结束的地方添加一个短划线(-),用于清除该分隔符前面和后面所有紧连着的空字符。例如{{ 23 -}} < {{- 45 }}
的渲染结果为23<45
。
{{-
、{{%-
、{#-
用于删除分隔符左侧紧连着的所有空字符。-}}
、-%}
、-%}
用于删除分隔符右侧紧连着的所有空字符。
短划线(-)和分隔符之间不能有空格。例如
{{- 3 }}
是有效的,渲染结果为3
;{{ - 3 }}
是无效的,渲染结果为-3
。清除空字符操作只对分隔符外部的空格有效,不影响分隔符内部的空格。例如
{{ "hello " }} {{- "world"}}
渲染结果为hello world
。
条件语句
条件判断支持对参数或者逻辑比较表达式进行判断。通过条件判断,可以进行动态渲染。
如果
if
后面传入的是常量或者普通变量,则对该值进行真值判断。其中布尔值false
、数字0
、空字符串""
、空值null
、空数组[]
、空对象{}
都会被判定为假,其它值被判定为真。如果
if
后面传入的是逻辑比较表达式,则按照比较结果进行判断。例如{{ if alert.severity >= 8 }}
用于判断告警严重度是否大于等于8。
条件判断支持如下几种形式:
使用方式 | 示例 |
if |
|
if-else |
|
if-elif |
|
if-elif-else |
|
嵌套使用 |
|
迭代
循环语句用于对数组和对象进行迭代操作。支持如下几种使用方式:
使用方式 | 示例 |
数组迭代 |
|
数组迭代,包含下标 | 使用enumerate函数对数组进行下标迭代。关于enumerate函数的更多信息,请参见enumerate函数。
下标默认从0开始。您也可以通过enumerate函数中的start参数自定义起始下标。例如:
|
对象迭代 | 通过items()方法将对象转为
|
嵌套使用 |
|
转义
如果您希望特殊字符串(例如{{
)不被内容模板解析和渲染,可对特殊字符串进行转义。例如:根据如下配置表示保留{% raw %}
和{% endraw %}
之间所有的内容。
内容模板配置
{% raw %} {% for result in alert.results %} {{ result }} {% endfor %} {% endraw %}
结果
{% for result in alert.results %} {{ result }} {% endfor %}
函数
内置模板函数便于您对数据进行各种操作,丰富了通知内容的格式和展示样式。更多信息,请参见内置模板函数。
例如您要通过Webhook方式发送JSON格式的内容,相关信息如下:
告警的查询语句(包含一个换行)
* | select count(*) as cnt
不同使用方式的对比说明
对比项
内容模板
结果
说明
不使用函数
{ "query": "{{ alert.results[0].query }}" }
{ "query": "* | select count(*) as pv" }
JSON格式不合法
使用quote函数
{ "query": {{ quote(alert.results[0].query) }} }
{ "query": "* | \nselect count(*) as pv" }
JSON格式合法
过滤器
在函数嵌套使用场景中,通知内容的编辑麻烦且不够直观,例如{{ block(to_list(alert.labels)) }}
,此时您可以使用过滤器功能。过滤器使用竖线(|) 操作符,并支持链式调用,一般格式为{{ xxx | filiter1 | filter2 | ... }}
。例如{{ blockquote(to_list(alert.labels)) }}
等同于{{ alert.labels | to_list | blockquote }}
。
使用过滤器方式时,请先确认目标内置函数是否支持过滤器方式。大部分内置函数都支持过滤器方式的调用。更多信息,请参见内置模板函数。
如果函数中没有参数,则只能使用函数方式,不支持过滤器方式。
当函数中只有一个参数时,推荐使用过滤器方式,即使用
{{ arg | fn }}
。例如{{ abs(-1) }}
等同于{{ -1 | abs }}
。如果函数中有多个参数,且从第二个参数开始有默认值,也可以使用过滤器。如果有多个参数值需要传递,通过过滤器方式并不直观。不建议对多参数的函数使用过滤器方式。
操作符
内容模板表达式中支持如下操作符。操作符的优先级说明请参见Operator precedence。
类别 | 操作符 | 说明 |
算数 | + | 加法 |
- | 减法 | |
* | 乘法 | |
/ | 除法,返回值是一个浮点数。 | |
// | 除法,返回整数。 | |
% | 取模 | |
比较 | == | 等于 |
!= | 不等于 | |
> | 大于 | |
>= | 大于等于 | |
< | 小于 | |
<= | 小于等于 | |
逻辑 | and | 且操作 |
or | 或操作 | |
not | 取反 | |
其它 | in | 判断是否包含,返回布尔类型的结果。
|
() | 操作组合,例如:{{ a > b and (a > c or b > c) }} |
使用告警变量
在新版内容模板中,告警变量的使用形式为alert.xxx
,例如alert.project
。更多信息,请参见内容模板变量说明(新版)。
配置示例
示例1:根据告警状态展示不同内容
触发告警后,展示告警状态、告警严重度和触发结果等信息;告警恢复时,只展示告警状态。
不使用函数
{% if alert.status == "firing" %} - 状态: <font color="#E03C39">触发</font> - 严重度:{{ alert.severity | format_severity }} - Results: {{ alert.results | to_json }} {% else %} - 状态: <font color="#72C140">恢复</font> {% endif %}
使用函数
使用format_status函数和format_severity函数简化配置。
- 状态: {{ alert.status | format_status }} {% if alert.status == "firing" %} - 严重度:{{ alert.severity | format_severity }} - Results: {{ alert.results | to_json }} {% endif %}
结构化数据展示
将告警标签的内容转换为列表形式,内容为Markdown格式。
不使用函数
- 项目: {{ alert.project }} - 告警名称: {{ alert.alert_name }} - 告警标签: {%- for key, val in alert.labels.items() %} > - {{ key }}: {{ val }} {%- endfor %}
使用函数
使用to_list函数和blockquote函数简化配置。
- 项目: {{ alert.project }} - 告警名称: {{ alert.alert_name }} - 告警标签: {{ alert.labels | to_list | blockquote }}