newrelic_f5_plugin 1.0.15 → 1.0.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: f4de3101ffe13d4eeb48b77722e6d0ede0d22ad6
4
- data.tar.gz: 209080c82f5e16c92bacb4d35c204404d02865cb
3
+ metadata.gz: 6b7cc8b0330af44b1a00392f0d9dc7a048c0ce79
4
+ data.tar.gz: 0aab0890155622be2e12ab0ba2263cb7593f1ba7
5
5
  SHA512:
6
- metadata.gz: 5796767f4c3461ff54ac392c3e6efde4d744fadf5d3b7f2743ce50345221d49cb40261309d7d10efce038a73e9f98197a346b3fa63c3c3119f13f81ad6daa6f1
7
- data.tar.gz: 96db6ecf6410ae9a21a6bccfafb007cd44b6dc22e4e65cf0d9ec3b996d059147a76b9402b4ddd2b7b350e4845aa7b1663c386f532f8ec54673ceb2e6da0a8322
6
+ metadata.gz: dd8e326a708d65cf0f2f799328fe2802e059154d531e10317385234b67c1b4abfa495cf6e7010fbe891e044903565268e3d7f5d52d3b03de4113c1e227fd53c5
7
+ data.tar.gz: aa3406c4791ab4ffe72ef4a7b15eedd04d7f0797c636938fd06aa0e148222daf3bf121264db28f79b0af3533aa3ba87681389ed368152f3c134efa25cefc5db5
data/CHANGES CHANGED
@@ -1,3 +1,12 @@
1
+ * 1.0.16
2
+ - Added Interface statistics
3
+ - State
4
+ - Throughput
5
+ - Packets per second (Unicast/Multicast)
6
+ - Errors per second
7
+ - Dropped packets per second
8
+ - Collisions per second
9
+
1
10
  * 1.0.15
2
11
  - Fix bug in 1.0.14 where pool data collection was multiplied by 8 twice
3
12
 
data/README.rdoc CHANGED
@@ -14,6 +14,14 @@ Device wide Metrics
14
14
  * TCP Details (Current connections, connection rate, Server/Client side, Wait State)
15
15
  * Node status
16
16
 
17
+ Interface Statistics
18
+ * State (Up/Down)
19
+ * Throughput
20
+ * Packets per Second (Unicast / Multicast)
21
+ * Errors per Second
22
+ * Dropped packets per Second
23
+ * Collisions per Second
24
+
17
25
  Virtual Server Statistics
18
26
  * Requests per Second
19
27
  * Current Connections
@@ -2,6 +2,7 @@ require 'rubygems'
2
2
  require 'newrelic_f5_plugin/util'
3
3
  require 'newrelic_f5_plugin/client_ssl'
4
4
  require 'newrelic_f5_plugin/device'
5
+ require 'newrelic_f5_plugin/interfaces'
5
6
  require 'newrelic_f5_plugin/nodes'
6
7
  require 'newrelic_f5_plugin/pools'
7
8
  require 'newrelic_f5_plugin/rules'
@@ -4,7 +4,7 @@ require 'newrelic_plugin'
4
4
  require 'snmp'
5
5
 
6
6
  module NewRelic::F5Plugin
7
- VERSION = '1.0.15'
7
+ VERSION = '1.0.16'
8
8
 
9
9
  # Register and run the agent
10
10
  def self.run
@@ -77,6 +77,11 @@ module NewRelic::F5Plugin
77
77
  @system ||= NewRelic::F5Plugin::Device.new
78
78
  @system.poll(self, snmp)
79
79
 
80
+ # Device Interface metrics
81
+ NewRelic::PlatformLogger.debug("Collecting Interface stats")
82
+ @interfaces ||= NewRelic::F5Plugin::Interfaces.new
83
+ @interfaces.poll(self, snmp)
84
+
80
85
  # Node stats
81
86
  NewRelic::PlatformLogger.debug("Collecting Node stats")
