Merge pull request #7683 from EMQ-YangM/rule-engine-doc
feat(rule-engine): add i18n support
This commit is contained in:
commit
1dc9ddeac7
|
@ -72,9 +72,9 @@ A host entry has the following form: `Host[:Port]`.<br/>
|
|||
The MongoDB default port 27017 is used if `[:Port]` is not specified.
|
||||
"""
|
||||
zh: """
|
||||
集群要连接的节点列表。 节点之间用逗号分隔,如:`Node[,Node].<br/>`
|
||||
对于每个节点,应为:将要连接的 IPv4 或 IPv6 地址或主机名。<br/>
|
||||
主机条目具有以下形式:`Host[:Port]`。<br/>
|
||||
集群将要连接的节点列表。 节点之间用逗号分隔,如:`Node[,Node].<br/>`
|
||||
每个节点的配置为:将要连接的 IPv4 或 IPv6 地址或主机名。<br/>
|
||||
主机名具有以下形式:`Host[:Port]`。<br/>
|
||||
如果未指定 `[:Port]`,则使用 MongoDB 默认端口 27017。
|
||||
"""
|
||||
}
|
||||
|
|
|
@ -72,9 +72,10 @@ A host entry has the following form: `Host[:Port]`.<br/>
|
|||
The MongoDB default port 27017 is used if `[:Port]` is not specified.
|
||||
"""
|
||||
zh: """
|
||||
集群要连接的节点列表。 节点之间用逗号分隔,如:`Node[,Node].<br/>`
|
||||
对于每个节点,应为:将要连接的 IPv4 或 IPv6 地址或主机名。<br/>
|
||||
主机条目具有以下形式:`Host[:Port]`。<br/>
|
||||
|
||||
集群将要连接的节点列表。 节点之间用逗号分隔,如:`Node[,Node].<br/>`
|
||||
每个节点的配置为:将要连接的 IPv4 或 IPv6 地址或主机名。<br/>
|
||||
主机名具有以下形式:`Host[:Port]`。<br/>
|
||||
如果未指定 `[:Port]`,则使用 Redis 默认端口 6379。
|
||||
"""
|
||||
}
|
||||
|
|
|
@ -0,0 +1,685 @@
|
|||
emqx_rule_api_schema {
|
||||
|
||||
event_event_type {
|
||||
desc {
|
||||
en: "Event Type"
|
||||
zh: "事件类型"
|
||||
}
|
||||
label: {
|
||||
en: "Event Type"
|
||||
zh: "事件类型"
|
||||
}
|
||||
}
|
||||
|
||||
event_id {
|
||||
desc {
|
||||
en: "Message ID"
|
||||
zh: "消息 ID"
|
||||
}
|
||||
label: {
|
||||
en: "Message ID"
|
||||
zh: "消息 ID"
|
||||
}
|
||||
}
|
||||
|
||||
event_clientid {
|
||||
desc {
|
||||
en: "The Client ID"
|
||||
zh: "客户端 ID"
|
||||
}
|
||||
label: {
|
||||
en: "Client ID"
|
||||
zh: "客户端 ID"
|
||||
}
|
||||
}
|
||||
|
||||
event_username {
|
||||
desc {
|
||||
en: "The User Name"
|
||||
zh: ""
|
||||
}
|
||||
label: {
|
||||
en: "Username"
|
||||
zh: "用户名"
|
||||
}
|
||||
}
|
||||
|
||||
event_payload {
|
||||
desc {
|
||||
en: "The Message Payload"
|
||||
zh: "消息负载"
|
||||
}
|
||||
label: {
|
||||
en: "Message Payload"
|
||||
zh: "消息负载"
|
||||
}
|
||||
}
|
||||
|
||||
event_peerhost {
|
||||
desc {
|
||||
en: "The IP Address of the Peer Client"
|
||||
zh: "对等客户端的 IP 地址"
|
||||
}
|
||||
label: {
|
||||
en: "Peer IP Address"
|
||||
zh: "对等客户端的 IP"
|
||||
}
|
||||
}
|
||||
|
||||
event_topic {
|
||||
desc {
|
||||
en: "Message Topic"
|
||||
zh: "消息主题"
|
||||
}
|
||||
label: {
|
||||
en: "Message Topic"
|
||||
zh: "消息主题"
|
||||
}
|
||||
}
|
||||
|
||||
event_publish_received_at {
|
||||
desc {
|
||||
en: "The Time that this Message is Received"
|
||||
zh: "消息被接受的时间"
|
||||
}
|
||||
label: {
|
||||
en: "Message Received Time"
|
||||
zh: "消息被接受的时间"
|
||||
}
|
||||
}
|
||||
|
||||
event_qos {
|
||||
desc {
|
||||
en: "The Message QoS"
|
||||
zh: "消息的 QoS"
|
||||
}
|
||||
label: {
|
||||
en: "Message QoS"
|
||||
zh: "消息 QoS"
|
||||
}
|
||||
}
|
||||
|
||||
event_from_clientid {
|
||||
desc {
|
||||
en: "The Client ID"
|
||||
zh: "事件来源客户端的 ID"
|
||||
}
|
||||
label: {
|
||||
en: "Client ID"
|
||||
zh: "客户端 ID"
|
||||
}
|
||||
}
|
||||
|
||||
event_from_username {
|
||||
desc {
|
||||
en: "The User Name"
|
||||
zh: "事件来源客户端的用户名"
|
||||
}
|
||||
label: {
|
||||
en: "Username"
|
||||
zh: "用户名"
|
||||
}
|
||||
}
|
||||
|
||||
event_mountpoint {
|
||||
desc {
|
||||
en: "The Mountpoint"
|
||||
zh: "挂载点"
|
||||
}
|
||||
label: {
|
||||
en: "Mountpoint"
|
||||
zh: "挂载点"
|
||||
}
|
||||
}
|
||||
|
||||
event_peername {
|
||||
desc {
|
||||
en: "The IP Address and Port of the Peer Client"
|
||||
zh: "对等客户端的 IP 地址和端口"
|
||||
}
|
||||
label: {
|
||||
en: "IP Address And Port"
|
||||
zh: "IP 地址和端口"
|
||||
}
|
||||
}
|
||||
|
||||
event_sockname {
|
||||
desc {
|
||||
en: "The IP Address and Port of the Local Listener"
|
||||
zh: "本地监听的 IP 地址和端口"
|
||||
}
|
||||
label: {
|
||||
en: "IP Address And Port"
|
||||
zh: "IP 地址和端口"
|
||||
}
|
||||
}
|
||||
|
||||
event_proto_name {
|
||||
desc {
|
||||
en: "Protocol Name"
|
||||
zh: "协议名称"
|
||||
}
|
||||
label: {
|
||||
en: "Protocol Name"
|
||||
zh: "协议名称"
|
||||
}
|
||||
}
|
||||
|
||||
event_proto_ver {
|
||||
desc {
|
||||
en: "Protocol Version"
|
||||
zh: "协议版本"
|
||||
}
|
||||
label: {
|
||||
en: "Protocol Version"
|
||||
zh: "协议版本"
|
||||
}
|
||||
}
|
||||
|
||||
event_keepalive {
|
||||
desc {
|
||||
en: "KeepAlive"
|
||||
zh: "保持连接"
|
||||
}
|
||||
label: {
|
||||
en: "KeepAlive"
|
||||
zh: "保持连接"
|
||||
}
|
||||
}
|
||||
|
||||
event_clean_start {
|
||||
desc {
|
||||
en: "Clean Start"
|
||||
zh: "清除会话"
|
||||
}
|
||||
label: {
|
||||
en: "Clean Start"
|
||||
zh: "清除会话"
|
||||
}
|
||||
}
|
||||
|
||||
event_expiry_interval {
|
||||
desc {
|
||||
en: "Expiry Interval"
|
||||
zh: "到期间隔"
|
||||
}
|
||||
label: {
|
||||
en: "Expiry Interval"
|
||||
zh: "到期间隔"
|
||||
}
|
||||
}
|
||||
|
||||
event_is_bridge {
|
||||
desc {
|
||||
en: "Is Bridge"
|
||||
zh: "是否桥接"
|
||||
}
|
||||
label: {
|
||||
en: "Is Bridge"
|
||||
zh: "是否桥接"
|
||||
}
|
||||
}
|
||||
|
||||
event_connected_at {
|
||||
desc {
|
||||
en: "The Time that this Client is Connected"
|
||||
zh: "客户端连接完成时的时刻"
|
||||
}
|
||||
label: {
|
||||
en: "Connected Time"
|
||||
zh: "连接完成时的时刻"
|
||||
}
|
||||
}
|
||||
|
||||
event_action {
|
||||
desc {
|
||||
en: "Publish or Subscribe"
|
||||
zh: "订阅或发布"
|
||||
}
|
||||
label: {
|
||||
en: "Publish or Subscribe"
|
||||
zh: "订阅或发布"
|
||||
}
|
||||
}
|
||||
|
||||
event_authz_source {
|
||||
desc {
|
||||
en: "Cache, Plugs or Default"
|
||||
zh: "缓存,插件或者默认值"
|
||||
}
|
||||
label: {
|
||||
en: "Auth Source"
|
||||
zh: "认证源"
|
||||
}
|
||||
}
|
||||
|
||||
event_result {
|
||||
desc {
|
||||
en: "Allow or Deny"
|
||||
zh: "允许或禁止"
|
||||
}
|
||||
label: {
|
||||
en: "Auth Result"
|
||||
zh: "认证结果"
|
||||
}
|
||||
}
|
||||
|
||||
event_server {
|
||||
desc {
|
||||
en: "The IP address (or hostname) and port of the MQTT broker, in IP:Port format"
|
||||
zh: "MQTT broker的 IP 地址(或主机名)和端口,采用 IP:Port 格式"
|
||||
}
|
||||
label: {
|
||||
en: "Server IP And Port"
|
||||
zh: "服务器 IP 地址和端口"
|
||||
}
|
||||
}
|
||||
|
||||
event_dup {
|
||||
desc {
|
||||
en: "The DUP flag of the MQTT message"
|
||||
zh: "MQTT 消息的 DUP 标志"
|
||||
}
|
||||
label: {
|
||||
en: "DUP Flag"
|
||||
zh: "DUP 标志"
|
||||
}
|
||||
}
|
||||
|
||||
event_retain {
|
||||
desc {
|
||||
en: "If is a retain message"
|
||||
zh: "是否是保留消息"
|
||||
}
|
||||
label: {
|
||||
en: "Retain Message"
|
||||
zh: "保留消息"
|
||||
}
|
||||
}
|
||||
|
||||
event_ctx_dropped {
|
||||
desc {
|
||||
en: "The Reason for Dropping"
|
||||
zh: "消息被丢弃的原因"
|
||||
}
|
||||
label: {
|
||||
en: "Dropped Reason"
|
||||
zh: "丢弃原因"
|
||||
}
|
||||
}
|
||||
|
||||
event_ctx_disconnected_reason {
|
||||
desc {
|
||||
en: "The Reason for Disconnect"
|
||||
zh: "断开连接的原因"
|
||||
}
|
||||
label: {
|
||||
en: "Disconnect Reason"
|
||||
zh: "断开连接原因"
|
||||
}
|
||||
}
|
||||
|
||||
event_ctx_disconnected_da {
|
||||
desc {
|
||||
en: "The Time that this Client is Disconnected"
|
||||
zh: "客户端断开连接的时刻"
|
||||
}
|
||||
label: {
|
||||
en: "Disconnected Time"
|
||||
zh: "客户端断开连接时刻"
|
||||
}
|
||||
}
|
||||
|
||||
event_ctx_connack_reason_code {
|
||||
desc {
|
||||
en: "The reason code"
|
||||
zh: "错误码"
|
||||
}
|
||||
label: {
|
||||
en: "Reason Code"
|
||||
zh: "错误码"
|
||||
}
|
||||
}
|
||||
|
||||
rule_id {
|
||||
desc {
|
||||
en: "The ID of the rule"
|
||||
zh: "规则的 ID "
|
||||
}
|
||||
label: {
|
||||
en: "Rule ID"
|
||||
zh: "规则 ID "
|
||||
}
|
||||
}
|
||||
|
||||
node_node {
|
||||
desc {
|
||||
en: "The node name"
|
||||
zh: "节点名字"
|
||||
}
|
||||
label: {
|
||||
en: "Node Name"
|
||||
zh: "节点名字"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_matched {
|
||||
desc {
|
||||
en: "How much times the FROM clause of the SQL is matched."
|
||||
zh: "SQL 的 FROM 子句匹配的次数。"
|
||||
}
|
||||
label: {
|
||||
en: "Matched"
|
||||
zh: "命中数"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_matched_rate {
|
||||
desc {
|
||||
en: "The rate of matched, times/second"
|
||||
zh: "命中速率,次/秒"
|
||||
}
|
||||
label: {
|
||||
en: "命中速率"
|
||||
zh: "Matched Rate"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_matched_rate_max {
|
||||
desc {
|
||||
en: "The max rate of matched, times/second"
|
||||
zh: "最大命中速率,次/秒"
|
||||
}
|
||||
label: {
|
||||
en: "Max Matched Rate"
|
||||
zh: "最大命中速率"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_matched_rate_last5m {
|
||||
desc {
|
||||
en: "The average rate of matched in last 5 minutes, times/second"
|
||||
zh: "5分钟平均命中速率,次/秒"
|
||||
}
|
||||
label: {
|
||||
en: "Average Matched Rate"
|
||||
zh: "平均命中速率"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_passed {
|
||||
desc {
|
||||
en: "How much times the SQL is passed"
|
||||
zh: "SQL 通过的次数"
|
||||
}
|
||||
label: {
|
||||
en: "SQL Passed"
|
||||
zh: "SQL 通过"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_failed {
|
||||
desc {
|
||||
en: "How much times the SQL is failed"
|
||||
zh: "SQL 失败的次数"
|
||||
}
|
||||
label: {
|
||||
en: "SQL Failed"
|
||||
zh: "SQL 失败"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_failed_exception {
|
||||
desc {
|
||||
en: "How much times the SQL is failed due to exceptions. This may because of a crash when calling a SQL function, or trying to do arithmetic operation on undefined variables"
|
||||
zh: "SQL 由于执行异常而失败的次数。 这可能是因为调用 SQL 函数时崩溃,或者试图对未定义的变量进行算术运算"
|
||||
}
|
||||
label: {
|
||||
en: "SQL Exception"
|
||||
zh: "SQL 执行异常"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_sql_failed_unknown {
|
||||
desc {
|
||||
en: "How much times the SQL is failed due to an unknown error."
|
||||
zh: "由于未知错误导致 SQL 失败的次数。"
|
||||
}
|
||||
label: {
|
||||
en: "SQL Unknown Error"
|
||||
zh: "SQL 未知错误"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_outputs_total {
|
||||
desc {
|
||||
en: "How much times the outputs are called by the rule. This value may several times of 'sql.matched', depending on the number of the outputs of the rule."
|
||||
zh: "规则调用输出的次数。 该值可能是“sql.matched”的几倍,具体取决于规则输出的数量。"
|
||||
}
|
||||
label: {
|
||||
en: "Output Total"
|
||||
zh: "调用输出次数"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_outputs_success {
|
||||
desc {
|
||||
en: "How much times the rule success to call the outputs."
|
||||
zh: "规则成功调用输出的次数。"
|
||||
}
|
||||
label: {
|
||||
en: "Success Output"
|
||||
zh: "成功调用输出次数"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_outputs_failed {
|
||||
desc {
|
||||
en: "How much times the rule failed to call the outputs."
|
||||
zh: "规则调用输出失败的次数。"
|
||||
}
|
||||
label: {
|
||||
en: "Failed Output"
|
||||
zh: "调用输出失败次数"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_outputs_failed_out_of_service {
|
||||
desc {
|
||||
en: "How much times the rule failed to call outputs due to the output is out of service. For example, a bridge is disabled or stopped."
|
||||
zh: "由于输出停止服务而导致规则调用输出失败的次数。 例如,桥接被禁用或停止。"
|
||||
}
|
||||
label: {
|
||||
en: "Fail Output"
|
||||
zh: "调用输出失败次数"
|
||||
}
|
||||
}
|
||||
|
||||
metrics_outputs_failed_unknown {
|
||||
desc {
|
||||
en: "How much times the rule failed to call outputs due to to an unknown error."
|
||||
zh: "由于未知错误,规则调用输出失败的次数。"
|
||||
}
|
||||
label: {
|
||||
en: "Fail Output"
|
||||
zh: "调用输出失败次数"
|
||||
}
|
||||
}
|
||||
|
||||
test_context {
|
||||
desc {
|
||||
en: "The context of the event for testing"
|
||||
zh: "测试事件的上下文"
|
||||
}
|
||||
label: {
|
||||
en: "Event Conetxt"
|
||||
zh: "事件上下文"
|
||||
}
|
||||
}
|
||||
|
||||
test_sql {
|
||||
desc {
|
||||
en: "The SQL of the rule for testing"
|
||||
zh: "测试的 SQL"
|
||||
}
|
||||
label: {
|
||||
en: "Test SQL"
|
||||
zh: "测试 SQL"
|
||||
}
|
||||
}
|
||||
|
||||
rs_event {
|
||||
desc {
|
||||
en: "The event topics"
|
||||
zh: "事件主题"
|
||||
}
|
||||
label: {
|
||||
en: "Event Topics"
|
||||
zh: "事件主题"
|
||||
}
|
||||
}
|
||||
|
||||
rs_title {
|
||||
desc {
|
||||
en: "The title"
|
||||
zh: "标题"
|
||||
}
|
||||
label: {
|
||||
en: "Title"
|
||||
zh: "标题"
|
||||
}
|
||||
}
|
||||
|
||||
rs_description {
|
||||
desc {
|
||||
en: "The description"
|
||||
zh: "描述"
|
||||
}
|
||||
label: {
|
||||
en: "Description"
|
||||
zh: "描述"
|
||||
}
|
||||
}
|
||||
|
||||
rs_columns {
|
||||
desc {
|
||||
en: "The columns"
|
||||
zh: "列"
|
||||
}
|
||||
label: {
|
||||
en: "Column"
|
||||
zh: "列"
|
||||
}
|
||||
}
|
||||
|
||||
rs_test_columns {
|
||||
desc {
|
||||
en: "The test columns"
|
||||
zh: "测试列"
|
||||
}
|
||||
label: {
|
||||
en: "Test Columns"
|
||||
zh: "测试列"
|
||||
}
|
||||
}
|
||||
|
||||
rs_sql_example {
|
||||
desc {
|
||||
en: "The sql_example"
|
||||
zh: "SQL 例子"
|
||||
}
|
||||
label: {
|
||||
en: "SQL Example"
|
||||
zh: "SQL 例子"
|
||||
}
|
||||
}
|
||||
|
||||
ri_metrics {
|
||||
desc {
|
||||
en: "The metrics of the rule"
|
||||
zh: "规则的计数器"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Metrics"
|
||||
zh: "规则计数器"
|
||||
}
|
||||
}
|
||||
|
||||
ri_node_metrics {
|
||||
desc {
|
||||
en: "The metrics of the rule for each node"
|
||||
zh: "每个节点的规则计数器"
|
||||
}
|
||||
label: {
|
||||
en: "Each Node Rule Metrics"
|
||||
zh: "每个节点规则计数器"
|
||||
}
|
||||
}
|
||||
|
||||
ri_from {
|
||||
desc {
|
||||
en: "The topics of the rule"
|
||||
zh: "规则指定的主题"
|
||||
}
|
||||
label: {
|
||||
en: "Topics of Rule"
|
||||
zh: "规则指定的主题"
|
||||
}
|
||||
}
|
||||
|
||||
ri_created_at {
|
||||
desc {
|
||||
en: "The created time of the rule"
|
||||
zh: "规则创建时间"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Create Time"
|
||||
zh: "规则创建时间"
|
||||
}
|
||||
}
|
||||
|
||||
root_rule_creation {
|
||||
desc {
|
||||
en: "Schema for creating rules"
|
||||
zh: "用于创建规则的 Schema"
|
||||
}
|
||||
label: {
|
||||
en: "Create Schema"
|
||||
zh: "用于创建规则的 Schema"
|
||||
}
|
||||
}
|
||||
|
||||
root_rule_info {
|
||||
desc {
|
||||
en: "Schema for rule info"
|
||||
zh: "用于规则信息的 Schema"
|
||||
}
|
||||
label: {
|
||||
en: "Info Schema"
|
||||
zh: "用于规则信息的 Schema"
|
||||
}
|
||||
}
|
||||
|
||||
root_rule_events {
|
||||
desc {
|
||||
en: "Schema for rule events"
|
||||
zh: "用于事件的 Schema"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Events Schema"
|
||||
zh: "用于规则事件的 Schema"
|
||||
}
|
||||
}
|
||||
|
||||
root_rule_test {
|
||||
desc {
|
||||
en: "Schema for testing rules"
|
||||
zh: "用于规则测试的 Schema"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Test Schema"
|
||||
zh: "用于规则测试的 Schema"
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,100 @@
|
|||
emqx_rule_engine_api {
|
||||
|
||||
api1 {
|
||||
desc {
|
||||
en: "List all rules"
|
||||
zh: "列出所有规则"
|
||||
}
|
||||
label: {
|
||||
en: "List All Rules"
|
||||
zh: "列出所有规则"
|
||||
}
|
||||
}
|
||||
|
||||
api2 {
|
||||
desc {
|
||||
en: "Create a new rule using given Id"
|
||||
zh: "通过指定 ID 创建规则"
|
||||
}
|
||||
label: {
|
||||
en: "Create Rule By ID"
|
||||
zh: "通过指定 ID 创建规则"
|
||||
}
|
||||
}
|
||||
|
||||
api3 {
|
||||
desc {
|
||||
en: "List all events can be used in rules"
|
||||
zh: "列出所有能被规则使用的事件"
|
||||
}
|
||||
label: {
|
||||
en: "List All Events Can Be Used In Rule"
|
||||
zh: "列出所有能被规则使用的事件"
|
||||
}
|
||||
}
|
||||
|
||||
api4 {
|
||||
desc {
|
||||
en: "Get a rule by given Id"
|
||||
zh: "通过 ID 查询规则"
|
||||
}
|
||||
label: {
|
||||
en: "Get Rule"
|
||||
zh: "查询规则"
|
||||
}
|
||||
}
|
||||
|
||||
api5 {
|
||||
desc {
|
||||
en: "Update a rule by given Id to all nodes in the cluster"
|
||||
zh: "通过 ID 更新集群里所有节点上的规则"
|
||||
}
|
||||
label: {
|
||||
en: "Update Cluster Rule"
|
||||
zh: "更新集群规则"
|
||||
}
|
||||
}
|
||||
|
||||
api6 {
|
||||
desc {
|
||||
en: "Delete a rule by given Id from all nodes in the cluster"
|
||||
zh: "通过 ID 删除集群里所有节点上的规则"
|
||||
}
|
||||
label: {
|
||||
en: "Delete Cluster Rule"
|
||||
zh: "删除集群规则"
|
||||
}
|
||||
}
|
||||
|
||||
api7 {
|
||||
desc {
|
||||
en: "Reset a rule metrics"
|
||||
zh: "重置规则计数"
|
||||
}
|
||||
label: {
|
||||
en: "Reset Rule Metrics"
|
||||
zh: "重置规则计数"
|
||||
}
|
||||
}
|
||||
|
||||
api8 {
|
||||
desc {
|
||||
en: "Test a rule"
|
||||
zh: "测试一个规则"
|
||||
}
|
||||
label: {
|
||||
en: "Test Rule"
|
||||
zh: "测试规则"
|
||||
}
|
||||
}
|
||||
desc9 {
|
||||
desc {
|
||||
en: "List of rules"
|
||||
zh: "列出所有规则"
|
||||
}
|
||||
label: {
|
||||
en: "List Rules"
|
||||
zh: "列出所有规则"
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,242 @@
|
|||
emqx_rule_engine_schema {
|
||||
|
||||
rules_name {
|
||||
desc {
|
||||
en: "The name of the rule"
|
||||
zh: "规则名字"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Name"
|
||||
zh: "规则名字"
|
||||
}
|
||||
}
|
||||
|
||||
rules_sql {
|
||||
desc {
|
||||
en: """
|
||||
SQL query to transform the messages.<br>
|
||||
Example: <code>SELECT * FROM "test/topic" WHERE payload.x = 1</code><br>
|
||||
"""
|
||||
zh: """
|
||||
用于处理消息的 SQL 。<br>
|
||||
示例:<code>SELECT * FROM "test/topic" WHERE payload.x = 1</code><br>
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Rule SQL"
|
||||
zh: "规则 SQL"
|
||||
}
|
||||
}
|
||||
|
||||
rules_outputs {
|
||||
desc {
|
||||
en: """
|
||||
A list of outputs of the rule.<br>
|
||||
An output can be a string that refers to the channel ID of an EMQX bridge, or an object
|
||||
that refers to a function.<br>
|
||||
There a some built-in functions like "republish" and "console", and we also support user
|
||||
provided functions in the format: "{module}:{function}".<br>
|
||||
The outputs in the list are executed sequentially.
|
||||
This means that if one of the output is executing slowly, all the following outputs will not
|
||||
be executed until it returns.<br>
|
||||
If one of the output crashed, all other outputs come after it will still be executed, in the
|
||||
original order.<br>
|
||||
If there's any error when running an output, there will be an error message, and the 'failure'
|
||||
counter of the function output or the bridge channel will increase.
|
||||
"""
|
||||
zh: """
|
||||
规则的动作列表。<br>
|
||||
动作可以是指向 EMQX bridge 的引用,也可以是一个指向函数的对象。<br>
|
||||
我们支持一些内置函数,如“republish”和“console”,我们还支持用户提供的函数,它的格式为:“{module}:{function}”。<br>
|
||||
列表中的动作按顺序执行。这意味着如果其中一个动作执行缓慢,则以下所有动作都不会被执行直到它返回。<br>
|
||||
如果其中一个动作崩溃,在它之后的所有动作仍然会被按照原始顺序执行。<br>
|
||||
如果运行动作时出现任何错误,则会出现错误消息,并且相应的计数器会增加。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Rule Action List"
|
||||
zh: "动作列表"
|
||||
}
|
||||
}
|
||||
|
||||
rules_enable {
|
||||
desc {
|
||||
en: "Enable or disable the rule"
|
||||
zh: "启用或禁用规则引擎"
|
||||
}
|
||||
label: {
|
||||
en: "Enable Or Disable Rule"
|
||||
zh: "启用或禁用规则引擎"
|
||||
}
|
||||
}
|
||||
|
||||
rules_description {
|
||||
desc {
|
||||
en: "The description of the rule"
|
||||
zh: "规则的描述"
|
||||
}
|
||||
label: {
|
||||
en: "Rule Description"
|
||||
zh: "规则描述"
|
||||
}
|
||||
}
|
||||
|
||||
republish_function {
|
||||
desc {
|
||||
en: """Republish the message as a new MQTT message"""
|
||||
zh: """将消息重新发布为新的 MQTT 消息"""
|
||||
}
|
||||
label: {
|
||||
en: "Republish Function"
|
||||
zh: "重新发布函数"
|
||||
}
|
||||
}
|
||||
|
||||
console_function {
|
||||
desc {
|
||||
en: """Print the outputs to the console"""
|
||||
zh: "将输出打印到控制台"
|
||||
}
|
||||
label: {
|
||||
en: "Console Function"
|
||||
zh: "控制台函数"
|
||||
}
|
||||
}
|
||||
|
||||
user_provided_function_function {
|
||||
desc {
|
||||
en: """
|
||||
The user provided function. Should be in the format: '{module}:{function}'.<br>
|
||||
Where {module} is the Erlang callback module and {function} is the Erlang function.
|
||||
<br>
|
||||
To write your own function, checkout the function <code>console</code> and
|
||||
<code>republish</code> in the source file:
|
||||
<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> as an example.
|
||||
"""
|
||||
zh: """
|
||||
用户提供的函数。 格式应为:'{module}:{function}'。<br>
|
||||
其中 {module} 是 Erlang 回调模块, {function} 是 Erlang 函数。<br>
|
||||
要编写自己的函数,请检查源文件:<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> 中的示例函数 <code>console</code> 和<code>republish</code> 。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "User Provided Function"
|
||||
zh: "用户提供的函数"
|
||||
}
|
||||
}
|
||||
|
||||
user_provided_function_args {
|
||||
desc {
|
||||
en: """
|
||||
The args will be passed as the 3rd argument to module:function/3,
|
||||
checkout the function <code>console</code> and <code>republish</code> in the source file:
|
||||
<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> as an example.
|
||||
"""
|
||||
zh: """
|
||||
用户提供的参数将作为函数 module:function/3 的第三个参数,
|
||||
请检查源文件:<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> 中的示例函数 <code>console</code> 和<code>republish</code> 。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "User Provided Function Args"
|
||||
zh: "用户提供函数的参数"
|
||||
}
|
||||
}
|
||||
|
||||
republish_args_topic {
|
||||
desc {
|
||||
en: """
|
||||
The target topic of message to be re-published.<br>
|
||||
Template with variables is allowed, see description of the 'republish_args'.
|
||||
"""
|
||||
zh: """
|
||||
重新发布消息的目标主题。<br>
|
||||
允许使用带有变量的模板,请参阅“republish_args”的描述。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Target Topic"
|
||||
zh: "目标主题"
|
||||
}
|
||||
}
|
||||
|
||||
republish_args_qos {
|
||||
desc {
|
||||
en: """
|
||||
The qos of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>
|
||||
Defaults to ${qos}. If variable ${qos} is not found from the selected result of the rule,
|
||||
0 is used.
|
||||
"""
|
||||
zh: """
|
||||
要重新发布的消息的 qos。允许使用带有变量的模板,请参阅“republish_args”的描述。<br>
|
||||
默认为 ${qos}。 如果从规则的选择结果中没有找到变量 ${qos},则使用 0。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Message QoS"
|
||||
zh: "消息 QoS 等级"
|
||||
}
|
||||
}
|
||||
|
||||
republish_args_retain {
|
||||
desc {
|
||||
en: """
|
||||
The 'retain' flag of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>
|
||||
Defaults to ${retain}. If variable ${retain} is not found from the selected result
|
||||
of the rule, false is used.
|
||||
"""
|
||||
zh: """
|
||||
要重新发布的消息的“保留”标志。允许使用带有变量的模板,请参阅“republish_args”的描述。<br>
|
||||
默认为 ${retain}。 如果从所选结果中未找到变量 ${retain},则使用 false。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Retain Flag"
|
||||
zh: "保留消息标志"
|
||||
}
|
||||
}
|
||||
|
||||
republish_args_payload {
|
||||
desc {
|
||||
en: """
|
||||
The payload of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>.
|
||||
Defaults to ${payload}. If variable ${payload} is not found from the selected result
|
||||
of the rule, then the string "undefined" is used.
|
||||
"""
|
||||
zh: """
|
||||
要重新发布的消息的有效负载。允许使用带有变量的模板,请参阅“republish_args”的描述。<br>。
|
||||
默认为 ${payload}。 如果从所选结果中未找到变量 ${payload},则使用字符串 "undefined"。
|
||||
"""
|
||||
}
|
||||
label: {
|
||||
en: "Message Payload"
|
||||
zh: "消息负载"
|
||||
}
|
||||
}
|
||||
|
||||
rule_engine_ignore_sys_message {
|
||||
desc {
|
||||
en: "When set to 'true' (default), rule-engine will ignore messages published to $SYS topics."
|
||||
zh: "当设置为“true”(默认)时,规则引擎将忽略发布到 $SYS 主题的消息。"
|
||||
}
|
||||
label: {
|
||||
en: "Ignore Sys Message"
|
||||
zh: "忽略系统消息"
|
||||
}
|
||||
}
|
||||
|
||||
rule_engine_rules {
|
||||
desc {
|
||||
en: """The rules"""
|
||||
zh: "规则"
|
||||
}
|
||||
label: {
|
||||
en: "Rules"
|
||||
zh: "规则"
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -3,6 +3,7 @@
|
|||
-behaviour(hocon_schema).
|
||||
|
||||
-include_lib("typerefl/include/types.hrl").
|
||||
-include_lib("hocon/include/hoconsc.hrl").
|
||||
-include_lib("emqx/include/logger.hrl").
|
||||
|
||||
-export([ check_params/2
|
||||
|
@ -30,10 +31,10 @@ check_params(Params, Tag) ->
|
|||
%% Hocon Schema Definitions
|
||||
|
||||
roots() ->
|
||||
[ {"rule_creation", sc(ref("rule_creation"), #{desc => "Schema for creating rules"})}
|
||||
, {"rule_info", sc(ref("rule_info"), #{desc => "Schema for rule info"})}
|
||||
, {"rule_events", sc(ref("rule_events"), #{desc => "Schema for rule events"})}
|
||||
, {"rule_test", sc(ref("rule_test"), #{desc => "Schema for testing rules"})}
|
||||
[ {"rule_creation", sc(ref("rule_creation"), #{desc => ?DESC("root_rule_creation")})}
|
||||
, {"rule_info", sc(ref("rule_info"), #{desc => ?DESC("root_rule_info")})}
|
||||
, {"rule_events", sc(ref("rule_events"), #{desc => ?DESC("root_rule_events")})}
|
||||
, {"rule_test", sc(ref("rule_test"), #{desc => ?DESC("root_rule_test")})}
|
||||
].
|
||||
|
||||
fields("rule_creation") ->
|
||||
|
@ -41,14 +42,14 @@ fields("rule_creation") ->
|
|||
|
||||
fields("rule_info") ->
|
||||
[ rule_id()
|
||||
, {"metrics", sc(ref("metrics"), #{desc => "The metrics of the rule"})}
|
||||
, {"metrics", sc(ref("metrics"), #{desc => ?DESC("ri_metrics")})}
|
||||
, {"node_metrics", sc(hoconsc:array(ref("node_metrics")),
|
||||
#{ desc => "The metrics of the rule for each node"
|
||||
#{ desc => ?DESC("ri_node_metrics")
|
||||
})}
|
||||
, {"from", sc(hoconsc:array(binary()),
|
||||
#{desc => "The topics of the rule", example => "t/#"})}
|
||||
#{desc => ?DESC("ri_from"), example => "t/#"})}
|
||||
, {"created_at", sc(binary(),
|
||||
#{ desc => "The created time of the rule"
|
||||
#{ desc => ?DESC("ri_created_at")
|
||||
, example => "2021-12-01T15:00:43.153+08:00"
|
||||
})}
|
||||
] ++ fields("rule_creation");
|
||||
|
@ -56,12 +57,12 @@ fields("rule_info") ->
|
|||
%% TODO: we can delete this API if the Dashboard not depends on it
|
||||
fields("rule_events") ->
|
||||
ETopics = [binary_to_atom(emqx_rule_events:event_topic(E)) || E <- emqx_rule_events:event_names()],
|
||||
[ {"event", sc(hoconsc:enum(ETopics), #{desc => "The event topics", required => true})}
|
||||
, {"title", sc(binary(), #{desc => "The title", example => "some title"})}
|
||||
, {"description", sc(binary(), #{desc => "The description", example => "some desc"})}
|
||||
, {"columns", sc(map(), #{desc => "The columns"})}
|
||||
, {"test_columns", sc(map(), #{desc => "The test columns"})}
|
||||
, {"sql_example", sc(binary(), #{desc => "The sql_example"})}
|
||||
[ {"event", sc(hoconsc:enum(ETopics), #{desc => ?DESC("rs_event"), required => true})}
|
||||
, {"title", sc(binary(), #{desc => ?DESC("rs_title"), example => "some title"})}
|
||||
, {"description", sc(binary(), #{desc => ?DESC("rs_description"), example => "some desc"})}
|
||||
, {"columns", sc(map(), #{desc => ?DESC("rs_columns")})}
|
||||
, {"test_columns", sc(map(), #{desc => ?DESC("rs_test_columns")})}
|
||||
, {"sql_example", sc(binary(), #{desc => ?DESC("rs_sql_example")})}
|
||||
];
|
||||
|
||||
fields("rule_test") ->
|
||||
|
@ -77,183 +78,177 @@ fields("rule_test") ->
|
|||
, ref("ctx_check_authz_complete")
|
||||
, ref("ctx_bridge_mqtt")
|
||||
]),
|
||||
#{desc => "The context of the event for testing",
|
||||
#{desc => ?DESC("test_context"),
|
||||
default => #{}})}
|
||||
, {"sql", sc(binary(), #{desc => "The SQL of the rule for testing", required => true})}
|
||||
, {"sql", sc(binary(), #{desc => ?DESC("test_sql"), required => true})}
|
||||
];
|
||||
|
||||
fields("metrics") ->
|
||||
[ {"sql.matched", sc(non_neg_integer(), #{
|
||||
desc => "How much times the FROM clause of the SQL is matched."
|
||||
desc => ?DESC("metrics_sql_matched")
|
||||
})}
|
||||
, {"sql.matched.rate", sc(float(), #{desc => "The rate of matched, times/second"})}
|
||||
, {"sql.matched.rate.max", sc(float(), #{desc => "The max rate of matched, times/second"})}
|
||||
, {"sql.matched.rate", sc(float(), #{desc => ?DESC("metrics_sql_matched_rate") })}
|
||||
, {"sql.matched.rate.max", sc(float(), #{desc => ?DESC("metrics_sql_matched_rate_max") })}
|
||||
, {"sql.matched.rate.last5m", sc(float(),
|
||||
#{desc => "The average rate of matched in last 5 minutes, times/second"})}
|
||||
, {"sql.passed", sc(non_neg_integer(), #{desc => "How much times the SQL is passed"})}
|
||||
, {"sql.failed", sc(non_neg_integer(), #{desc => "How much times the SQL is failed"})}
|
||||
#{desc => ?DESC("metrics_sql_matched_rate_last5m") })}
|
||||
, {"sql.passed", sc(non_neg_integer(), #{desc => ?DESC("metrics_sql_passed") })}
|
||||
, {"sql.failed", sc(non_neg_integer(), #{desc => ?DESC("metrics_sql_failed") })}
|
||||
, {"sql.failed.exception", sc(non_neg_integer(), #{
|
||||
desc => "How much times the SQL is failed due to exceptions. "
|
||||
"This may because of a crash when calling a SQL function, or "
|
||||
"trying to do arithmetic operation on undefined variables"
|
||||
desc => ?DESC("metrics_sql_failed_exception")
|
||||
})}
|
||||
, {"sql.failed.unknown", sc(non_neg_integer(), #{
|
||||
desc => "How much times the SQL is failed due to an unknown error."
|
||||
desc => ?DESC("metrics_sql_failed_unknown")
|
||||
})}
|
||||
, {"outputs.total", sc(non_neg_integer(), #{
|
||||
desc => "How much times the outputs are called by the rule. "
|
||||
"This value may several times of 'sql.matched', depending on the "
|
||||
"number of the outputs of the rule."
|
||||
desc => ?DESC("metrics_outputs_total")
|
||||
})}
|
||||
, {"outputs.success", sc(non_neg_integer(), #{
|
||||
desc => "How much times the rule success to call the outputs."
|
||||
desc => ?DESC("metrics_outputs_success")
|
||||
})}
|
||||
, {"outputs.failed", sc(non_neg_integer(), #{
|
||||
desc => "How much times the rule failed to call the outputs."
|
||||
desc => ?DESC("metrics_outputs_failed")
|
||||
})}
|
||||
, {"outputs.failed.out_of_service", sc(non_neg_integer(), #{
|
||||
desc => "How much times the rule failed to call outputs due to the output is "
|
||||
"out of service. For example, a bridge is disabled or stopped."
|
||||
desc => ?DESC("metrics_outputs_failed_out_of_service")
|
||||
})}
|
||||
, {"outputs.failed.unknown", sc(non_neg_integer(), #{
|
||||
desc => "How much times the rule failed to call outputs due to to an unknown error."
|
||||
desc => ?DESC("metrics_outputs_failed_unknown")
|
||||
})}
|
||||
];
|
||||
|
||||
fields("node_metrics") ->
|
||||
[ {"node", sc(binary(), #{desc => "The node name", example => "emqx@127.0.0.1"})}
|
||||
[ {"node", sc(binary(), #{desc => ?DESC("node_node"), example => "emqx@127.0.0.1"})}
|
||||
] ++ fields("metrics");
|
||||
|
||||
fields("ctx_pub") ->
|
||||
[ {"event_type", sc(message_publish, #{desc => "Event Type", required => true})}
|
||||
, {"id", sc(binary(), #{desc => "Message ID"})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"payload", sc(binary(), #{desc => "The Message Payload"})}
|
||||
, {"peerhost", sc(binary(), #{desc => "The IP Address of the Peer Client"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
[ {"event_type", sc(message_publish, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"id", sc(binary(), #{desc => ?DESC("event_id")})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"payload", sc(binary(), #{desc => ?DESC("event_payload")})}
|
||||
, {"peerhost", sc(binary(), #{desc => ?DESC("event_peerhost")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"publish_received_at", sc(integer(), #{
|
||||
desc => "The Time that this Message is Received"})}
|
||||
desc => ?DESC("event_publish_received_at")})}
|
||||
] ++ [qos()];
|
||||
|
||||
fields("ctx_sub") ->
|
||||
[ {"event_type", sc(session_subscribed, #{desc => "Event Type", required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"payload", sc(binary(), #{desc => "The Message Payload"})}
|
||||
, {"peerhost", sc(binary(), #{desc => "The IP Address of the Peer Client"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
[ {"event_type", sc(session_subscribed, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"payload", sc(binary(), #{desc => ?DESC("event_payload")})}
|
||||
, {"peerhost", sc(binary(), #{desc => ?DESC("event_peerhost")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"publish_received_at", sc(integer(), #{
|
||||
desc => "The Time that this Message is Received"})}
|
||||
desc => ?DESC("event_publish_received_at")})}
|
||||
] ++ [qos()];
|
||||
|
||||
fields("ctx_unsub") ->
|
||||
[{"event_type", sc(session_unsubscribed, #{desc => "Event Type", required => true})}] ++
|
||||
[{"event_type", sc(session_unsubscribed, #{desc => ?DESC("event_event_type"), required => true})}] ++
|
||||
proplists:delete("event_type", fields("ctx_sub"));
|
||||
|
||||
fields("ctx_delivered") ->
|
||||
[ {"event_type", sc(message_delivered, #{desc => "Event Type", required => true})}
|
||||
, {"id", sc(binary(), #{desc => "Message ID"})}
|
||||
, {"from_clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"from_username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"payload", sc(binary(), #{desc => "The Message Payload"})}
|
||||
, {"peerhost", sc(binary(), #{desc => "The IP Address of the Peer Client"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
[ {"event_type", sc(message_delivered, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"id", sc(binary(), #{desc => ?DESC("event_id")})}
|
||||
, {"from_clientid", sc(binary(), #{desc => ?DESC("event_from_clientid")})}
|
||||
, {"from_username", sc(binary(), #{desc => ?DESC("event_from_username")})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"payload", sc(binary(), #{desc => ?DESC("event_payload")})}
|
||||
, {"peerhost", sc(binary(), #{desc => ?DESC("event_peerhost")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"publish_received_at", sc(integer(), #{
|
||||
desc => "The Time that this Message is Received"})}
|
||||
desc => ?DESC("event_publish_received_at")})}
|
||||
] ++ [qos()];
|
||||
|
||||
fields("ctx_acked") ->
|
||||
[{"event_type", sc(message_acked, #{desc => "Event Type", required => true})}] ++
|
||||
[{"event_type", sc(message_acked, #{desc => ?DESC("event_event_type"), required => true})}] ++
|
||||
proplists:delete("event_type", fields("ctx_delivered"));
|
||||
|
||||
fields("ctx_dropped") ->
|
||||
[ {"event_type", sc(message_dropped, #{desc => "Event Type", required => true})}
|
||||
, {"id", sc(binary(), #{desc => "Message ID"})}
|
||||
, {"reason", sc(binary(), #{desc => "The Reason for Dropping"})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"payload", sc(binary(), #{desc => "The Message Payload"})}
|
||||
, {"peerhost", sc(binary(), #{desc => "The IP Address of the Peer Client"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
[ {"event_type", sc(message_dropped, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"id", sc(binary(), #{desc => ?DESC("event_id")})}
|
||||
, {"reason", sc(binary(), #{desc => ?DESC("event_ctx_dropped")})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"payload", sc(binary(), #{desc => ?DESC("event_payload")})}
|
||||
, {"peerhost", sc(binary(), #{desc => ?DESC("event_peerhost")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"publish_received_at", sc(integer(), #{
|
||||
desc => "The Time that this Message is Received"})}
|
||||
desc => ?DESC("event_publish_received_at")})}
|
||||
] ++ [qos()];
|
||||
|
||||
fields("ctx_connected") ->
|
||||
[ {"event_type", sc(client_connected, #{desc => "Event Type", required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"mountpoint", sc(binary(), #{desc => "The Mountpoint"})}
|
||||
, {"peername", sc(binary(), #{desc => "The IP Address and Port of the Peer Client"})}
|
||||
, {"sockname", sc(binary(), #{desc => "The IP Address and Port of the Local Listener"})}
|
||||
, {"proto_name", sc(binary(), #{desc => "Protocol Name"})}
|
||||
, {"proto_ver", sc(binary(), #{desc => "Protocol Version"})}
|
||||
, {"keepalive", sc(integer(), #{desc => "KeepAlive"})}
|
||||
, {"clean_start", sc(boolean(), #{desc => "Clean Start", default => true})}
|
||||
, {"expiry_interval", sc(integer(), #{desc => "Expiry Interval"})}
|
||||
, {"is_bridge", sc(boolean(), #{desc => "Is Bridge", default => false})}
|
||||
[ {"event_type", sc(client_connected, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"mountpoint", sc(binary(), #{desc => ?DESC("event_mountpoint")})}
|
||||
, {"peername", sc(binary(), #{desc => ?DESC("event_peername")})}
|
||||
, {"sockname", sc(binary(), #{desc => ?DESC("event_sockname")})}
|
||||
, {"proto_name", sc(binary(), #{desc => ?DESC("event_proto_name")})}
|
||||
, {"proto_ver", sc(binary(), #{desc => ?DESC("event_proto_ver")})}
|
||||
, {"keepalive", sc(integer(), #{desc => ?DESC("event_keepalive")})}
|
||||
, {"clean_start", sc(boolean(), #{desc => ?DESC("event_clean_start"), default => true})}
|
||||
, {"expiry_interval", sc(integer(), #{desc => ?DESC("event_expiry_interval")})}
|
||||
, {"is_bridge", sc(boolean(), #{desc => ?DESC("event_is_bridge"), default => false})}
|
||||
, {"connected_at", sc(integer(), #{
|
||||
desc => "The Time that this Client is Connected"})}
|
||||
desc => ?DESC("event_connected_at")})}
|
||||
];
|
||||
|
||||
fields("ctx_disconnected") ->
|
||||
[ {"event_type", sc(client_disconnected, #{desc => "Event Type", required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"reason", sc(binary(), #{desc => "The Reason for Disconnect"})}
|
||||
, {"peername", sc(binary(), #{desc => "The IP Address and Port of the Peer Client"})}
|
||||
, {"sockname", sc(binary(), #{desc => "The IP Address and Port of the Local Listener"})}
|
||||
[ {"event_type", sc(client_disconnected, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"reason", sc(binary(), #{desc => ?DESC("event_ctx_disconnected_reason")})}
|
||||
, {"peername", sc(binary(), #{desc => ?DESC("event_peername")})}
|
||||
, {"sockname", sc(binary(), #{desc => ?DESC("event_sockname")})}
|
||||
, {"disconnected_at", sc(integer(), #{
|
||||
desc => "The Time that this Client is Disconnected"})}
|
||||
desc => ?DESC("event_ctx_disconnected_da")})}
|
||||
];
|
||||
|
||||
fields("ctx_connack") ->
|
||||
[ {"event_type", sc(client_connack, #{desc => "Event Type", required => true})}
|
||||
, {"reason_code", sc(binary(), #{desc => "The reason code"})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"clean_start", sc(boolean(), #{desc => "Clean Start", default => true})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"peername", sc(binary(), #{desc => "The IP Address and Port of the Peer Client"})}
|
||||
, {"sockname", sc(binary(), #{desc => "The IP Address and Port of the Local Listener"})}
|
||||
, {"proto_name", sc(binary(), #{desc => "Protocol Name"})}
|
||||
, {"proto_ver", sc(binary(), #{desc => "Protocol Version"})}
|
||||
, {"keepalive", sc(integer(), #{desc => "KeepAlive"})}
|
||||
, {"expiry_interval", sc(integer(), #{desc => "Expiry Interval"})}
|
||||
[ {"event_type", sc(client_connack, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"reason_code", sc(binary(), #{desc => ?DESC("event_ctx_connack_reason_code")})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"clean_start", sc(boolean(), #{desc => ?DESC("event_clean_start"), default => true})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"peername", sc(binary(), #{desc => ?DESC("event_peername")})}
|
||||
, {"sockname", sc(binary(), #{desc => ?DESC("event_sockname")})}
|
||||
, {"proto_name", sc(binary(), #{desc => ?DESC("event_proto_name")})}
|
||||
, {"proto_ver", sc(binary(), #{desc => ?DESC("event_proto_ver")})}
|
||||
, {"keepalive", sc(integer(), #{desc => ?DESC("event_keepalive")})}
|
||||
, {"expiry_interval", sc(integer(), #{desc => ?DESC("event_expiry_interval")})}
|
||||
, {"connected_at", sc(integer(), #{
|
||||
desc => "The Time that this Client is Connected"})}
|
||||
desc => ?DESC("event_connected_at")})}
|
||||
];
|
||||
fields("ctx_check_authz_complete") ->
|
||||
[ {"event_type", sc(client_check_authz_complete, #{desc => "Event Type", required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => "The Client ID"})}
|
||||
, {"username", sc(binary(), #{desc => "The User Name"})}
|
||||
, {"peerhost", sc(binary(), #{desc => "The IP Address of the Peer Client"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
, {"action", sc(binary(), #{desc => "Publish or Subscribe"})}
|
||||
, {"authz_source", sc(binary(), #{desc => "Cache, Plugs or Default"})}
|
||||
, {"result", sc(binary(), #{desc => "Allow or Deny"})}
|
||||
[ {"event_type", sc(client_check_authz_complete, #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"clientid", sc(binary(), #{desc => ?DESC("event_clientid")})}
|
||||
, {"username", sc(binary(), #{desc => ?DESC("event_username")})}
|
||||
, {"peerhost", sc(binary(), #{desc => ?DESC("event_peerhost")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"action", sc(binary(), #{desc => ?DESC("event_action")})}
|
||||
, {"authz_source", sc(binary(), #{desc => ?DESC("event_authz_source")})}
|
||||
, {"result", sc(binary(), #{desc => ?DESC("event_result")})}
|
||||
];
|
||||
fields("ctx_bridge_mqtt") ->
|
||||
[ {"event_type", sc('$bridges/mqtt:*', #{desc => "Event Type", required => true})}
|
||||
, {"id", sc(binary(), #{desc => "Message ID"})}
|
||||
, {"payload", sc(binary(), #{desc => "The Message Payload"})}
|
||||
, {"topic", sc(binary(), #{desc => "Message Topic"})}
|
||||
, {"server", sc(binary(), #{desc => "The IP address (or hostname) and port of the MQTT broker,"
|
||||
" in IP:Port format"})}
|
||||
, {"dup", sc(binary(), #{desc => "The DUP flag of the MQTT message"})}
|
||||
, {"retain", sc(binary(), #{desc => "If is a retain message"})}
|
||||
[ {"event_type", sc('$bridges/mqtt:*', #{desc => ?DESC("event_event_type"), required => true})}
|
||||
, {"id", sc(binary(), #{desc => ?DESC("event_id")})}
|
||||
, {"payload", sc(binary(), #{desc => ?DESC("event_payload")})}
|
||||
, {"topic", sc(binary(), #{desc => ?DESC("event_topic")})}
|
||||
, {"server", sc(binary(), #{desc => ?DESC("event_server")})}
|
||||
, {"dup", sc(binary(), #{desc => ?DESC("event_dup")})}
|
||||
, {"retain", sc(binary(), #{desc => ?DESC("event_retain")})}
|
||||
, {"message_received_at", sc(integer(), #{
|
||||
desc => "The Time that this Message is Received"})}
|
||||
desc => ?DESC("event_publish_received_at")})}
|
||||
] ++ [qos()].
|
||||
|
||||
qos() ->
|
||||
{"qos", sc(emqx_schema:qos(), #{desc => "The Message QoS"})}.
|
||||
{"qos", sc(emqx_schema:qos(), #{desc => ?DESC("event_qos")})}.
|
||||
|
||||
rule_id() ->
|
||||
{"id", sc(binary(),
|
||||
#{ desc => "The ID of the rule", required => true
|
||||
#{ desc => ?DESC("rule_id"), required => true
|
||||
, example => "293fb66f"
|
||||
})}.
|
||||
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
|
||||
-include("rule_engine.hrl").
|
||||
-include_lib("emqx/include/logger.hrl").
|
||||
-include_lib("hocon/include/hoconsc.hrl").
|
||||
-include_lib("typerefl/include/types.hrl").
|
||||
|
||||
-behaviour(minirest_api).
|
||||
|
@ -102,14 +103,14 @@ schema("/rules") ->
|
|||
'operationId' => '/rules',
|
||||
get => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"List all rules">>,
|
||||
description => ?DESC("api1"),
|
||||
summary => <<"List Rules">>,
|
||||
responses => #{
|
||||
200 => mk(array(rule_info_schema()), #{desc => "List of rules"})
|
||||
200 => mk(array(rule_info_schema()), #{desc => ?DESC("desc9")})
|
||||
}},
|
||||
post => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Create a new rule using given Id">>,
|
||||
description => ?DESC("api2"),
|
||||
summary => <<"Create a Rule">>,
|
||||
'requestBody' => rule_creation_schema(),
|
||||
responses => #{
|
||||
|
@ -123,7 +124,7 @@ schema("/rule_events") ->
|
|||
'operationId' => '/rule_events',
|
||||
get => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"List all events can be used in rules">>,
|
||||
description => ?DESC("api3"),
|
||||
summary => <<"List Events">>,
|
||||
responses => #{
|
||||
200 => mk(ref(emqx_rule_api_schema, "rule_events"), #{})
|
||||
|
@ -136,7 +137,7 @@ schema("/rules/:id") ->
|
|||
'operationId' => '/rules/:id',
|
||||
get => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Get a rule by given Id">>,
|
||||
description => ?DESC("api4"),
|
||||
summary => <<"Get a Rule">>,
|
||||
parameters => param_path_id(),
|
||||
responses => #{
|
||||
|
@ -146,7 +147,7 @@ schema("/rules/:id") ->
|
|||
},
|
||||
put => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Update a rule by given Id to all nodes in the cluster">>,
|
||||
description => ?DESC("api5"),
|
||||
summary => <<"Update a Rule">>,
|
||||
parameters => param_path_id(),
|
||||
'requestBody' => rule_creation_schema(),
|
||||
|
@ -157,7 +158,7 @@ schema("/rules/:id") ->
|
|||
},
|
||||
delete => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Delete a rule by given Id from all nodes in the cluster">>,
|
||||
description => ?DESC("api6"),
|
||||
summary => <<"Delete a Rule">>,
|
||||
parameters => param_path_id(),
|
||||
responses => #{
|
||||
|
@ -171,7 +172,7 @@ schema("/rules/:id/reset_metrics") ->
|
|||
'operationId' => '/rules/:id/reset_metrics',
|
||||
put => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Reset a rule metrics">>,
|
||||
description => ?DESC("api7"),
|
||||
summary => <<"Reset a Rule Metrics">>,
|
||||
parameters => param_path_id(),
|
||||
responses => #{
|
||||
|
@ -186,7 +187,7 @@ schema("/rule_test") ->
|
|||
'operationId' => '/rule_test',
|
||||
post => #{
|
||||
tags => [<<"rules">>],
|
||||
description => <<"Test a rule">>,
|
||||
description => ?DESC("api8"),
|
||||
summary => <<"Test a Rule">>,
|
||||
'requestBody' => rule_test_schema(),
|
||||
responses => #{
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
-module(emqx_rule_engine_schema).
|
||||
|
||||
-include_lib("typerefl/include/types.hrl").
|
||||
-include_lib("hocon/include/hoconsc.hrl").
|
||||
|
||||
-behaviour(hocon_schema).
|
||||
|
||||
|
@ -34,38 +35,21 @@ namespace() -> rule_engine.
|
|||
roots() -> ["rule_engine"].
|
||||
|
||||
fields("rule_engine") ->
|
||||
[ {ignore_sys_message, sc(boolean(), #{default => true, desc =>
|
||||
"When set to 'true' (default), rule-engine will ignore messages published to $SYS topics."
|
||||
[ {ignore_sys_message, sc(boolean(), #{default => true, desc => ?DESC("rule_engine_ignore_sys_message")
|
||||
})}
|
||||
, {rules, sc(hoconsc:map("id", ref("rules")), #{desc => "The rules", default => #{}})}
|
||||
, {rules, sc(hoconsc:map("id", ref("rules")), #{desc => ?DESC("rule_engine_rules"), default => #{}})}
|
||||
];
|
||||
|
||||
fields("rules") ->
|
||||
[ rule_name()
|
||||
, {"sql", sc(binary(),
|
||||
#{ desc => "
|
||||
SQL query to transform the messages.<br>
|
||||
Example: <code>SELECT * FROM \"test/topic\" WHERE payload.x = 1</code><br>
|
||||
"
|
||||
#{ desc => ?DESC("rules_sql")
|
||||
, example => "SELECT * FROM \"test/topic\" WHERE payload.x = 1"
|
||||
, required => true
|
||||
, validator => fun ?MODULE:validate_sql/1
|
||||
})}
|
||||
, {"outputs", sc(hoconsc:array(hoconsc:union(outputs())),
|
||||
#{ desc => "
|
||||
A list of outputs of the rule.<br>
|
||||
An output can be a string that refers to the channel ID of an EMQX bridge, or an object
|
||||
that refers to a function.<br>
|
||||
There a some built-in functions like \"republish\" and \"console\", and we also support user
|
||||
provided functions in the format: \"{module}:{function}\".<br>
|
||||
The outputs in the list are executed sequentially.
|
||||
This means that if one of the output is executing slowly, all the following outputs will not
|
||||
be executed until it returns.<br>
|
||||
If one of the output crashed, all other outputs come after it will still be executed, in the
|
||||
original order.<br>
|
||||
If there's any error when running an output, there will be an error message, and the 'failure'
|
||||
counter of the function output or the bridge channel will increase.
|
||||
"
|
||||
#{ desc => ?DESC("rules_outputs")
|
||||
, default => []
|
||||
, example => [
|
||||
<<"http:my_http_bridge">>,
|
||||
|
@ -74,21 +58,21 @@ counter of the function output or the bridge channel will increase.
|
|||
#{function => console}
|
||||
]
|
||||
})}
|
||||
, {"enable", sc(boolean(), #{desc => "Enable or disable the rule", default => true})}
|
||||
, {"enable", sc(boolean(), #{desc => ?DESC("rules_enable"), default => true})}
|
||||
, {"description", sc(binary(),
|
||||
#{ desc => "The description of the rule"
|
||||
#{ desc => ?DESC("rules_description")
|
||||
, example => "Some description"
|
||||
, default => <<>>
|
||||
})}
|
||||
];
|
||||
|
||||
fields("builtin_output_republish") ->
|
||||
[ {function, sc(republish, #{desc => "Republish the message as a new MQTT message"})}
|
||||
[ {function, sc(republish, #{desc => ?DESC("republish_function")})}
|
||||
, {args, sc(ref("republish_args"), #{default => #{}})}
|
||||
];
|
||||
|
||||
fields("builtin_output_console") ->
|
||||
[ {function, sc(console, #{desc => "Print the outputs to the console"})}
|
||||
[ {function, sc(console, #{desc => ?DESC("console_function")})}
|
||||
%% we may support some args for the console output in the future
|
||||
%, {args, sc(map(), #{desc => "The arguments of the built-in 'console' output",
|
||||
% default => #{}})}
|
||||
|
@ -96,62 +80,33 @@ fields("builtin_output_console") ->
|
|||
|
||||
fields("user_provided_function") ->
|
||||
[ {function, sc(binary(),
|
||||
#{ desc => "
|
||||
The user provided function. Should be in the format: '{module}:{function}'.<br>
|
||||
Where {module} is the Erlang callback module and {function} is the Erlang function.
|
||||
<br>
|
||||
To write your own function, checkout the function <code>console</code> and
|
||||
<code>republish</code> in the source file:
|
||||
<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> as an example.
|
||||
"
|
||||
#{ desc => ?DESC("user_provided_function_function")
|
||||
, example => "module:function"
|
||||
})}
|
||||
, {args, sc(map(),
|
||||
#{ desc => "
|
||||
The args will be passed as the 3rd argument to module:function/3,
|
||||
checkout the function <code>console</code> and <code>republish</code> in the source file:
|
||||
<code>apps/emqx_rule_engine/src/emqx_rule_outputs.erl</code> as an example.
|
||||
"
|
||||
#{ desc => ?DESC("user_provided_function_args")
|
||||
, default => #{}
|
||||
})}
|
||||
];
|
||||
|
||||
fields("republish_args") ->
|
||||
[ {topic, sc(binary(),
|
||||
#{ desc =>"
|
||||
The target topic of message to be re-published.<br>
|
||||
Template with variables is allowed, see description of the 'republish_args'.
|
||||
"
|
||||
#{ desc => ?DESC("republish_args_topic")
|
||||
, required => true
|
||||
, example => <<"a/1">>
|
||||
})}
|
||||
, {qos, sc(qos(),
|
||||
#{ desc => "
|
||||
The qos of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>
|
||||
Defaults to ${qos}. If variable ${qos} is not found from the selected result of the rule,
|
||||
0 is used.
|
||||
"
|
||||
#{ desc => ?DESC("republish_args_qos")
|
||||
, default => <<"${qos}">>
|
||||
, example => <<"${qos}">>
|
||||
})}
|
||||
, {retain, sc(hoconsc:union([binary(), boolean()]),
|
||||
#{ desc => "
|
||||
The 'retain' flag of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>
|
||||
Defaults to ${retain}. If variable ${retain} is not found from the selected result
|
||||
of the rule, false is used.
|
||||
"
|
||||
#{ desc => ?DESC("republish_args_retain")
|
||||
, default => <<"${retain}">>
|
||||
, example => <<"${retain}">>
|
||||
})}
|
||||
, {payload, sc(binary(),
|
||||
#{ desc => "
|
||||
The payload of the message to be re-published.
|
||||
Template with variables is allowed, see description of the 'republish_args'.<br>.
|
||||
Defaults to ${payload}. If variable ${payload} is not found from the selected result
|
||||
of the rule, then the string \"undefined\" is used.
|
||||
"
|
||||
#{ desc => ?DESC("republish_args_payload")
|
||||
, default => <<"${payload}">>
|
||||
, example => <<"${payload}">>
|
||||
})}
|
||||
|
@ -191,7 +146,7 @@ desc(_) ->
|
|||
|
||||
rule_name() ->
|
||||
{"name", sc(binary(),
|
||||
#{ desc => "The name of the rule"
|
||||
#{ desc => ?DESC("rules_name")
|
||||
, default => ""
|
||||
, required => true
|
||||
, example => "foo"
|
||||
|
|
Loading…
Reference in New Issue