Skip to content

Commit ec5e258

Browse files
LoisSotoLopezmichaelklishin
authored andcommitted
Provide per-exchange/queue metrics w/out channelID
1 parent 0af8923 commit ec5e258

File tree

4 files changed

+194
-20
lines changed

4 files changed

+194
-20
lines changed

deps/rabbit_common/include/rabbit_core_metrics.hrl

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,14 @@
2828
{auth_attempt_metrics, set},
2929
{auth_attempt_detailed_metrics, set}]).
3030

31+
% `CORE_NON_CHANNEL_TABLES` are tables that store counters representing the
32+
% same info as some of the channel_queue_metrics, channel_exchange_metrics and
33+
% channel_queue_exchange_metrics but without including the channel ID in the
34+
% key.
35+
-define(CORE_NON_CHANNEL_TABLES, [{queue_counter_metrics, set},
36+
{exchange_metrics, set},
37+
{queue_exchange_metrics, set}]).
38+
3139
-define(CONNECTION_CHURN_METRICS, {node(), 0, 0, 0, 0, 0, 0, 0}).
3240

3341
%% connection_created :: {connection_id, proplist}

deps/rabbit_common/src/rabbit_core_metrics.erl

Lines changed: 29 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -111,13 +111,15 @@ create_table({Table, Type}) ->
111111
{read_concurrency, true}]).
112112

113113
init() ->
114-
_ = [create_table({Table, Type})
115-
|| {Table, Type} <- ?CORE_TABLES ++ ?CORE_EXTRA_TABLES],
114+
Tables = ?CORE_TABLES ++ ?CORE_EXTRA_TABLES ++ ?CORE_NON_CHANNEL_TABLES,
115+
_ = [create_table({Table, Type})
116+
|| {Table, Type} <- Tables],
116117
ok.
117118

118119
terminate() ->
120+
Tables = ?CORE_TABLES ++ ?CORE_EXTRA_TABLES ++ ?CORE_NON_CHANNEL_TABLES,
119121
[ets:delete(Table)
120-
|| {Table, _Type} <- ?CORE_TABLES ++ ?CORE_EXTRA_TABLES],
122+
|| {Table, _Type} <- Tables],
121123
ok.
122124

123125
connection_created(Pid, Infos) ->
@@ -166,53 +168,65 @@ channel_stats(reductions, Id, Value) ->
166168
ets:insert(channel_process_metrics, {Id, Value}),
167169
ok.
168170