82
87
  @nodes ||= NewRelic::F5Plugin::Nodes.new
@@ -0,0 +1,381 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'newrelic_plugin'
4
+ require 'snmp'
5
+
6
+ # sysInterfaceEntry
7
+ # sysInterfaceName LongDisplayString,
8
+ # sysInterfaceMediaMaxSpeed Integer32,
9
+ # sysInterfaceMediaMaxDuplex INTEGER,
10
+ # sysInterfaceMediaActiveSpeed Integer32,
11
+ # sysInterfaceMediaActiveDuplex INTEGER,
12
+ # sysInterfaceMacAddr MacAddress,
13
+ # sysInterfaceMtu Integer32,
14
+ # sysInterfaceEnabled INTEGER,
15
+ # sysInterfaceLearnMode INTEGER,
16
+ # sysInterfaceFlowCtrlReq INTEGER,
17
+ # sysInterfaceStpLink INTEGER,
18
+ # sysInterfaceStpEdge INTEGER,
19
+ # sysInterfaceStpEdgeActive INTEGER,
20
+ # sysInterfaceStpAuto INTEGER,
21
+ # sysInterfaceStpEnable INTEGER,
22
+ # sysInterfaceStpReset INTEGER,
23
+ # sysInterfaceStatus INTEGER,
24
+ # sysInterfaceComboPort INTEGER,
25
+ # sysInterfacePreferSfp INTEGER,
26
+ # sysInterfaceSfpMedia INTEGER,
27
+ # sysInterfacePhyMaster INTEGER
28
+
29
+ # sysInterfaceStatEntry
30
+ # sysInterfaceStatName LongDisplayString,
31
+ # sysInterfaceStatPktsIn Counter64,
32
+ # sysInterfaceStatBytesIn Counter64,
33
+ # sysInterfaceStatPktsOut Counter64,
34
+ # sysInterfaceStatBytesOut Counter64,
35
+ # sysInterfaceStatMcastIn Counter64,
36
+ # sysInterfaceStatMcastOut Counter64,
37
+ # sysInterfaceStatErrorsIn Counter64,
38
+ # sysInterfaceStatErrorsOut Counter64,
39
+ # sysInterfaceStatDropsIn Counter64,
40
+ # sysInterfaceStatDropsOut Counter64,
41
+ # sysInterfaceStatCollisions Counter64,
42
+ # sysInterfaceStatPauseActive INTEGER
43
+
44
+ module NewRelic
45
+ module F5Plugin
46
+
47
+ class Interfaces
48
+ attr_accessor :names, :snmp_manager
49
+
50
+ INTERFACE_ENABLED_STATES = {
51
+ 0 => 'Disabled',
52
+ 1 => 'Enabled',
53
+ }
54
+ INTERFACE_STATUS_STATES = {
55
+ 0 => 'Up',
56
+ 1 => 'Down',
57
+ 3 => 'Uninitialized',
58
+ 5 => 'Unpopulated',
59
+ }
60
+ INTERFACE_DUPLEX_STATES = {
61
+ 0 => 'None',
62
+ 1 => 'Half',
63
+ 2 => 'Full',
64
+ }
65
+
66
+ OID_SYS_INTERFACES = "1.3.6.1.4.1.3375.2.1.2.4"
67
+
68
+ # Config
69
+ OID_SYS_INTERFACE = "#{OID_SYS_INTERFACES}.1"
70
+ OID_SYS_INTERFACE_ENTRY = "#{OID_SYS_INTERFACE}.2.1"
71
+
72
+ OID_SYS_INTERFACE_NAME = "#{OID_SYS_INTERFACE_ENTRY}.1"
73
+ OID_SYS_INTERFACE_MEDIA_MAX_SPEED = "#{OID_SYS_INTERFACE_ENTRY}.2"
74
+ OID_SYS_INTERFACE_MEDIA_MAX_DUPLEX = "#{OID_SYS_INTERFACE_ENTRY}.3"
75
+ OID_SYS_INTERFACE_MEDIA_ACTIVE_SPEED = "#{OID_SYS_INTERFACE_ENTRY}.4"
76
+ OID_SYS_INTERFACE_MEDIA_ACTIVE_DUPLEX = "#{OID_SYS_INTERFACE_ENTRY}.5"
77
+ OID_SYS_INTERFACE_MAC_ADDR = "#{OID_SYS_INTERFACE_ENTRY}.6"
78
+ OID_SYS_INTERFACE_MTU = "#{OID_SYS_INTERFACE_ENTRY}.7"
79
+ OID_SYS_INTERFACE_ENABLED = "#{OID_SYS_INTERFACE_ENTRY}.8"
80
+ OID_SYS_INTERFACE_STATUS = "#{OID_SYS_INTERFACE_ENTRY}.17"
81
+
82
+ # Stats
83
+ OID_SYS_INTERFACE_STAT = "#{OID_SYS_INTERFACES}.4"
84
+ OID_SYS_INTERFACE_STAT_ENTRY = "#{OID_SYS_INTERFACE_STAT}.3.1"
85
+
86
+ OID_SYS_INTERFACE_STAT_NAME = "#{OID_SYS_INTERFACE_STAT_ENTRY}.1"
87
+ OID_SYS_INTERFACE_STAT_PKTS_IN = "#{OID_SYS_INTERFACE_STAT_ENTRY}.2"
88
+ OID_SYS_INTERFACE_STAT_BYTES_IN = "#{OID_SYS_INTERFACE_STAT_ENTRY}.3"
89
+ OID_SYS_INTERFACE_STAT_PKTS_OUT = "#{OID_SYS_INTERFACE_STAT_ENTRY}.4"
90
+ OID_SYS_INTERFACE_STAT_BYTES_OUT = "#{OID_SYS_INTERFACE_STAT_ENTRY}.5"
91
+ OID_SYS_INTERFACE_STAT_MCAST_IN = "#{OID_SYS_INTERFACE_STAT_ENTRY}.6"
92
+ OID_SYS_INTERFACE_STAT_MCAST_OUT = "#{OID_SYS_INTERFACE_STAT_ENTRY}.7"
93
+ OID_SYS_INTERFACE_STAT_ERRORS_IN = "#{OID_SYS_INTERFACE_STAT_ENTRY}.8"
94
+ OID_SYS_INTERFACE_STAT_ERRORS_OUT = "#{OID_SYS_INTERFACE_STAT_ENTRY}.9"
95
+ OID_SYS_INTERFACE_STAT_DROPS_IN = "#{OID_SYS_INTERFACE_STAT_ENTRY}.10"
96
+ OID_SYS_INTERFACE_STAT_DROPS_OUT = "#{OID_SYS_INTERFACE_STAT_ENTRY}.11"
97
+ OID_SYS_INTERFACE_STAT_COLLISIONS = "#{OID_SYS_INTERFACE_STAT_ENTRY}.12"
98
+
99
+
100
+
101
+ #
102
+ # Init
103
+ #
104
+ def initialize(snmp = nil)
105
+ @names = [ ]
106
+
107
+ if snmp
108
+ @snmp_manager = snmp
109
+ else
110
+ @snmp_manager = nil
111
+ end
112
+ end
113
+
114
+
115
+
116
+ #
117
+ # Perform polling and reportings of metrics
118
+ #
119
+ def poll(agent, snmp)
120
+ @snmp_manager = snmp
121
+
122
+ unless get_names.empty?
123
+ throughput_in = get_throughput_in
124
+ throughput_in.each_key { |m| agent.report_counter_metric m, "bits/sec", throughput_in[m] } unless throughput_in.nil?
125
+
126
+ throughput_out = get_throughput_out
127
+ throughput_out.each_key { |m| agent.report_counter_metric m, "bits/sec", throughput_out[m] } unless throughput_out.nil?
128
+
129
+ packets_in = get_packets_in
130
+ packets_in.each_key { |m| agent.report_counter_metric m, "pkts/sec", packets_in[m] } unless packets_in.nil?
131
+
132
+ packets_out = get_packets_out
133
+ packets_out.each_key { |m| agent.report_counter_metric m, "pkts/sec", packets_out[m] } unless packets_out.nil?
134
+
135
+ mcast_in = get_mcast_in
136
+ mcast_in.each_key { |m| agent.report_counter_metric m, "pkts/sec", mcast_in[m] } unless mcast_in.nil?
137
+
138
+ mcast_out = get_mcast_out
139
+ mcast_out.each_key { |m| agent.report_counter_metric m, "pkts/sec", mcast_out[m] } unless mcast_out.nil?
140
+
141
+ errors_in = get_errors_in
142
+ errors_in.each_key { |m| agent.report_counter_metric m, "errors/sec", errors_in[m] } unless errors_in.nil?
143
+
144
+ errors_out = get_errors_out
145
+ errors_out.each_key { |m| agent.report_counter_metric m, "errors/sec", errors_out[m] } unless errors_out.nil?
146
+
147
+ drops_in = get_drops_in
148
+ drops_in.each_key { |m| agent.report_counter_metric m, "drops/sec", drops_in[m] } unless drops_in.nil?
149
+
150
+ drops_out = get_drops_out
151
+ drops_out.each_key { |m| agent.report_counter_metric m, "drops/sec", drops_out[m] } unless drops_out.nil?
152
+
153
+ collisions = get_collisions
154
+ collisions.each_key { |m| agent.report_counter_metric m, "collisions/sec", collisions[m] } unless collisions.nil?
155
+
156
+ status = get_status
157
+ status.each_key { |m| agent.report_metric m, status[m][:label], status[m][:count] } unless status.nil?
158
+ end
159
+ end
160
+
161
+
162
+
163
+ #
164
+ # Get the list of Interface names
165
+ #
166
+ def get_names(snmp = nil)
167
+ snmp = snmp_manager unless snmp
168
+
169
+ if snmp
170
+ @names.clear
171
+
172
+ begin
173
+ snmp.walk([OID_SYS_INTERFACE_NAME]) do |row|
174
+ row.each do |vb|
175
+ @names.push(vb.value)
176
+ end
177
+ end
178
+ rescue Exception => e
179
+ NewRelic::PlatformLogger.error("Unable to gather Interface names with error: #{e}")
180
+ end
181
+
182
+ NewRelic::PlatformLogger.debug("Interfaces: Found #{@names.size} interfaces")
183
+ return @names
184
+ end
185
+ end
186
+
187
+
188
+
189
+ #
190
+ # Gather Throughput Inbound (returns in bits)
191
+ #
192
+ def get_throughput_in(snmp = nil)
193
+ snmp = snmp_manager unless snmp
194
+
195
+ get_names(snmp) if @names.empty?
196
+ res = gather_snmp_metrics_by_name("Interfaces/Throughput/In", @names, OID_SYS_INTERFACE_STAT_BYTES_IN, snmp)
197
+ res = res.each_key { |n| res[n] *= 8 }
198
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Inbound Throughput metrics")
199
+ return res
200
+ end
201
+
202
+
203
+
204
+ #
205
+ # Gather Throughput Inbound (returns in bits)
206
+ #
207
+ def get_throughput_out(snmp = nil)
208
+ snmp = snmp_manager unless snmp
209
+
210
+ get_names(snmp) if @names.empty?
211
+ res = gather_snmp_metrics_by_name("Interfaces/Throughput/Out", @names, OID_SYS_INTERFACE_STAT_BYTES_OUT, snmp)
212
+ res = res.each_key { |n| res[n] *= 8 }
213
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Outbound Throughput metrics")
214
+ return res
215
+ end
216
+
217
+
218
+
219
+ #
220
+ # Gather Packets Inbound
221
+ #
222
+ def get_packets_in(snmp = nil)
223
+ snmp = snmp_manager unless snmp
224
+
225
+ get_names(snmp) if @names.empty?
226
+ res = gather_snmp_metrics_by_name("Interfaces/Packets/In", @names, OID_SYS_INTERFACE_STAT_PKTS_IN, snmp)
227
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Inbound packet metrics")
228
+ return res
229
+ end
230
+
231
+
232
+
233
+ #
234
+ # Gather Packets Outbound
235
+ #
236
+ def get_packets_out(snmp = nil)
237
+ snmp = snmp_manager unless snmp
238
+
239
+ get_names(snmp) if @names.empty?
240
+ res = gather_snmp_metrics_by_name("Interfaces/Packets/Out", @names, OID_SYS_INTERFACE_STAT_PKTS_OUT, snmp)
241
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Outbound packet metrics")
242
+ return res
243
+ end
244
+
245
+
246
+
247
+ #
248
+ # Gather Multicast Packets Inbound
249
+ #
250
+ def get_mcast_in(snmp = nil)
251
+ snmp = snmp_manager unless snmp
252
+
253
+ get_names(snmp) if @names.empty?
254
+ res = gather_snmp_metrics_by_name("Interfaces/Multicast/In", @names, OID_SYS_INTERFACE_STAT_MCAST_IN, snmp)
255
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Inbound multicast metrics")
256
+ return res
257
+ end
258
+
259
+
260
+
261
+ #
262
+ # Gather Multicast Packets Outbound
263
+ #
264
+ def get_mcast_out(snmp = nil)
265
+ snmp = snmp_manager unless snmp
266
+
267
+ get_names(snmp) if @names.empty?
268
+ res = gather_snmp_metrics_by_name("Interfaces/Multicast/Out", @names, OID_SYS_INTERFACE_STAT_MCAST_OUT, snmp)
269
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Outbound multicast metrics")
270
+ return res
271
+ end
272
+
273
+
274
+
275
+ #
276
+ # Gather Errors Inbound
277
+ #
278
+ def get_errors_in(snmp = nil)
279
+ snmp = snmp_manager unless snmp
280
+
281
+ get_names(snmp) if @names.empty?
282
+ res = gather_snmp_metrics_by_name("Interfaces/Errors/In", @names, OID_SYS_INTERFACE_STAT_ERRORS_IN, snmp)
283
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Inbound error metrics")
284
+ return res
285
+ end
286
+
287
+
288
+
289
+ #
290
+ # Gather Errors Outbound
291
+ #
292
+ def get_errors_out(snmp = nil)
293
+ snmp = snmp_manager unless snmp
294
+
295
+ get_names(snmp) if @names.empty?
296
+ res = gather_snmp_metrics_by_name("Interfaces/Errors/Out", @names, OID_SYS_INTERFACE_STAT_ERRORS_OUT, snmp)
297
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Outbound error metrics")
298
+ return res
299
+ end
300
+
301
+
302
+
303
+ #
304
+ # Gather Drops Inbound
305
+ #
306
+ def get_drops_in(snmp = nil)
307
+ snmp = snmp_manager unless snmp
308
+
309
+ get_names(snmp) if @names.empty?
310
+ res = gather_snmp_metrics_by_name("Interfaces/Drops/In", @names, OID_SYS_INTERFACE_STAT_DROPS_IN, snmp)
311
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Inbound drop metrics")
312
+ return res
313
+ end
314
+
315
+
316
+
317
+ #
318
+ # Gather Drops Outbound
319
+ #
320
+ def get_drops_out(snmp = nil)
321
+ snmp = snmp_manager unless snmp
322
+
323
+ get_names(snmp) if @names.empty?
324
+ res = gather_snmp_metrics_by_name("Interfaces/Drops/Out", @names, OID_SYS_INTERFACE_STAT_DROPS_OUT, snmp)
325
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Outbound drop metrics")
326
+ return res
327
+ end
328
+
329
+
330
+
331
+ #
332
+ # Gather Collisions
333
+ #
334
+ def get_collisions(snmp = nil)
335
+ snmp = snmp_manager unless snmp
336
+
337
+ get_names(snmp) if @names.empty?
338
+ res = gather_snmp_metrics_by_name("Interfaces/Collisions", @names, OID_SYS_INTERFACE_STAT_COLLISIONS, snmp)
339
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{res.size}/#{@names.size} Collision metrics")
340
+ return res
341
+ end
342
+
343
+
344
+
345
+ #
346
+ # Gather Interface Status
347
+ #
348
+ def get_status(snmp = nil)
349
+ snmp = snmp_manager unless snmp
350
+ metrics = { }
351
+ counter = 0
352
+
353
+ if snmp
354
+ # Init all the states with zeros so we always get them
355
+ base_name = "Interfaces/Status"
356
+ INTERFACE_STATUS_STATES.each do |key,value|
357
+ metrics["#{base_name}/#{value}"] = { :label => "interfaces", :count => 0 }
358
+ end
359
+
360
+ # ltmNodeAddrMonitorStatus
361
+ begin
362
+ snmp.walk([OID_SYS_INTERFACE_STATUS]) do |row|
363
+ row.each do |vb|
364
+ metric_name = "#{base_name}/#{INTERFACE_STATUS_STATES[vb.value.to_i]}"
365
+ metrics[metric_name][:count] += 1
366
+ counter += 1
367
+ end
368
+ end
369
+ rescue Exception => e
370
+ NewRelic::PlatformLogger.error("Unable to gather Interface status metrics with error: #{e}")
371
+ end
372
+ end
373
+
374
+ NewRelic::PlatformLogger.debug("Interfaces: Got #{counter} Status metrics")
375
+ return metrics
376
+ end
377
+
378
+ end
379
+ end
380
+ end
381
+
@@ -13,8 +13,8 @@ Gem::Specification.new do |s|
13
13
  ## If your rubyforge_project name is different, then edit it and comment out
