From 446198c926637bf996df90ceb22810db20f46a81 Mon Sep 17 00:00:00 2001 From: Jonathan Gourdon Date: Mon, 16 May 2022 23:28:25 +0200 Subject: [PATCH] Add exchanges filtering capabilities --- README.md | 2 ++ config.example.json | 2 ++ config.go | 16 ++++++++++++ exporter_exchange.go | 14 ++++++++++ exporter_test.go | 61 ++++++++++++++++++++++++++++++++++++-------- main.go | 2 ++ rabbitClient_test.go | 2 +- 7 files changed, 88 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 937d284..1c7db65 100644 --- a/README.md +++ b/README.md @@ -60,6 +60,8 @@ SKIP_VHOST | ^$ |regex, matching vhost names are not exported. First performs IN INCLUDE_VHOST | .* | regex vhost filter. Only queues in matching vhosts are exported INCLUDE_QUEUES | .* | regex queue filter. Just matching names are exported SKIP_QUEUES | ^$ |regex, matching queue names are not exported (useful for short-lived rpc queues). First performed INCLUDE, after SKIP +INCLUDE_EXCHANGES | .* | regex exchange filter. (Only exchanges in matching vhosts are exported) +SKIP_EXCHANGES | ^$ | regex, matching exchanges names are not exported. First performed INCLUDE, after SKIP RABBIT_CAPABILITIES | bert,no_sort | comma-separated list of extended scraping capabilities supported by the target RabbitMQ server RABBIT_EXPORTERS | exchange,node,queue | List of enabled modules. Possible modules: connections,shovel,federation,exchange,node,queue,memory RABBIT_TIMEOUT | 30 | timeout in seconds for retrieving data from management plugin. diff --git a/config.example.json b/config.example.json index 405d936..603cc1b 100644 --- a/config.example.json +++ b/config.example.json @@ -10,6 +10,8 @@ "key_file": "client-key.pem", "insecure_skip_verify": false, "exlude_metrics": [], + "include_exchanges": ".*", + "skip_exchanges": "^$", "include_queues": ".*", "skip_queues": "^$", "skip_vhost": "^$", diff --git a/config.go b/config.go index 7115adc..ff2c165 100644 --- a/config.go +++ b/config.go @@ -25,6 +25,8 @@ var ( KeyFile: "client-key.pem", InsecureSkipVerify: false, ExcludeMetrics: []string{}, + SkipExchanges: regexp.MustCompile("^$"), + IncludeExchanges: regexp.MustCompile(".*"), SkipQueues: regexp.MustCompile("^$"), IncludeQueues: regexp.MustCompile(".*"), SkipVHost: regexp.MustCompile("^$"), @@ -49,10 +51,14 @@ type rabbitExporterConfig struct { KeyFile string `json:"key_file"` InsecureSkipVerify bool `json:"insecure_skip_verify"` ExcludeMetrics []string `json:"exlude_metrics"` + SkipExchanges *regexp.Regexp `json:"-"` + IncludeExchanges *regexp.Regexp `json:"-"` SkipQueues *regexp.Regexp `json:"-"` IncludeQueues *regexp.Regexp `json:"-"` SkipVHost *regexp.Regexp `json:"-"` IncludeVHost *regexp.Regexp `json:"-"` + IncludeExchangesString string `json:"include_exchanges"` + SkipExchangesString string `json:"skip_exchanges"` IncludeQueuesString string `json:"include_queues"` SkipQueuesString string `json:"skip_queues"` SkipVHostString string `json:"skip_vhost"` @@ -91,6 +97,8 @@ func initConfigFromFile(configFile string) error { } } + config.SkipExchanges = regexp.MustCompile(config.SkipExchangesString) + config.IncludeExchanges = regexp.MustCompile(config.IncludeExchangesString) config.SkipQueues = regexp.MustCompile(config.SkipQueuesString) config.IncludeQueues = regexp.MustCompile(config.IncludeQueuesString) config.SkipVHost = regexp.MustCompile(config.SkipVHostString) @@ -173,6 +181,14 @@ func initConfig() { config.ExcludeMetrics = strings.Split(ExcludeMetrics, ",") } + if SkipExchanges := os.Getenv("SKIP_EXCHANGES"); SkipExchanges != "" { + config.SkipExchanges = regexp.MustCompile(SkipExchanges) + } + + if IncludeExchanges := os.Getenv("INCLUDE_EXCHANGES"); IncludeExchanges != "" { + config.IncludeExchanges = regexp.MustCompile(IncludeExchanges) + } + if SkipQueues := os.Getenv("SKIP_QUEUES"); SkipQueues != "" { config.SkipQueues = regexp.MustCompile(SkipQueues) } diff --git a/exporter_exchange.go b/exporter_exchange.go index 4acdc3b..a079b0a 100644 --- a/exporter_exchange.go +++ b/exporter_exchange.go @@ -62,6 +62,20 @@ func (e exporterExchange) Collect(ctx context.Context, ch chan<- prometheus.Metr for key, countvec := range e.exchangeMetrics { for _, exchange := range exchangeData { + ename := exchange.labels["name"] + vname := exchange.labels["vhost"] + if vhostIncluded := config.IncludeVHost.MatchString(vname); !vhostIncluded { + continue + } + if skipVhost := config.SkipVHost.MatchString(vname); skipVhost { + continue + } + if exchangeIncluded := config.IncludeExchanges.MatchString(ename); !exchangeIncluded { + continue + } + if exchangeSkipped := config.SkipExchanges.MatchString(ename); exchangeSkipped { + continue + } if value, ok := exchange.metrics[key]; ok { // log.WithFields(log.Fields{"vhost": exchange.vhost, "exchange": exchange.name, "key": key, "value": value}).Debug("Set exchange metric for key") ch <- prometheus.MustNewConstMetric(countvec, prometheus.CounterValue, value, cluster, exchange.labels["vhost"], exchange.labels["name"]) diff --git a/exporter_test.go b/exporter_test.go index 1a5dcd1..96db97a 100644 --- a/exporter_test.go +++ b/exporter_test.go @@ -15,9 +15,9 @@ import ( ) const ( - overviewTestData = `{"management_version":"3.5.1","rates_mode":"basic","exchange_types":[{"name":"topic","description":"AMQP topic exchange, as per the AMQP specification","enabled":true},{"name":"fanout","description":"AMQP fanout exchange, as per the AMQP specification","enabled":true},{"name":"direct","description":"AMQP direct exchange, as per the AMQP specification","enabled":true},{"name":"headers","description":"AMQP headers exchange, as per the AMQP specification","enabled":true}],"rabbitmq_version":"3.5.1","cluster_name":"my-rabbit@ae74c041248b","erlang_version":"17.5","erlang_full_version":"Erlang/OTP 17 [erts-6.4] [source] [64-bit] [smp:2:2] [async-threads:30] [kernel-poll:true]","message_stats":{},"queue_totals":{"messages":48,"messages_details":{"rate":0.0},"messages_ready":48,"messages_ready_details":{"rate":0.0},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0}},"object_totals":{"consumers":0,"queues":4,"exchanges":8,"connections":0,"channels":0},"statistics_db_event_queue":0,"node":"my-rabbit@ae74c041248b","statistics_db_node":"my-rabbit@ae74c041248b","listeners":[{"node":"my-rabbit@ae74c041248b","protocol":"amqp","ip_address":"::","port":5672},{"node":"my-rabbit@ae74c041248b","protocol":"clustering","ip_address":"::","port":25672}],"contexts":[{"node":"my-rabbit@ae74c041248b","description":"RabbitMQ Management","path":"/","port":"15672"}]}` + overviewTestData = `{"management_version":"3.5.1","rates_mode":"basic","exchange_types":[{"name":"topic","description":"AMQP topic exchange, as per the AMQP specification","enabled":true},{"name":"fanout","description":"AMQP fanout exchange, as per the AMQP specification","enabled":true},{"name":"direct","description":"AMQP direct exchange, as per the AMQP specification","enabled":true},{"name":"headers","description":"AMQP headers exchange, as per the AMQP specification","enabled":true}],"rabbitmq_version":"3.5.1","cluster_name":"my-rabbit@ae74c041248b","erlang_version":"17.5","erlang_full_version":"Erlang/OTP 17 [erts-6.4] [source] [64-bit] [smp:2:2] [async-threads:30] [kernel-poll:true]","message_stats":{},"queue_totals":{"messages":48,"messages_details":{"rate":0.0},"messages_ready":48,"messages_ready_details":{"rate":0.0},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0}},"object_totals":{"consumers":0,"queues":4,"exchanges":11,"connections":0,"channels":0},"statistics_db_event_queue":0,"node":"my-rabbit@ae74c041248b","statistics_db_node":"my-rabbit@ae74c041248b","listeners":[{"node":"my-rabbit@ae74c041248b","protocol":"amqp","ip_address":"::","port":5672},{"node":"my-rabbit@ae74c041248b","protocol":"clustering","ip_address":"::","port":25672}],"contexts":[{"node":"my-rabbit@ae74c041248b","description":"RabbitMQ Management","path":"/","port":"15672"}]}` queuesTestData = `[{"memory":16056,"message_stats":{"disk_writes":6,"disk_writes_details":{"rate":0.4},"publish":6,"publish_details":{"rate":0.4}},"messages":6,"messages_details":{"rate":0.4},"messages_ready":6,"messages_ready_details":{"rate":0.4},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0},"consumer_utilisation":"","policy":"","exclusive_consumer_tag":"","consumers":0,"recoverable_slaves":"","state":"flow","messages_ram":6,"messages_ready_ram":6,"messages_unacknowledged_ram":0,"messages_persistent":6,"message_bytes":30,"message_bytes_ready":30,"message_bytes_unacknowledged":0,"message_bytes_ram":30,"message_bytes_persistent":30,"disk_reads":0,"disk_writes":6,"backing_queue_status":{"q1":0,"q2":0,"delta":["delta","undefined",0,"undefined"],"q3":0,"q4":6,"len":6,"target_ram_count":"infinity","next_seq_id":6,"avg_ingress_rate":0.007658533940556533,"avg_egress_rate":0.0,"avg_ack_ingress_rate":0.0,"avg_ack_egress_rate":0.0},"name":"myQueue1","vhost":"/","durable":true,"auto_delete":false,"arguments":{},"node":"my-rabbit@ae74c041248b"},{"memory":55344,"message_stats":{"disk_reads":25,"disk_reads_details":{"rate":0.0}},"messages":25,"messages_details":{"rate":0.0},"messages_ready":25,"messages_ready_details":{"rate":0.0},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0},"idle_since":"2015-07-07 18:57:52","consumer_utilisation":"","policy":"ha-2","exclusive_consumer_tag":"","consumers":0,"recoverable_slaves":"","state":"running","messages_ram":25,"messages_ready_ram":25,"messages_unacknowledged_ram":0,"messages_persistent":25,"message_bytes":75,"message_bytes_ready":75,"message_bytes_unacknowledged":0,"message_bytes_ram":75,"message_bytes_persistent":75,"disk_reads":25,"disk_writes":0,"backing_queue_status":{"q1":0,"q2":0,"delta":["delta","undefined",0,"undefined"],"q3":24,"q4":1,"len":25,"target_ram_count":"infinity","next_seq_id":16384,"avg_ingress_rate":0.0,"avg_egress_rate":0.0,"avg_ack_ingress_rate":0.0,"avg_ack_egress_rate":0.0},"name":"myQueue2","vhost":"/","durable":true,"auto_delete":false,"arguments":{},"node":"my-rabbit@ae74c041248b"},{"memory":34648,"message_stats":{"disk_reads":23,"disk_reads_details":{"rate":0.0}},"messages":23,"messages_details":{"rate":0.0},"messages_ready":23,"messages_ready_details":{"rate":0.0},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0},"idle_since":"2015-07-07 18:57:52","consumer_utilisation":"","policy":"","exclusive_consumer_tag":"","consumers":0,"recoverable_slaves":"","state":"running","messages_ram":23,"messages_ready_ram":23,"messages_unacknowledged_ram":0,"messages_persistent":23,"message_bytes":207,"message_bytes_ready":207,"message_bytes_unacknowledged":0,"message_bytes_ram":207,"message_bytes_persistent":207,"disk_reads":23,"disk_writes":0,"backing_queue_status":{"q1":0,"q2":0,"delta":["delta","undefined",0,"undefined"],"q3":22,"q4":1,"len":23,"target_ram_count":"infinity","next_seq_id":16384,"avg_ingress_rate":0.0,"avg_egress_rate":0.0,"avg_ack_ingress_rate":0.0,"avg_ack_egress_rate":0.0},"name":"myQueue3","vhost":"/","durable":true,"auto_delete":false,"arguments":{},"node":"my-rabbit@ae74c041248b"},{"memory":13912,"messages":0,"messages_details":{"rate":0.0},"messages_ready":0,"messages_ready_details":{"rate":0.0},"messages_unacknowledged":0,"messages_unacknowledged_details":{"rate":0.0},"idle_since":"2015-07-07 18:57:52","consumer_utilisation":"","policy":"","exclusive_consumer_tag":"","consumers":0,"recoverable_slaves":"","state":"running","messages_ram":0,"messages_ready_ram":0,"messages_unacknowledged_ram":0,"messages_persistent":0,"message_bytes":0,"message_bytes_ready":0,"message_bytes_unacknowledged":0,"message_bytes_ram":0,"message_bytes_persistent":0,"disk_reads":0,"disk_writes":0,"backing_queue_status":{"q1":0,"q2":0,"delta":["delta","undefined",0,"undefined"],"q3":0,"q4":0,"len":0,"target_ram_count":"infinity","next_seq_id":0,"avg_ingress_rate":0.0,"avg_egress_rate":0.0,"avg_ack_ingress_rate":0.0,"avg_ack_egress_rate":0.0},"name":"myQueue4","vhost":"vhost4","durable":true,"auto_delete":false,"arguments":{},"node":"my-rabbit@ae74c041248b"}]` - exchangeAPIResponse = `[{"name":"","vhost":"/","type":"direct","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.direct","vhost":"/","type":"direct","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.fanout","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.headers","vhost":"/","type":"headers","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.match","vhost":"/","type":"headers","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.rabbitmq.log","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":true,"arguments":{}},{"name":"amq.rabbitmq.trace","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":true,"arguments":{}},{"name":"amq.topic","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"message_stats":{"publish":0,"publish_details":{"rate":0.0},"publish_in":5,"publish_in_details":{"rate":0.0},"publish_out":0,"publish_out_details":{"rate":0.0},"ack":0,"ack_details":{"rate":0.0},"deliver_get":0,"deliver_get_details":{"rate":0.0},"confirm":5,"confirm_details":{"rate":0.0},"return_unroutable":5,"return_unroutable_details":{"rate":0.0},"redeliver":0,"redeliver_details":{"rate":0.0}},"name":"myExchange","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}}]` + exchangeAPIResponse = `[{"name":"","vhost":"/","type":"direct","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.direct","vhost":"/","type":"direct","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.fanout","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.headers","vhost":"/","type":"headers","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.match","vhost":"/","type":"headers","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"name":"amq.rabbitmq.log","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":true,"arguments":{}},{"name":"amq.rabbitmq.trace","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":true,"arguments":{}},{"name":"amq.topic","vhost":"/","type":"topic","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"message_stats":{"publish":0,"publish_details":{"rate":0.0},"publish_in":5,"publish_in_details":{"rate":0.0},"publish_out":0,"publish_out_details":{"rate":0.0},"ack":0,"ack_details":{"rate":0.0},"deliver_get":0,"deliver_get_details":{"rate":0.0},"confirm":5,"confirm_details":{"rate":0.0},"return_unroutable":5,"return_unroutable_details":{"rate":0.0},"redeliver":0,"redeliver_details":{"rate":0.0}},"name":"myExchange","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"message_stats":{"publish":0,"publish_details":{"rate":0.0},"publish_in":5,"publish_in_details":{"rate":0.0},"publish_out":0,"publish_out_details":{"rate":0.0},"ack":0,"ack_details":{"rate":0.0},"deliver_get":0,"deliver_get_details":{"rate":0.0},"confirm":5,"confirm_details":{"rate":0.0},"return_unroutable":5,"return_unroutable_details":{"rate":0.0},"redeliver":0,"redeliver_details":{"rate":0.0}},"name":"myExchange2","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"message_stats":{"publish":0,"publish_details":{"rate":0.0},"publish_in":5,"publish_in_details":{"rate":0.0},"publish_out":0,"publish_out_details":{"rate":0.0},"ack":0,"ack_details":{"rate":0.0},"deliver_get":0,"deliver_get_details":{"rate":0.0},"confirm":5,"confirm_details":{"rate":0.0},"return_unroutable":5,"return_unroutable_details":{"rate":0.0},"redeliver":0,"redeliver_details":{"rate":0.0}},"name":"myExchange3","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}},{"message_stats":{"publish":0,"publish_details":{"rate":0.0},"publish_in":5,"publish_in_details":{"rate":0.0},"publish_out":0,"publish_out_details":{"rate":0.0},"ack":0,"ack_details":{"rate":0.0},"deliver_get":0,"deliver_get_details":{"rate":0.0},"confirm":5,"confirm_details":{"rate":0.0},"return_unroutable":5,"return_unroutable_details":{"rate":0.0},"redeliver":0,"redeliver_details":{"rate":0.0}},"name":"myExchange4","vhost":"/","type":"fanout","durable":true,"auto_delete":false,"internal":false,"arguments":{}}]` nodesAPIResponse = `[{"mem_used":150456032,"mem_used_details":{"rate":25176},"fd_used":55,"fd_used_details":{"rate":0},"sockets_used":0,"sockets_used_details":{"rate":0},"proc_used":226,"proc_used_details":{"rate":0},"disk_free":189045161984,"disk_free_details":{"rate":0},"partitions":["rabbit@ribbit-0","rabbit@ribbit-1","rabbit@ribbit-3","rabbit@ribbit-4"],"os_pid":"113","fd_total":1048576,"sockets_total":943626,"mem_limit":838395494,"mem_alarm":false,"disk_free_limit":50000000,"disk_free_alarm":false,"proc_total":1048576,"rates_mode":"basic","uptime":3772165,"run_queue":0,"processors":4,"name":"my-rabbit@5a00cd8fe2f4","type":"disc","running":true}]` connectionAPIResponse = `[{"auth_mechanism": "PLAIN","channel_max": 65535,"channels": 1,"client_properties": {"copyright": "Copyright (c) 2007-2014 VMWare Inc, Tony Garnock-Jones, and Alan Antonuk.","information": "See https://github.com/alanxz/rabbitmq-c","platform": "linux-gn","product": "rabbitmq-c","version": "0.5.3-pre"},"connected_at": 1501868641834,"frame_max": 131072,"garbage_collection": {"fullsweep_after": 65535,"min_bin_vheap_size": 46422,"min_heap_size": 233,"minor_gcs": 3},"host": "172.31.15.10","name": "172.31.0.130:32769 -> 172.31.15.10:5672","node": "my-rabbit@ae74c041248b","peer_cert_issuer": null,"peer_cert_subject": null,"peer_cert_validity": null,"peer_host": "172.31.0.130","peer_port": 32769,"port": 5672,"protocol": "AMQP 0-9-1","recv_cnt": 22708,"recv_oct": 8905713,"recv_oct_details": {"rate": 169.6},"reductions": 6257210,"reductions_details": {"rate": 148.8},"send_cnt": 6,"send_oct": 573,"send_oct_details": {"rate": 0.0},"send_pend": 0,"ssl": false,"ssl_cipher": null,"ssl_hash": null,"ssl_key_exchange": null,"ssl_protocol": null,"state": "running","timeout": 0,"type": "network","user": "rmq_oms","vhost": "/"},{"auth_mechanism": "PLAIN","channel_max": 65535,"channels": 1,"client_properties": {"copyright": "Copyright (c) 2007-2014 VMWare Inc, Tony Garnock-Jones, and Alan Antonuk.","information": "See https://github.com/alanxz/rabbitmq-c","platform": "linux-gn","product": "rabbitmq-c","version": "0.5.3-pre"},"connected_at": 1501868641834,"frame_max": 131072,"garbage_collection": {"fullsweep_after": 65535,"min_bin_vheap_size": 46422,"min_heap_size": 233,"minor_gcs": 3},"host": "172.31.15.10","name": "172.31.0.130:32769 -> 172.31.15.10:5672","node": "rabbit@rmq-cluster-node-04","peer_cert_issuer": null,"peer_cert_subject": null,"peer_cert_validity": null,"peer_host": "172.31.0.130","peer_port": 32769,"port": 5672,"protocol": "AMQP 0-9-1","recv_cnt": 22708,"recv_oct": 8905713,"recv_oct_details": {"rate": 169.6},"reductions": 6257210,"reductions_details": {"rate": 148.8},"send_cnt": 6,"send_oct": 573,"send_oct_details": {"rate": 0.0},"send_pend": 0,"ssl": false,"ssl_cipher": null,"ssl_hash": null,"ssl_key_exchange": null,"ssl_protocol": null,"state": "running","timeout": 0,"type": "network","user": "rmq_oms","vhost": "/"}]` shovelAPIResponse = `[{"node":"my-rabbit@4a6df52ebc2a","timestamp":"2019-04-23 10:32:08","name":"test-shovel","vhost":"/","type":"dynamic","state":"terminated","reason":"{failed_to_connect_using_provided_uris,\n [{rabbit_amqp091_shovel,make_conn_and_chan,2,\n [{file,\"src/rabbit_amqp091_shovel.erl\"},{line,324}]},\n {rabbit_amqp091_shovel,connect_source,1,\n [{file,\"src/rabbit_amqp091_shovel.erl\"},{line,78}]},\n {rabbit_shovel_worker,handle_cast,2,\n [{file,\"src/rabbit_shovel_worker.erl\"},{line,64}]},\n {gen_server2,handle_msg,2,[{file,\"src/gen_server2.erl\"},{line,1056}]},\n {proc_lib,init_p_do_apply,3,[{file,\"proc_lib.erl\"},{line,249}]}]}"},{"node":"my-rabbit@ae74c041248b","timestamp":"2019-04-17 1:01:11","name":"ADMIN-3779-1","vhost":"/","type":"dynamic","state":"running","src_uri":"amqp://","src_protocol":"amqp091","dest_protocol":"amqp091","dest_uri":"amqps://rabbitmq.example.com:5671/dev-1","src_exchange":"test.exchange","src_exchange_key":"EVENT_SNAPSHOT.#","dest_exchange":"test.event.snapshot.v1"}]` @@ -88,13 +88,13 @@ func TestWholeApp(t *testing.T) { body := w.Body.String() t.Log(body) lines := strings.Split(body, "\n") - if lc := len(lines); lc != 369 { - t.Errorf("expected 369 lines, got %d", lc) + if lc := len(lines); lc != 390 { + t.Errorf("expected 390 lines, got %d", lc) } expectSubstring(t, body, `rabbitmq_up{cluster="my-rabbit@ae74c041248b",node="my-rabbit@ae74c041248b"} 1`) // overview - expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 8`) + expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 11`) expectSubstring(t, body, `rabbitmq_queues{cluster="my-rabbit@ae74c041248b"} 4`) expectSubstring(t, body, `rabbitmq_queue_messages_global{cluster="my-rabbit@ae74c041248b"} 48`) expectSubstring(t, body, `rabbitmq_queue_messages_ready_global{cluster="my-rabbit@ae74c041248b"} 48`) @@ -146,7 +146,7 @@ func TestWholeAppInverted(t *testing.T) { expectSubstring(t, body, `rabbitmq_up{cluster="my-rabbit@ae74c041248b",node="my-rabbit@ae74c041248b"} 1`) // overview is always scraped and exported - expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 8`) + expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 11`) expectSubstring(t, body, `rabbitmq_queues{cluster="my-rabbit@ae74c041248b"} 4`) expectSubstring(t, body, `rabbitmq_queue_messages_global{cluster="my-rabbit@ae74c041248b"} 48`) expectSubstring(t, body, `rabbitmq_queue_messages_ready_global{cluster="my-rabbit@ae74c041248b"} 48`) @@ -197,7 +197,7 @@ func TestAppMaxQueues(t *testing.T) { expectSubstring(t, body, `rabbitmq_up{cluster="my-rabbit@ae74c041248b",node="my-rabbit@ae74c041248b"} 1`) // overview - expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 8`) + expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 11`) expectSubstring(t, body, `rabbitmq_queues{cluster="my-rabbit@ae74c041248b"} 4`) expectSubstring(t, body, `rabbitmq_queue_messages_global{cluster="my-rabbit@ae74c041248b"} 48`) expectSubstring(t, body, `rabbitmq_queue_messages_ready_global{cluster="my-rabbit@ae74c041248b"} 48`) @@ -313,7 +313,7 @@ func TestResetMetricsOnRabbitFailure(t *testing.T) { expectSubstring(t, body, `rabbitmq_module_up{cluster="my-rabbit@ae74c041248b",module="connections",node="my-rabbit@ae74c041248b"} 1`) // overview - expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 8`) + expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 11`) expectSubstring(t, body, `rabbitmq_queues{cluster="my-rabbit@ae74c041248b"} 4`) expectSubstring(t, body, `rabbitmq_queue_messages_global{cluster="my-rabbit@ae74c041248b"} 48`) expectSubstring(t, body, `rabbitmq_queue_messages_ready_global{cluster="my-rabbit@ae74c041248b"} 48`) @@ -356,7 +356,7 @@ func TestResetMetricsOnRabbitFailure(t *testing.T) { expectSubstring(t, body, `rabbitmq_module_up{cluster="my-rabbit@ae74c041248b",module="connections",node="my-rabbit@ae74c041248b"} 1`) // overview - expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 8`) + expectSubstring(t, body, `rabbitmq_exchanges{cluster="my-rabbit@ae74c041248b"} 11`) expectSubstring(t, body, `rabbitmq_queues{cluster="my-rabbit@ae74c041248b"} 4`) expectSubstring(t, body, `rabbitmq_queue_messages_global{cluster="my-rabbit@ae74c041248b"} 48`) expectSubstring(t, body, `rabbitmq_queue_messages_ready_global{cluster="my-rabbit@ae74c041248b"} 48`) @@ -444,7 +444,7 @@ func TestExporter(t *testing.T) { `rabbitmq_queue_messages_ready{cluster="my-rabbit@ae74c041248b",durable="true",policy="ha-2",queue="myQueue2",self="1",vhost="/"} 25`, }, dontExpect: []string{}, - lines: 398, + lines: 419, }, { name: "Include specific queue", @@ -494,6 +494,47 @@ func TestExporter(t *testing.T) { `rabbitmq_queue_messages_published_total{cluster="my-rabbit@ae74c041248b",durable="true",policy="",queue="myQueue4",self="1",vhost="vhost4"} 0`, }, }, + { + name: "Include specific exchange", + setup: func() { + config.IncludeExchanges = regexp.MustCompile("^myExchange$") + }, + expect: []string{ + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange",vhost="/"} 0`, + }, + dontExpect: []string{ + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange2",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange3",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange4",vhost="/"} 0`, + }, + }, + { + name: "IncludeExchanges (Substring)", + setup: func() { + config.IncludeExchanges = regexp.MustCompile("Exchange") + }, + expect: []string{ + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange2",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange3",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange4",vhost="/"} 0`, + }, + dontExpect: []string{}, + }, + { + name: "Skip exchanges (Substring)", + setup: func() { + config.SkipExchanges = regexp.MustCompile("[3-4]") + }, + expect: []string{ + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange2",vhost="/"} 0`, + }, + dontExpect: []string{ + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange3",vhost="/"} 0`, + `rabbitmq_exchange_messages_published_total{cluster="my-rabbit@ae74c041248b",exchange="myExchange4",vhost="/"} 0`, + }, + }, } for _, tt := range tests { diff --git a/main.go b/main.go index 73094ee..e240a85 100644 --- a/main.go +++ b/main.go @@ -72,6 +72,8 @@ func main() { "KEYFILE": config.KeyFile, "SKIPVERIFY": config.InsecureSkipVerify, "EXCLUDE_METRICS": config.ExcludeMetrics, + "SKIP_EXCHANGES": config.SkipExchanges.String(), + "INCLUDE_EXCHANGES": config.IncludeExchanges.String(), "SKIP_QUEUES": config.SkipQueues.String(), "INCLUDE_QUEUES": config.IncludeQueues.String(), "SKIP_VHOST": config.SkipVHost.String(), diff --git a/rabbitClient_test.go b/rabbitClient_test.go index 1086cab..d8c768b 100644 --- a/rabbitClient_test.go +++ b/rabbitClient_test.go @@ -101,7 +101,7 @@ func TestExchanges(t *testing.T) { exchanges, err := getStatsInfo(*config, "exchanges", exchangeLabelKeys) expect(t, err, nil) - expect(t, len(exchanges), 9) + expect(t, len(exchanges), 12) expect(t, exchanges[0].labels["name"], "") expect(t, exchanges[0].labels["vhost"], "/") expect(t, exchanges[1].labels["name"], "amq.direct")