zabbix_nudge 0.1.3

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,79 @@
1
+ require "zabbix_nudge/version"
2
+ require "active_support/core_ext/string/inflections.rb"
3
+ require 'nokogiri'
4
+ require 'yajl/json_gem'
5
+ require 'zabbix'
6
+ require "socket"
7
+ require "zabbix_nudge/jmx"
8
+
9
+ module ZabbixNudge
10
+
11
+ def self.root
12
+ @root ="#{File.expand_path('../..',__FILE__)}"
13
+ end
14
+
15
+ class Nudge
16
+ def initialize(templates, options = {} )
17
+ options[:zabbix_server_name] = 'localhost' unless options[:zabbix_server_name]
18
+ options[:zabbix_server_port] = '10051' unless options[:zabbix_server_port]
19
+ options[:sender_hostname] = Socket.gethostname unless options[:sender_hostname]
20
+
21
+ @options = options
22
+ @templates = template_files(templates)
23
+ @items = template_items(@templates)
24
+ end
25
+
26
+ def template_files(templates)
27
+ template_files = []
28
+ template_files = Dir.glob(File.join(templates,'*.xml')) if !templates.is_a?(Array) && File.directory?(templates)
29
+ template_files = templates.map{ |template| template if File.exist?(template) }.compact if templates.is_a?(Array)
30
+ template_files = [templates] if !templates.is_a?(Array) && File.exist?(templates) && !File.directory?(templates)
31
+ template_files
32
+ end
33
+
34
+ def template_items(templates)
35
+ parsed_items = Hash.new
36
+
37
+ templates.each do |template|
38
+ template_items = Nokogiri::XML(File.open(template))
39
+ items = template_items.xpath('//item').map {|item| item.attributes['key'].text}.compact
40
+ items.each do |item|
41
+ parts = item.match(/([^\[]+)\[([^\]]+)/)
42
+ unless parts.nil?
43
+ key = parts[1].underscore.to_sym
44
+ attributes = parts[2]
45
+ (parsed_items[key]) ? parsed_items[key] << attributes : parsed_items[key] = [attributes]
46
+ else
47
+ puts "not evaluating: "+item
48
+ end
49
+ end
50
+ end
51
+ parsed_items
52
+ end
53
+
54
+ def send(items = :all)
55
+
56
+ return if @items.nil?
57
+
58
+
59
+ pushers = ( items == :all) ? ( @items.keys.map{ |key| "ZabbixNudge::#{key.to_s.camelize}".constantize }) : ["ZabbixNudge::#{items.camelize}".constantize]
60
+
61
+ processed_items = Hash.new
62
+
63
+ pushers.map do |pusher|
64
+ pusher_key = pusher.to_s.demodulize.underscore.to_sym
65
+ processed_items.update pusher.new(@items[pusher_key],@options[pusher_key]).send(:processed_items)
66
+ end
67
+
68
+ zbx = Zabbix::Sender::Buffer.new :host => @options[:zabbix_server_name], :port => @options[:zabbix_server_port]
69
+
70
+ processed_items.each do |key,value|
71
+ zbx.append key, value, :host => @options[:sender_hostname]
72
+ end
73
+ zbx.flush
74
+
75
+ processed_items
76
+ end
77
+ end
78
+
79
+ end
@@ -0,0 +1,61 @@
1
+ require 'httparty'
2
+
3
+ module ZabbixNudge
4
+
5
+ class Jmx
6
+
7
+ include HTTParty
8
+ base_uri 'http://localhost:8080'
9
+ format :json
10
+
11
+ def initialize(items=[] ,options={})
12
+ self.class.base_uri options[:base_uri] if options[:base_uri]
13
+ @payload = Array.new
14
+ @items = items
15
+ @items.each do |item| mbean,attribute,path = item.split(';')
16
+ tokens = { "mbean" => mbean, "attribute" => attribute, "type" => "READ"}
17
+ tokens["path"] = path if path
18
+ @payload << tokens
19
+ end
20
+ end
21
+
22
+ # http://www.jolokia.org/reference/html/protocol.html#search
23
+
24
+ def search(mbean,config={})
25
+ self.class.post('/jolokia', :body => { "type" => "SEARCH", "mbean" => mbean, "config" => config}.to_json)
26
+ end
27
+
28
+ # http://www.jolokia.org/reference/html/protocol.html#list
29
+ # use options = { "maxDepth" => 2} to limit depth
30
+
31
+ def list(path,config={})
32
+ self.class.post('/jolokia', :body => { "type" => "LIST", "path" => path, "config" => config}.to_json)
33
+ end
34
+
35
+ def read(mbean,attribute,path=nil,config={})
36
+ payload = { "type" => "READ", "mbean" => mbean, "attribute" => attribute}
37
+ payload["path"] = path if path
38
+ payload["config"] = config if config.length > 0
39
+ ap payload.to_json
40
+ self.class.post('/jolokia', :body => payload.to_json, :timeout => 5)
41
+ end
42
+
43
+ def version
44
+ self.class.post('/jolokia', :body => { "type" => "VERSION"}.to_json)
45
+ end
46
+
47
+ def processed_items
48
+ data = self.class.post('/jolokia', :body => @payload.to_json, :timeout => 5) rescue nil
49
+ result = Hash.new
50
+ data.each{|datum| result[result_key(datum)] = datum['value'] if datum['request']} if data
51
+ result
52
+ end
53
+
54
+ private
55
+
56
+ def result_key(datum)
57
+ "#{self.class.to_s.demodulize.underscore}[#{datum['request']['mbean']};#{datum['request']['attribute']};#{datum['request']['path']}]"
58
+ end
59
+ end
60
+
61
+ end
@@ -0,0 +1,54 @@
1
+ require 'mixlib/cli'
2
+
3
+ module ZabbixNudge
4
+ class NudgeCLI
5
+ include Mixlib::CLI
6
+
7
+ option :jmx__base_uri,
8
+ :long => "--jmx_base_uri uri",
9
+ :description => "The jmx base uri"
10
+
11
+ end
12
+
13
+ class JmxCLI
14
+ include Mixlib::CLI
15
+
16
+ option :base_uri,
17
+ :short => "-b uri",
18
+ :default => "localhost:8080",
19
+ :long => "--base_uri uri",
20
+ :description => "The jmx base uri"
21
+
22
+ option :command,
23
+ :short => "-o command",
24
+ :default => "read",
25
+ :long => "--command action",
26
+ :description => "The command to perform",
27
+ :proc => Proc.new { |o| o.to_sym }
28
+
29
+ option :mbean,
30
+ :short => "-m mbean",
31
+ :long => "--mbean mbean",
32
+ :description => "The name of the mbean e.g. java.lang:type=Memory (needed for read command)"
33
+
34
+ option :attribute,
35
+ :short => "-a attribute",
36
+ :long => "--attribute attribute",
37
+ :description => "The name of the action e.g. HeapMemoryUsage (needed for read command)"
38
+
39
+ option :path,
40
+ :short => "-p path",
41
+ :long => "--path path",
42
+ :description => "The name of the path e.g. used (needed for read and list command)"
43
+
44
+ option :help,
45
+ :short => "-h",
46
+ :long => "--help",
47
+ :description => "Show this message",
48
+ :on => :tail,
49
+ :boolean => true,
50
+ :show_options => true,
51
+ :exit => 0
52
+
53
+ end
54
+ end
@@ -0,0 +1,74 @@
1
+ require 'mixlib/cli'
2
+ require 'socket'
3
+
4
+ module ZabbixNudge
5
+ class NudgeCLI
6
+ include Mixlib::CLI
7
+ include Socket
8
+
9
+ option :config_file,
10
+ :short => "-c CONFIG",
11
+ :long => "--config CONFIG",
12
+ :default => '/etc/zabbix-nudge/config.rb',
13
+ :description => "The configuration file to use"
14
+
15
+ option :templates,
16
+ :short => "-t FILE",
17
+ :long => "--template FILE",
18
+ :default => File.join(ZabbixNudge.root,"examples"),
19
+ :description => "The template file(s) to use, can be a file a comma separated list of files or a directory",
20
+ :proc => Proc.new { |t| (t =~ /,/) ? t.split(',') : t }
21
+
22
+ option :zabbix_server_name,
23
+ :short => "-z SERVER",
24
+ :long => "--zabbix-server SERVER",
25
+ :default => 'localhost',
26
+ :description => "Hostname or IP address of Zabbix Server. Default is localhost"
27
+
28
+ option :zabbix_server_port,
29
+ :short => "-p SERVER PORT",
30
+ :long => "--port SERVER PORT",
31
+ :default => '10051',
32
+ :description => "Specify port number of server trapper running on the server. Default is 10051"
33
+
34
+ option :sender_hostname,
35
+ :short => "-s HOST",
36
+ :long => "--host HOSTNAME",
37
+ :default => Socket.gethostname,
38
+ :description => "Specify host name. Default is current hostname"
39
+
40
+ option :jolokia_hostname,
41
+ :short => "-P JHOSTNAME",
42
+ :long => "--jolokiahostname JHOSTNAME",
43
+ :default => "localhost",
44
+ :description => "Specify jolokia hostname. Default is localhost"
45
+
46
+ option :jolokia_port,
47
+ :short => "-P JPORT",
48
+ :long => "--jolokiaport JPORT",
49
+ :default => "8080",
50
+ :description => "Specify jolokia port. Default is 8080."
51
+
52
+ option :log_level,
53
+ :short => "-l LEVEL",
54
+ :long => "--log_level LEVEL",
55
+ :description => "Set the log level (debug, info, warn, error, fatal)",
56
+ :proc => Proc.new { |l| l.to_sym }
57
+
58
+ option :show_send_values,
59
+ :short => "-v",
60
+ :long => "--show_send_values",
61
+ :description => "shows what values got send to zabbix",
62
+ :boolean => true
63
+
64
+ option :help,
65
+ :short => "-h",
66
+ :long => "--help",
67
+ :description => "Show this message",
68
+ :on => :tail,
69
+ :boolean => true,
70
+ :show_options => true,
71
+ :exit => 0
72
+
73
+ end
74
+ end
@@ -0,0 +1,3 @@
1
+ module ZabbixNudge
2
+ VERSION = "0.1.3"
3
+ end
@@ -0,0 +1,7 @@
1
+ HTTP/1.1 200 OK
2
+ Server: Apache-Coyote/1.1
3
+ Content-Type: text/plain;charset=utf-8
4
+ Content-Length: 512
5
+ Date: Wed, 15 Jun 2011 15:17:12 GMT
6
+
7
+ [{"timestamp":1308151032,"status":200,"request":{"mbean":"java.lang:name=CMS Perm Gen,type=MemoryPool","path":"committed","attribute":"Usage","type":"read"},"value":31518720},{"timestamp":1308151032,"status":200,"request":{"mbean":"java.lang:name=CMS Perm Gen,type=MemoryPool","path":"max","attribute":"Usage","type":"read"},"value":67108864},{"timestamp":1308151032,"status":200,"request":{"mbean":"java.lang:name=CMS Perm Gen,type=MemoryPool","path":"used","attribute":"Usage","type":"read"},"value":18890360}]
@@ -0,0 +1,92 @@
1
+ <?xml version="1.0"?>
2
+ <zabbix_export version="1.0" date="22.12.07" time="03.42">
3
+ <hosts>
4
+ <host name="Template_Tomcat">
5
+ <proxy_hostid>0</proxy_hostid>
6
+ <useip>0</useip>
7
+ <dns/>
8
+ <ip>0.0.0.0</ip>
9
+ <port>0</port>
10
+ <status>3</status>
11
+ <groups>
12
+ <group>Templates</group>
13
+ <group>Web Server</group>
14
+ </groups>
15
+ <items>
16
+ <item type="7" key="jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;committed]" value_type="3">
17
+ <description>memorypool cms perm gen committed</description>
18
+ <delay>30</delay>
19
+ <history>90</history>
20
+ <trends>365</trends>
21
+ <units>B</units>
22
+ <formula>1</formula>
23
+ <snmp_community>public</snmp_community>
24
+ <snmp_oid>interfaces.ifTable.ifEntry.ifInOctets.1</snmp_oid>
25
+ <snmp_port>161</snmp_port>
26
+ </item>
27
+ <item type="7" key="jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;max]" value_type="3">
28
+ <description>memorypool cms perm gen max</description>
29
+ <delay>3600</delay>
30
+ <history>90</history>
31
+ <trends>365</trends>
32
+ <units>B</units>
33
+ <formula>1</formula>
34
+ <snmp_community>public</snmp_community>
35
+ <snmp_oid>interfaces.ifTable.ifEntry.ifInOctets.1</snmp_oid>
36
+ <snmp_port>161</snmp_port>
37
+ </item>
38
+ <item type="7" key="jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;used]" value_type="3">
39
+ <description>memorypool cms perm gen used</description>
40
+ <delay>30</delay>
41
+ <history>90</history>
42
+ <trends>365</trends>
43
+ <units>B</units>
44
+ <formula>1</formula>
45
+ <snmp_community>public</snmp_community>
46
+ <snmp_oid>interfaces.ifTable.ifEntry.ifInOctets.1</snmp_oid>
47
+ <snmp_port>161</snmp_port>
48
+ </item>
49
+ </items>
50
+ <triggers/>
51
+ <graphs>
52
+ <graph name="memorypool cms perm gen" width="900" height="200">
53
+ <show_work_period>1</show_work_period>
54
+ <show_triggers>1</show_triggers>
55
+ <ymin_type>0</ymin_type>
56
+ <ymax_type>0</ymax_type>
57
+ <ymin_item_key></ymin_item_key>
58
+ <ymax_item_key></ymax_item_key>
59
+ <show_work_period>0</show_work_period>
60
+ <show_triggers>0</show_triggers>
61
+ <graphtype>1</graphtype>
62
+ <yaxismin>0.0000</yaxismin>
63
+ <yaxismax>100.0000</yaxismax>
64
+ <show_legend>0</show_legend>
65
+ <show_3d>0</show_3d>
66
+ <percent_left>0.0000</percent_left>
67
+ <percent_right>0.0000</percent_right>
68
+ <graph_elements>
69
+ <graph_element item="{HOSTNAME}:jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;committed]">
70
+ <color>000099</color>
71
+ <yaxisside>1</yaxisside>
72
+ <calc_fnc>2</calc_fnc>
73
+ <periods_cnt>5</periods_cnt>
74
+ </graph_element>
75
+ <graph_element item="{HOSTNAME}:jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;max]">
76
+ <color>990000</color>
77
+ <yaxisside>1</yaxisside>
78
+ <calc_fnc>2</calc_fnc>
79
+ <periods_cnt>5</periods_cnt>
80
+ </graph_element>
81
+ <graph_element item="{HOSTNAME}:jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;used]">
82
+ <color>009900</color>
83
+ <yaxisside>1</yaxisside>
84
+ <calc_fnc>2</calc_fnc>
85
+ <periods_cnt>5</periods_cnt>
86
+ </graph_element>
87
+ </graph_elements>
88
+ </graph>
89
+ </graphs>
90
+ </host>
91
+ </hosts>
92
+ </zabbix_export>
@@ -0,0 +1,13 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ $: << File.join(File.dirname(__FILE__), "/../lib")
4
+ require 'zabbix_nudge'
5
+ require 'fakeweb'
6
+
7
+ FakeWeb.allow_net_connect = false
8
+
9
+ def fixture_file(filename)
10
+ return '' if filename == ''
11
+ file_path = File.expand_path(File.dirname(__FILE__) + '/fixtures/' + filename)
12
+ File.read(file_path)
13
+ end
@@ -0,0 +1,32 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ require File.join(File.dirname(__FILE__), "/spec_helper")
4
+ require 'ap'
5
+
6
+ describe ZabbixNudge::Nudge do
7
+
8
+ context 'Initialization' do
9
+
10
+ FakeWeb.register_uri(:post, "http://localhost:4568/jolokia", :response => fixture_file("cms_perm_response.txt"))
11
+
12
+ it 'should accept a template file' do
13
+ @m = ZabbixNudge::Nudge.new(File.join(File.dirname(__FILE__), 'fixtures/tomcat_template.xml'),:jmx => {:base_uri => "http://localhost:4568"})
14
+ @m.send.should == {"jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;max]"=>67108864, "jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;used]"=>18890360, "jmx[java.lang:name=CMS Perm Gen,type=MemoryPool;Usage;committed]"=>31518720}
15
+
16
+ end
17
+
18
+ end
19
+
20
+ context 'process items' do
21
+
22
+
23
+ before(:each) do
24
+ end
25
+
26
+ it "should get the title" do
27
+ end
28
+
29
+
30
+ end
31
+
32
+ end
@@ -0,0 +1,37 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ $:.push File.expand_path("../lib", __FILE__)
4
+ require "zabbix_nudge/version"
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = "zabbix_nudge"
8
+ s.version = ZabbixNudge::VERSION
9
+ s.authors = ["Myroslav Rys"]
10
+ s.email = ["stonevil@gmail.com"]
11
+ s.homepage = "http://www.stone.org.ua"
12
+ s.license = 'GPL'
13
+
14
+ s.summary = %q{Collect metrics from different sources and push (nudge) data to Zabbix}
15
+ s.description = %q{zabbix-nudge is a gem to collect metrics from different sources, parse zabbix templates and push (nudge) the data to zabbix proxy or server}
16
+
17
+ s.rubyforge_project = "zabbix-nudge"
18
+
19
+ s.files = `git ls-files`.split("\n")
20
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
21
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
22
+ s.require_paths = ["lib"]
23
+
24
+ s.add_dependency 'nokogiri', '~> 1.4.4'
25
+ s.add_dependency 'zabbix', '~> 0.3.0'
26
+ s.add_dependency 'httparty', '~> 0.7.8'
27
+ s.add_dependency 'activesupport', '~> 3.0.8'
28
+ s.add_dependency "i18n", "~> 0.6.0"
29
+ s.add_dependency 'yajl-ruby', '~> 0.8.2'
30
+ s.add_dependency "awesome_print", "~> 0.4.0"
31
+ s.add_dependency "mixlib-cli", "~> 1.2.0"
32
+ s.add_dependency "daemons", "~> 1.1.9"
33
+
34
+ s.add_development_dependency 'rspec', '~> 2.6.0'
35
+ s.add_development_dependency 'fakeweb', '~> 1.3.0'
36
+
37
+ end