14
14
  ## the sub! line in the Rakefile
15
15
  s.name = 'newrelic_f5_plugin'
16
- s.version = '1.0.15'
17
- s.date = '2014-07-07'
16
+ s.version = '1.0.16'
17
+ s.date = '2014-08-18'
18
18
  s.rubyforge_project = 'newrelic_f5_plugin'
19
19
  s.licenses = ['MIT']
20
20
 
@@ -78,6 +78,7 @@ to find out how to install and run the plugin agent.
78
78
  lib/newrelic_f5_plugin/agent.rb
79
79
  lib/newrelic_f5_plugin/client_ssl.rb
80
80
  lib/newrelic_f5_plugin/device.rb
81
+ lib/newrelic_f5_plugin/interfaces.rb
81
82
  lib/newrelic_f5_plugin/nodes.rb
82
83
  lib/newrelic_f5_plugin/pools.rb
83
84
  lib/newrelic_f5_plugin/rules.rb
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: newrelic_f5_plugin
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.15
4
+ version: 1.0.16
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jonathan Thurman
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-07-07 00:00:00.000000000 Z
11
+ date: 2014-08-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: newrelic_plugin
@@ -73,6 +73,7 @@ files:
73
73
  - lib/newrelic_f5_plugin/agent.rb
74
74
  - lib/newrelic_f5_plugin/client_ssl.rb
75
75
  - lib/newrelic_f5_plugin/device.rb
76
+ - lib/newrelic_f5_plugin/interfaces.rb
76
77
  - lib/newrelic_f5_plugin/nodes.rb
77
78
  - lib/newrelic_f5_plugin/pools.rb
78
79
  - lib/newrelic_f5_plugin/rules.rb