169-
channel_stats(exchange_stats, publish, Id, Value) ->
171+
channel_stats(exchange_stats, publish, {_ChannelPid, XName} = Id, Value) ->
170172
%% Includes delete marker
171173
_ = ets:update_counter(channel_exchange_metrics, Id, {2, Value}, {Id, 0, 0, 0, 0, 0}),
174+
_ = ets:update_counter(exchange_metrics, XName, {2, Value}, {XName, 0, 0, 0, 0, 0}),
172175
ok;
173-
channel_stats(exchange_stats, confirm, Id, Value) ->
176+
channel_stats(exchange_stats, confirm, {_ChannelPid, XName} = Id, Value) ->
174177
%% Includes delete marker
175178
_ = ets:update_counter(channel_exchange_metrics, Id, {3, Value}, {Id, 0, 0, 0, 0, 0}),
179+
_ = ets:update_counter(exchange_metrics, XName, {3, Value}, {XName, 0, 0, 0, 0, 0}),
176180
ok;
177-
channel_stats(exchange_stats, return_unroutable, Id, Value) ->
181+
channel_stats(exchange_stats, return_unroutable, {_ChannelPid, XName} = Id, Value) ->
178182
%% Includes delete marker
179183
_ = ets:update_counter(channel_exchange_metrics, Id, {4, Value}, {Id, 0, 0, 0, 0, 0}),
184+
_ = ets:update_counter(exchange_metrics, XName, {4, Value}, {XName, 0, 0, 0, 0, 0}),
180185
ok;
181-
channel_stats(exchange_stats, drop_unroutable, Id, Value) ->
186+
channel_stats(exchange_stats, drop_unroutable, {_ChannelPid, XName} = Id, Value) ->
182187
%% Includes delete marker
183188
_ = ets:update_counter(channel_exchange_metrics, Id, {5, Value}, {Id, 0, 0, 0, 0, 0}),
189+
_ = ets:update_counter(exchange_metrics, XName, {5, Value}, {XName, 0, 0, 0, 0, 0}),
184190
ok;
185-
channel_stats(queue_exchange_stats, publish, Id, Value) ->
191+
channel_stats(queue_exchange_stats, publish, {_ChannelPid, QueueExchange} = Id, Value) ->
186192
%% Includes delete marker
187193
_ = ets:update_counter(channel_queue_exchange_metrics, Id, Value, {Id, 0, 0}),
194+
_ = ets:update_counter(queue_exchange_metrics, QueueExchange, Value, {QueueExchange, 0, 0}),
188195
ok;
189-
channel_stats(queue_stats, get, Id, Value) ->
196+
channel_stats(queue_stats, get, {_ChannelPid, QName} = Id, Value) ->
190197
%% Includes delete marker
191198
_ = ets:update_counter(channel_queue_metrics, Id, {2, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
199+
_ = ets:update_counter(queue_counter_metrics, QName, {2, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
192200
ok;
193-
channel_stats(queue_stats, get_no_ack, Id, Value) ->
201+
channel_stats(queue_stats, get_no_ack, {_ChannelPid, QName} = Id, Value) ->
194202
%% Includes delete marker
195203
_ = ets:update_counter(channel_queue_metrics, Id, {3, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
204+
_ = ets:update_counter(queue_counter_metrics, QName, {3, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
196205
ok;
197-
channel_stats(queue_stats, deliver, Id, Value) ->
206+
channel_stats(queue_stats, deliver, {_ChannelPid, QName} = Id, Value) ->
198207
%% Includes delete marker
199208
_ = ets:update_counter(channel_queue_metrics, Id, {4, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
209+
_ = ets:update_counter(queue_counter_metrics, QName, {4, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
200210
ok;
201-
channel_stats(queue_stats, deliver_no_ack, Id, Value) ->
211+
channel_stats(queue_stats, deliver_no_ack, {_ChannelPid, QName} = Id, Value) ->
202212
%% Includes delete marker
203213
_ = ets:update_counter(channel_queue_metrics, Id, {5, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
214+
_ = ets:update_counter(queue_counter_metrics, QName, {5, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
204215
ok;
205-
channel_stats(queue_stats, redeliver, Id, Value) ->
216+
channel_stats(queue_stats, redeliver, {_ChannelPid, QName} = Id, Value) ->
206217
%% Includes delete marker
207218
_ = ets:update_counter(channel_queue_metrics, Id, {6, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
219+
_ = ets:update_counter(queue_counter_metrics, QName, {6, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
208220
ok;
209-
channel_stats(queue_stats, ack, Id, Value) ->
221+
channel_stats(queue_stats, ack, {_ChannelPid, QName} = Id, Value) ->
210222
%% Includes delete marker
211223
_ = ets:update_counter(channel_queue_metrics, Id, {7, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
224+
_ = ets:update_counter(queue_counter_metrics, QName, {7, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
212225
ok;
213-
channel_stats(queue_stats, get_empty, Id, Value) ->
226+
channel_stats(queue_stats, get_empty, {_ChannelPid, QName} = Id, Value) ->
214227
%% Includes delete marker
215228
_ = ets:update_counter(channel_queue_metrics, Id, {8, Value}, {Id, 0, 0, 0, 0, 0, 0, 0, 0}),
229+
_ = ets:update_counter(queue_counter_metrics, QName, {8, Value}, {QName, 0, 0, 0, 0, 0, 0, 0, 0}),
216230
ok.
217231

218232
delete(Table, Key) ->

deps/rabbitmq_prometheus/src/collectors/prometheus_rabbitmq_core_metrics_collector.erl

Lines changed: 64 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,15 @@
160160
{2, undefined, queue_disk_writes_total, counter, "Total number of times queue wrote messages to disk", disk_writes},
161161
{2, undefined, stream_segments, counter, "Total number of stream segment files", segments}
162162
]},
163-
163+
{queue_counter_metrics, [
164+
{2, undefined, queue_get_ack_total, counter, "Total number of messages fetched with basic.get in manual acknowledgement mode"},
165+
{3, undefined, queue_get_total, counter, "Total number of messages fetched with basic.get in automatic acknowledgement mode"},
166+
{4, undefined, queue_messages_delivered_ack_total, counter, "Total number of messages delivered to consumers in manual acknowledgement mode"},
167+
{5, undefined, queue_messages_delivered_total, counter, "Total number of messages delivered to consumers in automatic acknowledgement mode"},
168+
{6, undefined, queue_messages_redelivered_total, counter, "Total number of messages redelivered to consumers"},
169+
{7, undefined, queue_messages_acked_total, counter, "Total number of messages acknowledged by consumers"},
170+
{8, undefined, queue_get_empty_total, counter, "Total number of times basic.get operations fetched no message"}
171+
]},
164172
%%% Metrics that contain reference to a channel. Some of them also have
165173
%%% a queue name, but in this case filtering on it doesn't make any
166174
%%% sense, as the queue is not an object of interest here.
@@ -174,6 +182,13 @@
174182
{2, undefined, channel_prefetch, gauge, "Total limit of unacknowledged messages for all consumers on a channel", global_prefetch_count}
175183
]},
176184

185+
{exchange_metrics, [
186+
{2, undefined, exchange_messages_published_total, counter, "Total number of messages published into an exchange on a channel"},
187+
{3, undefined, exchange_messages_confirmed_total, counter, "Total number of messages published into an exchange and confirmed on the channel"},
188+
{4, undefined, exchange_messages_unroutable_returned_total, counter, "Total number of messages published as mandatory into an exchange and returned to the publisher as unroutable"},
189+
{5, undefined, exchange_messages_unroutable_dropped_total, counter, "Total number of messages published as non-mandatory into an exchange and dropped as unroutable"}
190+
]},
191+
177192
{channel_exchange_metrics, [
178193
{2, undefined, channel_messages_published_total, counter, "Total number of messages published into an exchange on a channel"},
179194
{3, undefined, channel_messages_confirmed_total, counter, "Total number of messages published into an exchange and confirmed on the channel"},
@@ -208,6 +223,10 @@
208223
{2, undefined, connection_channels, gauge, "Channels on a connection", channels}
209224
]},
210225

226+
{queue_exchange_metrics, [
227+
{2, undefined, queue_exchange_messages_published_total, counter, "Total number of messages published to queues"}
228+
]},
229+
211230
{channel_queue_exchange_metrics, [
212231
{2, undefined, queue_messages_published_total, counter, "Total number of messages published to queues"}
213232
]}
@@ -542,15 +561,20 @@ get_data(queue_metrics = Table, false, VHostsFilter) ->
542561
{disk_reads, A15}, {disk_writes, A16}, {segments, A17}]}];
543562
get_data(Table, false, VHostsFilter) when Table == channel_exchange_metrics;
544563
Table == queue_coarse_metrics;
564+
Table == queue_counter_metrics;
545565
Table == channel_queue_metrics;
546566
Table == connection_coarse_metrics;
567+
Table == exchange_metrics;
568+
Table == queue_exchange_metrics;
547569
Table == channel_queue_exchange_metrics;
548570
Table == ra_metrics;
549571
Table == channel_process_metrics ->
550572
Result = ets:foldl(fun
551573
%% For queue_coarse_metrics
552574
({#resource{kind = queue, virtual_host = VHost}, _, _, _, _}, Acc) when is_map(VHostsFilter), map_get(VHost, VHostsFilter) == false ->
553575
Acc;
576+
({#resource{kind = queue, virtual_host = VHost}, _, _, _, _, _, _, _, _}, Acc) when is_map(VHostsFilter), map_get(VHost, VHostsFilter) == false ->
577+
Acc;
554578
({_, V1}, {T, A1}) ->
555579
{T, V1 + A1};
556580
({_, V1, _}, {T, A1}) ->
@@ -577,6 +601,42 @@ get_data(Table, false, VHostsFilter) when Table == channel_exchange_metrics;
577601
_ ->
578602
[Result]
579603
end;
604+
get_data(exchange_metrics = Table, true, VHostsFilter) when is_map(VHostsFilter)->
605+
ets:foldl(fun
606+
({#resource{kind = exchange, virtual_host = VHost}, _, _, _, _, _} = Row, Acc) when
607+
map_get(VHost, VHostsFilter)
608+
->
609+
[Row | Acc];
610+
(_Row, Acc) ->
611+
Acc
612+
end, [], Table);
613+
get_data(exchange_metrics, true, _VhostsFilter) ->
614+
[];
615+
get_data(queue_counter_metrics = Table, true, VHostsFilter) when is_map(VHostsFilter)->
616+
ets:foldl(fun
617+
({#resource{kind = queue, virtual_host = VHost}, _, _, _, _, _, _, _, _} = Row, Acc) when
618+
map_get(VHost, VHostsFilter)
619+
->
620+
[Row | Acc];
621+
(_Row, Acc) ->
622+
Acc
623+
end, [], Table);
624+
get_data(queue_counter_metrics, true, _VHostsFilter) ->
625+
[];
626+
get_data(queue_exchange_metrics = Table, true, VHostsFilter) ->
627+
ets:foldl(fun
628+
({{
629+
#resource{kind = queue, virtual_host = VHost},
630+
#resource{kind = exchange, virtual_host = VHost}
631+
}, _, _} = Row, Acc) when
632+
map_get(VHost, VHostsFilter)
633+
->
634+
[Row | Acc];
635+
(_Row, Acc) ->
636+
Acc
637+
end, [], Table);
638+
get_data(queue_exchange_metrics, true, _VHostsFilter) ->
639+
[];
580640
get_data(queue_coarse_metrics = Table, true, VHostsFilter) when is_map(VHostsFilter) ->
581641
ets:foldl(fun
582642
({#resource{kind = queue, virtual_host = VHost}, _, _, _, _} = Row, Acc) when map_get(VHost, VHostsFilter) ->
@@ -669,15 +729,15 @@ division(A, B) ->
669729
accumulate_count_and_sum(Value, {Count, Sum}) ->
670730
{Count + 1, Sum + Value}.
671731

672-
empty(T) when T == channel_queue_exchange_metrics; T == channel_process_metrics; T == queue_consumer_count ->
732+
empty(T) when T == channel_queue_exchange_metrics; T == queue_exchange_metrics; T == channel_process_metrics; T == queue_consumer_count ->
673733
{T, 0};
674734
empty(T) when T == connection_coarse_metrics; T == auth_attempt_metrics; T == auth_attempt_detailed_metrics ->
675735
{T, 0, 0, 0};
676-
empty(T) when T == channel_exchange_metrics; T == queue_coarse_metrics; T == connection_metrics ->
736+
empty(T) when T == channel_exchange_metrics; T == exchange_metrics; T == queue_coarse_metrics; T == connection_metrics ->
677737
{T, 0, 0, 0, 0};
678738
empty(T) when T == ra_metrics ->
679739
{T, 0, 0, 0, 0, 0, {0, 0}};
680-
empty(T) when T == channel_queue_metrics; T == channel_metrics ->
740+
empty(T) when T == channel_queue_metrics; T == queue_counter_metrics; T == channel_metrics ->
681741
{T, 0, 0, 0, 0, 0, 0, 0};
682742
empty(queue_metrics = T) ->
683743
{T, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}.

deps/rabbitmq_prometheus/test/rabbit_prometheus_http_SUITE.erl

Lines changed: 93 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ groups() ->
3434
{config_path, [], generic_tests()},
3535
{global_labels, [], generic_tests()},
3636
{aggregated_metrics, [], [
37-
aggregated_metrics_test,
37+
aggregated_metrics_test,
3838
specific_erlang_metrics_present_test,
3939
global_metrics_present_test,
4040
global_metrics_single_metric_family_test
@@ -57,6 +57,8 @@ groups() ->
5757
queue_consumer_count_single_vhost_per_object_test,
5858
queue_consumer_count_all_vhosts_per_object_test,
5959
queue_coarse_metrics_per_object_test,
60+
queue_counter_metrics_per_object_test,
61+
queue_exchange_metrics_per_object_test,
6062
queue_metrics_per_object_test,
6163
queue_consumer_count_and_queue_metrics_mutually_exclusive_test,
6264
vhost_status_metric,
@@ -523,6 +525,96 @@ queue_coarse_metrics_per_object_test(Config) ->
523525
map_get(rabbitmq_detailed_queue_messages, parse_response(Body3))),
524526
ok.
525527

528+
queue_counter_metrics_per_object_test(Config) ->
529+
Expected1 = #{#{queue => "vhost-1-queue-with-consumer", vhost => "vhost-1"} => [7]},
530+
531+
{_, Body1} = http_get_with_pal(Config,
532+
"/metrics/detailed?vhost=vhost-1&family=queue_counter_metrics",
533+
[], 200),
534+
?assertEqual(
535+
Expected1,
536+
map_get(
537+
rabbitmq_detailed_queue_messages_delivered_ack_total,
538+
parse_response(Body1))),
539+
540+
{_, Body2} = http_get_with_pal(Config,
541+
"/metrics/detailed?vhost=vhost-2&family=queue_counter_metrics",
542+
[], 200),
543+
Expected2 = #{#{queue => "vhost-2-queue-with-consumer", vhost => "vhost-2"} => [11]},
544+
545+
?assertEqual(
546+
Expected2,
547+
map_get(
548+
rabbitmq_detailed_queue_messages_delivered_ack_total,
549+
parse_response(Body2))),
550+
551+
%% Maybe missing, tests for the queue_exchange_metrics
552+
ok.
553+
554+
555+
queue_exchange_metrics_per_object_test(Config) ->
556+
Expected1 = #{
557+
#{
558+
queue => "vhost-1-queue-with-messages",
559+
vhost => "vhost-1",
560+
exchange => ""
561+
} => [7],
562+
#{
563+
exchange => "",
564+
queue => "vhost-1-queue-with-consumer",
565+
vhost => "vhost-1"
566+
} => [7]
567+
},
568+
569+
{_, Body1} = http_get_with_pal(Config,
570+
"/metrics/detailed?vhost=vhost-1&family=queue_exchange_metrics",
571+
[], 200),
572+
?assertEqual(
573+
Expected1,
574+
map_get(
575+
rabbitmq_detailed_queue_exchange_messages_published_total,
576+
parse_response(Body1))),
577+
578+
579+
{_, Body2} = http_get_with_pal(Config,
580+
"/metrics/detailed?vhost=vhost-2&family=queue_exchange_metrics",
581+
[], 200),
582+
583+
584+
Expected2 = #{
585+
#{
586+
queue => "vhost-2-queue-with-messages",
587+
vhost => "vhost-2",
588+
exchange => ""
589+
} => [11],
590+
#{
591+
exchange => "",
592+
queue => "vhost-2-queue-with-consumer",
593+
vhost => "vhost-2"
594+
} => [11]
595+
},
596+
597+
?assertEqual(
598+
Expected2,
599+
map_get(
600+
rabbitmq_detailed_queue_exchange_messages_published_total,
601+
parse_response(Body2))),
602+
603+
ok.
604+
605+
exchange_metrics_per_object_test(Config) ->
606+
Expected1 = #{#{queue => "vhost-1-queue-with-consumer", vhost => "vhost-1"} => [7]},
607+
608+
{_, Body} = http_get_with_pal(Config,
609+
"/metrics/detailed?vhost=vhost-1&family=exchange_metrics",
610+
[], 200),
611+
?assertEqual(
612+
Expected1,
613+
map_get(
614+
rabbitmq_detailed_queue_messages_delivered_ack_total,
615+
parse_response(Body))),
616+
ok.
617+
526618
queue_metrics_per_object_test(Config) ->
527619
Expected1 = #{#{queue => "vhost-1-queue-with-consumer", vhost => "vhost-1"} => [7],
528620
#{queue => "vhost-1-queue-with-messages", vhost => "vhost-1"} => [1]},

0 commit comments

Comments
 (0)