148 lines
6.6 KiB
Erlang
148 lines
6.6 KiB
Erlang
-module(emqx_rule_api_schema).
|
|
|
|
-behaviour(hocon_schema).
|
|
|
|
-include_lib("typerefl/include/types.hrl").
|
|
-include_lib("emqx/include/logger.hrl").
|
|
|
|
-export([ check_params/2
|
|
]).
|
|
|
|
-export([roots/0, fields/1]).
|
|
|
|
-type tag() :: rule_creation | rule_test.
|
|
|
|
-spec check_params(map(), tag()) -> {ok, map()} | {error, term()}.
|
|
check_params(Params, Tag) ->
|
|
BTag = atom_to_binary(Tag),
|
|
try hocon_schema:check_plain(?MODULE, #{BTag => Params},
|
|
#{atom_key => true, nullable => true}, [BTag]) of
|
|
#{Tag := Checked} -> {ok, Checked}
|
|
catch
|
|
Error:Reason:ST ->
|
|
?SLOG(error, #{msg => "check_rule_params_failed",
|
|
exception => Error,
|
|
reason => Reason,
|
|
stacktrace => ST}),
|
|
{error, {Reason, ST}}
|
|
end.
|
|
|
|
%%======================================================================================
|
|
%% Hocon Schema Definitions
|
|
|
|
roots() ->
|
|
[ {"rule_creation", sc(ref("rule_creation"), #{desc => "Schema for creating rules"})}
|
|
, {"rule_test", sc(ref("rule_test"), #{desc => "Schema for testing rules"})}
|
|
].
|
|
|
|
fields("rule_creation") ->
|
|
[ {"id", sc(binary(), #{desc => "The Id of the rule", nullable => false})}
|
|
] ++ emqx_rule_engine_schema:fields("rules");
|
|
|
|
fields("rule_test") ->
|
|
[ {"context", sc(hoconsc:union([ ref("ctx_pub")
|
|
, ref("ctx_sub")
|
|
, ref("ctx_delivered")
|
|
, ref("ctx_acked")
|
|
, ref("ctx_dropped")
|
|
, ref("ctx_connected")
|
|
, ref("ctx_disconnected")
|
|
]),
|
|
#{desc => "The context of the event for testing",
|
|
default => #{}})}
|
|
, {"sql", sc(binary(), #{desc => "The SQL of the rule for testing", nullable => false})}
|
|
];
|
|
|
|
fields("ctx_pub") ->
|
|
[ {"event_type", sc(message_publish, #{desc => "Event Type", nullable => false})}
|
|
, {"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"})}
|
|
, {"publish_received_at", sc(integer(), #{
|
|
desc => "The Time that this Message is Received"})}
|
|
] ++ [qos()];
|
|
|
|
fields("ctx_sub") ->
|
|
[ {"event_type", sc(session_subscribed, #{desc => "Event Type", nullable => false})}
|
|
, {"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"})}
|
|
, {"publish_received_at", sc(integer(), #{
|
|
desc => "The Time that this Message is Received"})}
|
|
] ++ [qos()];
|
|
|
|
fields("ctx_unsub") ->
|
|
[{"event_type", sc(session_unsubscribed, #{desc => "Event Type", nullable => false})}] ++
|
|
proplists:delete("event_type", fields("ctx_sub"));
|
|
|
|
fields("ctx_delivered") ->
|
|
[ {"event_type", sc(message_delivered, #{desc => "Event Type", nullable => false})}
|
|
, {"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"})}
|
|
, {"publish_received_at", sc(integer(), #{
|
|
desc => "The Time that this Message is Received"})}
|
|
] ++ [qos()];
|
|
|
|
fields("ctx_acked") ->
|
|
[{"event_type", sc(message_acked, #{desc => "Event Type", nullable => false})}] ++
|
|
proplists:delete("event_type", fields("ctx_delivered"));
|
|
|
|
fields("ctx_dropped") ->
|
|
[ {"event_type", sc(message_dropped, #{desc => "Event Type", nullable => false})}
|
|
, {"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"})}
|
|
, {"publish_received_at", sc(integer(), #{
|
|
desc => "The Time that this Message is Received"})}
|
|
] ++ [qos()];
|
|
|
|
fields("ctx_connected") ->
|
|
[ {"event_type", sc(client_connected, #{desc => "Event Type", nullable => false})}
|
|
, {"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})}
|
|
, {"connected_at", sc(integer(), #{
|
|
desc => "The Time that this Client is Connected"})}
|
|
];
|
|
|
|
fields("ctx_disconnected") ->
|
|
[ {"event_type", sc(client_disconnected, #{desc => "Event Type", nullable => false})}
|
|
, {"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"})}
|
|
, {"disconnected_at", sc(integer(), #{
|
|
desc => "The Time that this Client is Disconnected"})}
|
|
].
|
|
|
|
qos() ->
|
|
{"qos", sc(hoconsc:union([typerefl:integer(0), typerefl:integer(1), typerefl:integer(2)]),
|
|
#{desc => "The Message QoS"})}.
|
|
|
|
sc(Type, Meta) -> hoconsc:mk(Type, Meta).
|
|
ref(Field) -> hoconsc:ref(?MODULE, Field).
|