Merge pull request #7865 from EMQ-YangM/fix_imporve_authn_authz_metrics
fix: improve authn, authz metrics
This commit is contained in:
commit
c7826db3f7
|
@ -616,8 +616,8 @@ handle_create_authenticator(Chain, Config, Providers) ->
|
|||
ok = emqx_metrics_worker:create_metrics(
|
||||
authn_metrics,
|
||||
AuthenticatorID,
|
||||
[matched, success, failed, ignore],
|
||||
[matched]
|
||||
[total, success, failed, nomatch],
|
||||
[total]
|
||||
),
|
||||
{ok, serialize_authenticator(Authenticator)};
|
||||
{error, Reason} ->
|
||||
|
@ -628,10 +628,10 @@ handle_create_authenticator(Chain, Config, Providers) ->
|
|||
do_authenticate([], _) ->
|
||||
{stop, {error, not_authorized}};
|
||||
do_authenticate([#authenticator{id = ID, provider = Provider, state = State} | More], Credential) ->
|
||||
emqx_metrics_worker:inc(authn_metrics, ID, matched),
|
||||
emqx_metrics_worker:inc(authn_metrics, ID, total),
|
||||
try Provider:authenticate(Credential, State) of
|
||||
ignore ->
|
||||
ok = emqx_metrics_worker:inc(authn_metrics, ID, ignore),
|
||||
ok = emqx_metrics_worker:inc(authn_metrics, ID, nomatch),
|
||||
do_authenticate(More, Credential);
|
||||
Result ->
|
||||
%% {ok, Extra}
|
||||
|
@ -657,7 +657,7 @@ do_authenticate([#authenticator{id = ID, provider = Provider, state = State} | M
|
|||
stacktrace => Stacktrace,
|
||||
authenticator => ID
|
||||
}),
|
||||
emqx_metrics_worker:inc(authn_metrics, ID, ignore),
|
||||
emqx_metrics_worker:inc(authn_metrics, ID, nomatch),
|
||||
do_authenticate(More, Credential)
|
||||
end.
|
||||
|
||||
|
|
|
@ -163,4 +163,81 @@ emqx_authn_schema {
|
|||
zh: """节点名称。"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_nomatch {
|
||||
desc {
|
||||
en: """The number of times the instance was ignored when the required authentication information was not found in the current instance."""
|
||||
zh: """在当前实例中没有找到需要的认证信息,实例被忽略的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Nomatch Times"""
|
||||
zh: """实例被忽略的次数"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_total {
|
||||
desc {
|
||||
en: """The total number of times the current instance was triggered."""
|
||||
zh: """当前实例被触发的总次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Total Triggered Times"""
|
||||
zh: """当前实例被触发的总次数"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_success {
|
||||
desc {
|
||||
en: """The required authentication information is found in the current instance, and the instance returns authentication success."""
|
||||
zh: """在当前实例中找到需要的认证信息,并且实例返回认证成功的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Authentication Success Times"""
|
||||
zh: """实例认证成功的次数"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_failed {
|
||||
desc {
|
||||
en: """The required authentication information is found in the current instance, and the instance returns authentication failure."""
|
||||
zh: """在当前实例中找到需要的认证信息,并且实例返回认证失败的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Authentication Failed Times"""
|
||||
zh: """实例认证失败的次数"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_rate {
|
||||
desc {
|
||||
en: """The total rate at which instances are triggered, times/second."""
|
||||
zh: """实例被触发的速率。触发速率等于匹配速率 + 忽略速率,单位:次/秒。"""
|
||||
}
|
||||
label: {
|
||||
en: """Total Triggered Rate"""
|
||||
zh: """实例被触发的速率"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_rate_max {
|
||||
desc {
|
||||
en: """The highest trigger rate the instance has ever reached, times/second."""
|
||||
zh: """实例曾经达到的最高触发速率,单位:次/秒。"""
|
||||
}
|
||||
label: {
|
||||
en: """Highest Triggered Rate"""
|
||||
zh: """实例曾经达到的最高触发速率"""
|
||||
}
|
||||
}
|
||||
|
||||
metrics_rate_last5m {
|
||||
desc {
|
||||
en: """The average trigger rate of the instance within 5 minutes, times/second."""
|
||||
zh: """实例5分钟内平均触发速率,单位:次/秒。"""
|
||||
}
|
||||
label: {
|
||||
en: """Average Triggered Rate in Last 5min"""
|
||||
zh: """实例5分钟内平均触发速率"""
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1036,14 +1036,14 @@ make_result_map(ResList) ->
|
|||
lists:foldl(Fun, {maps:new(), maps:new(), maps:new(), maps:new()}, ResList).
|
||||
|
||||
restructure_map(#{
|
||||
counters := #{failed := Failed, matched := Match, success := Succ, ignore := Ignore},
|
||||
rate := #{matched := #{current := Rate, last5m := Rate5m, max := RateMax}}
|
||||
counters := #{failed := Failed, total := Total, success := Succ, nomatch := Nomatch},
|
||||
rate := #{total := #{current := Rate, last5m := Rate5m, max := RateMax}}
|
||||
}) ->
|
||||
#{
|
||||
matched => Match,
|
||||
total => Total,
|
||||
success => Succ,
|
||||
failed => Failed,
|
||||
ignore => Ignore,
|
||||
nomatch => Nomatch,
|
||||
rate => Rate,
|
||||
rate_last5m => Rate5m,
|
||||
rate_max => RateMax
|
||||
|
@ -1451,11 +1451,32 @@ status_metrics_example() ->
|
|||
status_metrics => #{
|
||||
summary => <<"Authn status metrics">>,
|
||||
value => #{
|
||||
metrics => #{
|
||||
resource_metrics => #{
|
||||
matched => 0,
|
||||
success => 0,
|
||||
failed => 0,
|
||||
ignore => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
},
|
||||
node_resource_metrics => [
|
||||
#{
|
||||
node => node(),
|
||||
metrics => #{
|
||||
matched => 0,
|
||||
success => 0,
|
||||
failed => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
}
|
||||
}
|
||||
],
|
||||
metrics => #{
|
||||
total => 0,
|
||||
success => 0,
|
||||
failed => 0,
|
||||
nomatch => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
|
@ -1466,9 +1487,9 @@ status_metrics_example() ->
|
|||
node => node(),
|
||||
metrics => #{
|
||||
matched => 0,
|
||||
success => 0,
|
||||
total => 0,
|
||||
failed => 0,
|
||||
ignore => 0,
|
||||
nomatch => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
|
|
|
@ -115,8 +115,14 @@ fields("metrics_status_fields") ->
|
|||
];
|
||||
fields("metrics") ->
|
||||
[
|
||||
{"ignore", mk(integer(), #{desc => ?DESC("failed")})}
|
||||
] ++ common_field();
|
||||
{"nomatch", mk(integer(), #{desc => ?DESC("metrics_nomatch")})},
|
||||
{"total", mk(integer(), #{desc => ?DESC("metrics_total")})},
|
||||
{"success", mk(integer(), #{desc => ?DESC("metrics_success")})},
|
||||
{"failed", mk(integer(), #{desc => ?DESC("metrics_failed")})},
|
||||
{"rate", mk(float(), #{desc => ?DESC("metrics_rate")})},
|
||||
{"rate_max", mk(float(), #{desc => ?DESC("metrics_rate_max")})},
|
||||
{"rate_last5m", mk(float(), #{desc => ?DESC("metrics_rate_last5m")})}
|
||||
];
|
||||
fields("resource_metrics") ->
|
||||
common_field();
|
||||
fields("node_metrics") ->
|
||||
|
|
|
@ -125,24 +125,24 @@ t_aggregate_metrics(_) ->
|
|||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 1,
|
||||
total => 1,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.1,
|
||||
success => 1,
|
||||
ignore => 1
|
||||
nomatch => 1
|
||||
}
|
||||
},
|
||||
'emqx@node2.emqx.io' => #{
|
||||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 1,
|
||||
total => 1,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.1,
|
||||
success => 1,
|
||||
ignore => 2
|
||||
nomatch => 2
|
||||
}
|
||||
}
|
||||
},
|
||||
|
@ -152,12 +152,12 @@ t_aggregate_metrics(_) ->
|
|||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 2,
|
||||
total => 2,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.2,
|
||||
success => 2,
|
||||
ignore => 3
|
||||
nomatch => 3
|
||||
}
|
||||
},
|
||||
Res
|
||||
|
@ -226,7 +226,7 @@ test_authenticator(PathPrefix) ->
|
|||
LookFun = fun(List) -> LookupVal(List, RList) end,
|
||||
MetricsList = [
|
||||
{<<"failed">>, 0},
|
||||
{<<"matched">>, 0},
|
||||
{<<"total">>, 0},
|
||||
{<<"rate">>, 0.0},
|
||||
{<<"rate_last5m">>, 0.0},
|
||||
{<<"rate_max">>, 0.0},
|
||||
|
@ -321,17 +321,17 @@ test_authenticator_users(PathPrefix) ->
|
|||
[] ->
|
||||
#{
|
||||
<<"metrics">> := #{
|
||||
<<"matched">> := 1,
|
||||
<<"total">> := 1,
|
||||
<<"success">> := 0,
|
||||
<<"ignore">> := 1
|
||||
<<"nomatch">> := 1
|
||||
}
|
||||
} = jiffy:decode(PageData0, [return_maps]);
|
||||
["listeners", 'tcp:default'] ->
|
||||
#{
|
||||
<<"metrics">> := #{
|
||||
<<"matched">> := 1,
|
||||
<<"total">> := 1,
|
||||
<<"success">> := 0,
|
||||
<<"ignore">> := 1
|
||||
<<"nomatch">> := 1
|
||||
}
|
||||
} = jiffy:decode(PageData0, [return_maps])
|
||||
end,
|
||||
|
@ -379,17 +379,17 @@ test_authenticator_users(PathPrefix) ->
|
|||
[] ->
|
||||
#{
|
||||
<<"metrics">> := #{
|
||||
<<"matched">> := 2,
|
||||
<<"total">> := 2,
|
||||
<<"success">> := 1,
|
||||
<<"ignore">> := 1
|
||||
<<"nomatch">> := 1
|
||||
}
|
||||
} = jiffy:decode(PageData01, [return_maps]);
|
||||
["listeners", 'tcp:default'] ->
|
||||
#{
|
||||
<<"metrics">> := #{
|
||||
<<"matched">> := 2,
|
||||
<<"total">> := 2,
|
||||
<<"success">> := 1,
|
||||
<<"ignore">> := 1
|
||||
<<"nomatch">> := 1
|
||||
}
|
||||
} = jiffy:decode(PageData01, [return_maps])
|
||||
end,
|
||||
|
|
|
@ -528,36 +528,47 @@ Filter supports the following placeholders:
|
|||
}
|
||||
}
|
||||
|
||||
ignore {
|
||||
metrics_total {
|
||||
desc {
|
||||
en: """Not match any rules."""
|
||||
zh: """没有匹配到任何规则。"""
|
||||
en: """The total number of times the authorization rule was triggered."""
|
||||
zh: """鉴权实例被触发的总次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Not Match Any Rules"""
|
||||
zh: """没有匹配到任何规则。"""
|
||||
en: """The Total Number of Times the Authorization Rule was Triggered"""
|
||||
zh: """鉴权实例被触发的总次数"""
|
||||
}
|
||||
}
|
||||
|
||||
nomatch {
|
||||
desc {
|
||||
en: """The number of times that no authorization rules were matched."""
|
||||
zh: """没有匹配到任何鉴权规则的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """The Number of Times that no Authorization Rules were Matched"""
|
||||
zh: """没有匹配到任何鉴权规则的次数"""
|
||||
}
|
||||
}
|
||||
|
||||
allow {
|
||||
desc {
|
||||
en: """Authorize allow."""
|
||||
zh: """鉴权成功。"""
|
||||
en: """The number of times the authentication was successful."""
|
||||
zh: """鉴权成功的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Authorize Allow"""
|
||||
zh: """鉴权成功"""
|
||||
en: """The Number of Times the Authentication was Successful"""
|
||||
zh: """鉴权成功次数"""
|
||||
}
|
||||
}
|
||||
|
||||
deny {
|
||||
desc {
|
||||
en: """Authorize Deny."""
|
||||
zh: """鉴权失败"""
|
||||
en: """The number of authentication failures."""
|
||||
zh: """鉴权失败的次数。"""
|
||||
}
|
||||
label: {
|
||||
en: """Authorize Deny"""
|
||||
zh: """鉴权失败"""
|
||||
en: """The Number of Authentication Failures"""
|
||||
zh: """鉴权失败次数"""
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -176,8 +176,8 @@ do_post_config_update({?CMD_PREPEND, RawNewSource}, Sources) ->
|
|||
ok = emqx_metrics_worker:create_metrics(
|
||||
authz_metrics,
|
||||
TypeName,
|
||||
[matched, allow, deny, ignore],
|
||||
[matched]
|
||||
[total, allow, deny, nomatch],
|
||||
[total]
|
||||
),
|
||||
[InitedNewSource] ++ lookup();
|
||||
do_post_config_update({?CMD_APPEND, RawNewSource}, Sources) ->
|
||||
|
@ -271,8 +271,8 @@ init_metrics(Source) ->
|
|||
emqx_metrics_worker:create_metrics(
|
||||
authz_metrics,
|
||||
TypeName,
|
||||
[matched, allow, deny, ignore],
|
||||
[matched]
|
||||
[total, allow, deny, nomatch],
|
||||
[total]
|
||||
).
|
||||
|
||||
%%--------------------------------------------------------------------
|
||||
|
@ -354,13 +354,24 @@ do_authorize(
|
|||
[Connector = #{type := Type} | Tail]
|
||||
) ->
|
||||
Module = authz_module(Type),
|
||||
emqx_metrics_worker:inc(authz_metrics, Type, matched),
|
||||
case Module:authorize(Client, PubSub, Topic, Connector) of
|
||||
emqx_metrics_worker:inc(authz_metrics, Type, total),
|
||||
try Module:authorize(Client, PubSub, Topic, Connector) of
|
||||
nomatch ->
|
||||
emqx_metrics_worker:inc(authz_metrics, Type, ignore),
|
||||
emqx_metrics_worker:inc(authz_metrics, Type, nomatch),
|
||||
do_authorize(Client, PubSub, Topic, Tail);
|
||||
Matched ->
|
||||
{Matched, Type}
|
||||
catch
|
||||
Class:Reason:Stacktrace ->
|
||||
emqx_metrics_worker:inc(authz_metrics, Type, nomatch),
|
||||
?SLOG(warning, #{
|
||||
msg => "unexpected_error_in_authorize",
|
||||
exception => Class,
|
||||
reason => Reason,
|
||||
stacktrace => Stacktrace,
|
||||
authorize_type => Type
|
||||
}),
|
||||
do_authorize(Client, PubSub, Topic, Tail)
|
||||
end.
|
||||
|
||||
get_enabled_authzs() ->
|
||||
|
|
|
@ -398,14 +398,14 @@ make_result_map(ResList) ->
|
|||
lists:foldl(Fun, {maps:new(), maps:new(), maps:new(), maps:new()}, ResList).
|
||||
|
||||
restructure_map(#{
|
||||
counters := #{deny := Failed, matched := Match, allow := Succ, ignore := Ignore},
|
||||
rate := #{matched := #{current := Rate, last5m := Rate5m, max := RateMax}}
|
||||
counters := #{deny := Failed, total := Total, allow := Succ, nomatch := Nomatch},
|
||||
rate := #{total := #{current := Rate, last5m := Rate5m, max := RateMax}}
|
||||
}) ->
|
||||
#{
|
||||
matched => Match,
|
||||
total => Total,
|
||||
allow => Succ,
|
||||
deny => Failed,
|
||||
ignore => Ignore,
|
||||
nomatch => Nomatch,
|
||||
rate => Rate,
|
||||
rate_last5m => Rate5m,
|
||||
rate_max => RateMax
|
||||
|
@ -592,10 +592,10 @@ status_metrics_example() ->
|
|||
}
|
||||
],
|
||||
metrics => #{
|
||||
matched => 0,
|
||||
total => 0,
|
||||
allow => 0,
|
||||
deny => 0,
|
||||
ignore => 0,
|
||||
nomatch => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
|
@ -604,10 +604,10 @@ status_metrics_example() ->
|
|||
#{
|
||||
node => node(),
|
||||
metrics => #{
|
||||
matched => 0,
|
||||
total => 0,
|
||||
allow => 0,
|
||||
deny => 0,
|
||||
ignore => 0,
|
||||
nomatch => 0,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.0
|
||||
|
|
|
@ -166,10 +166,10 @@ fields("metrics_status_fields") ->
|
|||
];
|
||||
fields("metrics") ->
|
||||
[
|
||||
{"matched", mk(integer(), #{desc => ?DESC("matched")})},
|
||||
{"total", mk(integer(), #{desc => ?DESC("metrics_total")})},
|
||||
{"allow", mk(integer(), #{desc => ?DESC("allow")})},
|
||||
{"deny", mk(integer(), #{desc => ?DESC("deny")})},
|
||||
{"ignore", mk(float(), #{desc => ?DESC("ignore")})}
|
||||
{"nomatch", mk(float(), #{desc => ?DESC("nomatch")})}
|
||||
] ++ common_rate_field();
|
||||
fields("node_metrics") ->
|
||||
[
|
||||
|
|
|
@ -243,8 +243,8 @@ t_api(_) ->
|
|||
<<"metrics">> := #{
|
||||
<<"allow">> := 0,
|
||||
<<"deny">> := 0,
|
||||
<<"matched">> := 0,
|
||||
<<"ignore">> := 0
|
||||
<<"total">> := 0,
|
||||
<<"nomatch">> := 0
|
||||
}
|
||||
} = jiffy:decode(Status4, [return_maps]),
|
||||
?assertMatch(
|
||||
|
@ -298,8 +298,8 @@ t_api(_) ->
|
|||
<<"metrics">> := #{
|
||||
<<"allow">> := 0,
|
||||
<<"deny">> := 0,
|
||||
<<"matched">> := 0,
|
||||
<<"ignore">> := 0
|
||||
<<"total">> := 0,
|
||||
<<"nomatch">> := 0
|
||||
}
|
||||
} = jiffy:decode(Status5_1, [return_maps]),
|
||||
|
||||
|
@ -377,8 +377,8 @@ t_api(_) ->
|
|||
<<"metrics">> := #{
|
||||
<<"allow">> := 1,
|
||||
<<"deny">> := 0,
|
||||
<<"matched">> := 1,
|
||||
<<"ignore">> := 0
|
||||
<<"total">> := 1,
|
||||
<<"nomatch">> := 0
|
||||
}
|
||||
} = jiffy:decode(Status5, [return_maps]),
|
||||
|
||||
|
@ -396,8 +396,8 @@ t_api(_) ->
|
|||
<<"metrics">> := #{
|
||||
<<"allow">> := 2,
|
||||
<<"deny">> := 0,
|
||||
<<"matched">> := 2,
|
||||
<<"ignore">> := 0
|
||||
<<"total">> := 2,
|
||||
<<"nomatch">> := 0
|
||||
}
|
||||
} = jiffy:decode(Status6, [return_maps]),
|
||||
|
||||
|
@ -416,8 +416,8 @@ t_api(_) ->
|
|||
<<"metrics">> := #{
|
||||
<<"allow">> := 3,
|
||||
<<"deny">> := 0,
|
||||
<<"matched">> := 3,
|
||||
<<"ignore">> := 0
|
||||
<<"total">> := 3,
|
||||
<<"nomatch">> := 0
|
||||
}
|
||||
} = jiffy:decode(Status7, [return_maps]),
|
||||
|
||||
|
@ -508,7 +508,7 @@ t_aggregate_metrics(_) ->
|
|||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 1,
|
||||
total => 1,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.1,
|
||||
|
@ -519,7 +519,7 @@ t_aggregate_metrics(_) ->
|
|||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 1,
|
||||
total => 1,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.1,
|
||||
|
@ -533,7 +533,7 @@ t_aggregate_metrics(_) ->
|
|||
metrics =>
|
||||
#{
|
||||
failed => 0,
|
||||
matched => 2,
|
||||
total => 2,
|
||||
rate => 0.0,
|
||||
rate_last5m => 0.0,
|
||||
rate_max => 0.2,
|
||||
|
|
Loading…
Reference in New Issue