zabbix-monitor-modded 0.0.3

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.
@@ -0,0 +1,15 @@
1
+ ---
2
+ !binary "U0hBMQ==":
3
+ metadata.gz: !binary |-
4
+ NjcxNzEwZjM2Nzc4NmI5YTJjOWE2YTQ2ODIxMGJiOWZhMTYzNjA0NA==
5
+ data.tar.gz: !binary |-
6
+ N2UxNTQ2ZmU1NjY1ZjAxNzU2Y2U5ZGQyNjYwMDM0NWMyYTBiNGU2Nw==
7
+ SHA512:
8
+ metadata.gz: !binary |-
9
+ Y2UyYWY4MzAxZjc3Y2ZhOWQ0NGQ5NWYxMTk1OTAzMGY4ODBjYWIyNmFmNDY2
10
+ NzI3NjViMTBhZmRlYzRmOWRlYjI0MTU5YjU2YTgzNThmZjNkMTA0NmE1ODYx
11
+ ODA4ZThmYzExNDY5ZWJiNmQzNDViODkxMTM4MjAzMTY4NDNlZjE=
12
+ data.tar.gz: !binary |-
13
+ ZjM3OGNhOGM5NjBiNjc1Yjk1YmYxZjUyMzhlZDJmMDkwNmIxOGZlNGIzMTI0
14
+ MDhhMzQzZWM2MTdiYzBkZmNhOTAzZTdhNGIxOGVjMDkwN2M5NmYxZTg2ZGM3
15
+ ODAwODFhYWJkYzhiMzMwZmU4YzkxYTdjY2U3MzE5ZjExNjBiNmY=
@@ -0,0 +1,21 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
18
+ .ruby-gemset
19
+ .ruby-version
20
+ log/*
21
+ /.rspec
@@ -0,0 +1,19 @@
1
+ language: ruby
2
+ cache: bundler
3
+ rvm:
4
+ - 1.9.3
5
+ - 2.0.0
6
+ - 2.1.0
7
+ - jruby-19mode
8
+ - ruby-head
9
+ - jruby-head
10
+ matrix:
11
+ allow_failures:
12
+ - rvm: ruby-head
13
+ - rvm: jruby-head
14
+
15
+ addons:
16
+ code_climate:
17
+ repo_token: af39e5d1bbdd46699d027fd4eee89ed4cfa9d560eeafccf1293423651d0d6b0c
18
+
19
+ script: "bundle exec rake spec"
@@ -0,0 +1,5 @@
1
+ --readme README.md
2
+ --charset utf-8
3
+ --private
4
+ --protected
5
+ 'lib/**/*.rb' - '*.md'
@@ -0,0 +1,62 @@
1
+ # Zabbix Monitor Changelog
2
+
3
+ ##Changed to zabbix-monitor-modded and reversioned to 0.0.1
4
+
5
+ - Now gets hostname from config file
6
+ - Scheduler is now configurable
7
+ - Will not start unless a config file exists
8
+
9
+
10
+ ## v0.0.10 (2014-12-22)
11
+
12
+ - Require ActiveRecord 3.2 or higher
13
+
14
+ ## v0.0.9 (2014-12-22)
15
+
16
+ - Fixed some logging, docs and specs
17
+ - Require ActiveRecord explicit
18
+ - Added Capistrano tasks to stop and start the daemon to make it work with God.rb, removed after deploy:restart rule
19
+
20
+ ## v0.0.8 (2014-06-18)
21
+
22
+ - Made Yell log adapter configurable, defaults to :file
23
+
24
+ ## v0.0.7 (2014-06-18)
25
+
26
+ - Don't log while setting mode because the logger could still be uninitialized
27
+ - Don't create a symlinked log, depond on log rotate instead
28
+ - Added some logging to see if the monitor is running
29
+
30
+ ## v0.0.6 (2014-05-27)
31
+
32
+ - Moved pid files the the correct location
33
+
34
+ ## v0.0.5 (2014-05-27)
35
+
36
+ - Fixed permissions issue in v0.0.4
37
+
38
+ ## v0.0.4 (2014-05-27) (yanked)
39
+
40
+ - Added Capistrano 2 recipe
41
+
42
+ ## v0.0.3 (2014-05-27)
43
+
44
+ - Added codeclimate coverage
45
+ - Puts results to the STDOUT
46
+ - Removed YAML dependency from reader
47
+ - Use Dante to daemonize the monitoring tasks
48
+
49
+ ## v0.0.2 (2014-04-24)
50
+
51
+ - Added :file mode
52
+ - Write monitoring data to `tmp/zabbix-stats.yml`
53
+ - Read values with `$ zabbix_reader test`
54
+ - Added specs
55
+ - Added documentation
56
+ - Added services:
57
+ - Travis CI
58
+ - Rdoc
59
+
60
+ ## v0.0.1 (2014-04-17)
61
+
62
+ - Initial release
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in zabbix-agent-monitor.gemspec
4
+ gemspec
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2014 Robert Jan de Gelder
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,126 @@
1
+ # Zabbix Monitor
2
+ [![Gem Version](https://badge.fury.io/rb/zabbix-monitor.png)][gemversion]
3
+ [![Build Status](https://secure.travis-ci.org/sping/zabbix-monitor.png?branch=master)][travis]
4
+ [![Code Climate](https://codeclimate.com/github/sping/zabbix-monitor.png)][codeclimate]
5
+ [![Coverage](https://codeclimate.com/github/sping/zabbix-monitor/coverage.png)][coverage]
6
+
7
+ [gemversion]: http://badge.fury.io/rb/zabbix-monitor
8
+ [travis]: http://travis-ci.org/sping/zabbix-monitor
9
+ [codeclimate]: https://codeclimate.com/github/sping/zabbix-monitor
10
+ [coverage]: https://codeclimate.com/github/sping/zabbix-monitor
11
+
12
+ Zabbix monitoring for Ruby apps. Works with pushing and polling: push data to the agent server with zabbix_sender or collect data with the Zabbix agent.
13
+
14
+ Here you can find [Documentation](http://rubydoc.info/github/sping/zabbix-monitor/master/frames)
15
+
16
+ ## Installation
17
+
18
+ Requires the Zabbix agent to be installed.
19
+
20
+ Add this line to your application's Gemfile:
21
+
22
+ gem 'zabbix-monitor'
23
+
24
+ And then execute:
25
+
26
+ $ bundle
27
+
28
+ Or install it yourself as:
29
+
30
+ $ gem install zabbix-monitor
31
+
32
+ To include the rake tasks in your application, add the following line to your Rakefile (before `App::Application.load_tasks`):
33
+
34
+ require 'tasks/zabbix'
35
+
36
+ ## Usage
37
+
38
+ ### For Rails applications:
39
+
40
+ Place your Zabbix Monitoring configuration in an initializer:
41
+
42
+ ```ruby
43
+ require 'zabbix'
44
+
45
+ Zabbix.configure do |config|
46
+ config.config_file_path = '/etc/zabbix/zabbix_agentd.conf'
47
+ # optional, defaults to ./log/#{RACK_ENV}.log
48
+ # config.log_file_path = '/var/log/monitor.log'
49
+ config.rate = '1m'
50
+ config.mode = :push
51
+ config.rules = [
52
+ {
53
+ :command => 'Monitor.new.test',
54
+ :zabbix_key => 'zabbix.test'
55
+ }
56
+ ]
57
+ end
58
+ ```
59
+
60
+ Put the rate of the scheduler in rate.
61
+
62
+ Set the `config.mode` to one of the following options:
63
+
64
+ - `:push` uses the Zabbix agent to push the data to the Zabbix server
65
+ - `:file` writes the data to tmp/zabbix-stats.yml
66
+ - `:stdout` writes the data to the stdout
67
+
68
+ Put your monitoring rules in `config.rules`. Each rule contains a Ruby command to be executed by the Zabbix Monitor and the key as configured on the Zabbix Server.
69
+
70
+ Start running your monitoring jobs with:
71
+
72
+ $ rake zabbix:start
73
+
74
+ ### File mode
75
+
76
+ In `:file` mode, monitoring var can be read from the monitoring file using `zabbix_reader` command.
77
+ Create a script that's been executed by the Zabbix daemon:
78
+
79
+ ```bash
80
+ #! /bin/bash
81
+ cd /path/to/app/
82
+ echo $( RAILS_ENV=production bundle exec zabbix_reader $1 )
83
+ ```
84
+
85
+ To speed up the reading of variables, you can also use awk to look for variables. Create the following script instead:
86
+
87
+ ```bash
88
+ #! /bin/bash
89
+ cd /path/to/app/
90
+
91
+ if [ -f tmp/zabbix-stats.yml ]
92
+ then
93
+ echo $( awk -F: -v var=$1 '$0 ~ var {$1=""; print $0; exit}' tmp/zabbix-stats.yml )
94
+ else
95
+ echo Zabbix monitor file not found
96
+ fi
97
+ ```
98
+
99
+ ## Capistrano
100
+
101
+ Capistrano tasks are added in lib/tasks/zabbix.rb. Currently, only Capistrano 2 is supported. Add the following lines of code to your deploy.rb:
102
+
103
+ ```ruby
104
+ require 'zabbix/capistrano'
105
+
106
+ namespace :deploy do
107
+
108
+ # if you're running God.rb, it will be restarted automatically
109
+ after 'deploy:update_code', 'zabbix:stop'
110
+ # else
111
+ after 'deploy:update_code', 'zabbix:restart'
112
+
113
+ end
114
+ ```
115
+
116
+ ## Changelog
117
+
118
+ A detailed overview can be found in the [CHANGELOG](CHANGELOG.md).
119
+
120
+ ## Contributing
121
+
122
+ 1. Fork it
123
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
124
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
125
+ 4. Push to the branch (`git push origin my-new-feature`)
126
+ 5. Create new Pull Request
@@ -0,0 +1,11 @@
1
+ require 'bundler/gem_tasks'
2
+ require 'rspec/core/rake_task'
3
+ require 'yard'
4
+
5
+ RSpec::Core::RakeTask.new(:spec) do |task|
6
+ task.rspec_opts = ['--color', '--format', 'documentation']
7
+ end
8
+
9
+ YARD::Rake::YardocTask.new do |t|
10
+ t.options += ["--title", "Zabbix monitor Documentation"]
11
+ end
data/TODO.md ADDED
@@ -0,0 +1,5 @@
1
+ # Zabbix Monitor Todo
2
+
3
+ - Make Rufus Schedulere ActiveRecord independent
4
+ - Make schedule frequency configurable
5
+ - Capistrano integration / recipes
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'zabbix'
4
+
5
+ puts Zabbix::Reader.new.get_value ARGV[0]
@@ -0,0 +1,40 @@
1
+ require 'zabbix'
2
+ require 'dante'
3
+
4
+ namespace :zabbix do
5
+ desc 'Collect data for Zabbix'
6
+ task :run_once => :environment do
7
+ if Zabbix.run
8
+ Zabbix.logger.info "[Rake] executing #collect_once"
9
+ Zabbix::Monitor.new.collect_data
10
+ end
11
+ end
12
+
13
+ desc 'Collect data for Zabbix'
14
+ task :start => :environment do
15
+ if Zabbix.run
16
+ Zabbix.logger.info "[Rake] executing #start, setting up Rufus"
17
+ Dante::Runner.new('zabbix-monitor').execute(:daemonize => true, :pid_path => 'tmp/pids/zabbix-monitor.pid', :log_path => 'log/zabbix-monitor.log') do
18
+ Zabbix::Monitor.new.schedule
19
+ end
20
+ end
21
+ end
22
+
23
+ desc 'Stop collecting data for Zabbix'
24
+ task :stop => :environment do
25
+ if Zabbix.run
26
+ Zabbix.logger.info "[Rake] executing #stop, stopping daemon"
27
+ Dante::Runner.new('zabbix-monitor').execute(:kill => true, :pid_path => 'tmp/pids/zabbix-monitor.pid')
28
+ end
29
+ end
30
+
31
+ desc 'Restart collecting data for Zabbix'
32
+ task :restart => :environment do
33
+ if Zabbix.run
34
+ Zabbix.logger.info "[Rake] executing #stop, stopping daemon"
35
+ Dante::Runner.new('zabbix-monitor').execute(:daemonize => true, :restart => true, :pid_path => 'tmp/pids/zabbix-monitor.pid', :log_path => 'log/zabbix-monitor.log') do
36
+ Zabbix::Monitor.new.schedule
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,52 @@
1
+ require 'zabbix/config'
2
+ require 'zabbix/monitor'
3
+ require 'zabbix/reader'
4
+ require 'yell'
5
+
6
+ # Zabbix Monitor
7
+ module Zabbix
8
+
9
+ class FileNotFoundError < StandardError; end
10
+
11
+ class << self
12
+
13
+ # Call this method to modify defaults in your initializers.
14
+ #
15
+ # @example
16
+ # require 'zabbix'
17
+ #
18
+ # Zabbix.configure do |config|
19
+ # config.config_file_path = '/etc/zabbix/zabbix_agentd.conf'
20
+ # config.log_file_path = '/var/log/monitor.log' #optional
21
+ # config.rate = '1m'
22
+ # config.mode = :push
23
+ # config.rules = [
24
+ # {
25
+ # :command => 'Monitor.new.test',
26
+ # :zabbix_key => 'zabbix.test'
27
+ # }
28
+ # ]
29
+ # end
30
+ #
31
+ # @param [Hash] config variables
32
+ def configure
33
+ yield config
34
+ end
35
+
36
+ # @return [Zabbix::Config] creates a new or returns the existing the zabbix-monitor config
37
+ def config
38
+ @config ||= Config.new
39
+ end
40
+
41
+ def run
42
+ File.exist?(config.config_file_path)
43
+ end
44
+
45
+ # @return [Yell] creates a new or returns the +Yell+ logger instance
46
+ def logger
47
+ @logger ||= Yell.new do |l|
48
+ l.adapter self.config.log_adapter, :filename => self.config.log_file_path, :symlink => false
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,21 @@
1
+ require 'capistrano'
2
+
3
+ Capistrano::Configuration.instance.load do
4
+
5
+ namespace :zabbix do
6
+ desc 'Start Zabbix monitoring'
7
+ task :start, :roles => :web do
8
+ run "cd #{release_path}; RAILS_ENV=#{rails_env} bundle exec rake zabbix:start"
9
+ end
10
+
11
+ desc 'Stop Zabbix monitoring'
12
+ task :stop, :roles => :web do
13
+ run "cd #{release_path}; RAILS_ENV=#{rails_env} bundle exec rake zabbix:stop"
14
+ end
15
+
16
+ desc 'Restart Zabbix monitoring'
17
+ task :restart, :roles => :web do
18
+ run "cd #{release_path}; RAILS_ENV=#{rails_env} bundle exec rake zabbix:restart"
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,83 @@
1
+ module Zabbix
2
+
3
+ # The +Zabbix::Config+ object used for initializing zabbix-monitor
4
+ #
5
+ # @example
6
+ # Zabbix.configure do |config|
7
+ # config.config_file_path = '/etc/zabbix/zabbix_agentd.conf'
8
+ # config.log_file_path = '/var/log/monitor.log' #optional
9
+ # config.rate = '1m'
10
+ # config.mode = :push
11
+ # config.rules = [
12
+ # {
13
+ # :command => 'Monitor.new.test',
14
+ # :zabbix_key => 'zabbix.test'
15
+ # }
16
+ # ]
17
+ # end
18
+ #
19
+ class Config
20
+
21
+ # @return [String] the zabbix agentd config file location
22
+ attr_accessor :config_file_path
23
+
24
+ # @note
25
+ # (optional) Defaults to +./log/#{RACK_ENV}.log+
26
+ # @return [String] The zabbix-monitor log file location (optional)
27
+ attr_accessor :log_file_path
28
+
29
+ # @overload log_adapter
30
+ # @return [Symbol] The zabbix-monitor log adapter
31
+ # @overload log_adapter=(value)
32
+ # Sets the yell / zabbix-monitor log adapter
33
+ # See https://github.com/rudionrails/yell#usage for more information (optional)
34
+ #
35
+ # Options:
36
+ # :stdout logs to STDOUT
37
+ # :stderr logs to STDERR
38
+ # :file logs to a file
39
+ # :datefile logs to a timestamped file
40
+ # @param value [Symbol] the log_adapter
41
+ # @return [Symbol] the new log_adapter
42
+ attr_accessor :log_adapter
43
+
44
+ # @return [String] the zabbix hostname
45
+ attr_accessor :rate
46
+
47
+ # @return [Array<Symbol>] the set of rules to monitor
48
+ attr_accessor :rules
49
+
50
+ # @overload mode
51
+ # @return [Symbol] the mode zabbix-monitor uses to process the results of the rules
52
+ # @overload mode=(value)
53
+ # Sets the mode type, so zabbix-monitor knows how to process the results of the rules
54
+ #
55
+ # Options:
56
+ # :push uses the Zabbix agent to push the data to the Zabbix server
57
+ # :file writes the data to tmp/zabbix-stats.yml
58
+ # :stdout writes the data to the stdout
59
+ #
60
+ # @param value [Symbol] the mode
61
+ # @return [Symbol] the new mode
62
+ # @raise [StandardError] when a unsupported mode is specified
63
+ attr_accessor :mode
64
+
65
+ def mode= value
66
+ allowed_modes = [:push, :file, :stdout].freeze
67
+ if allowed_modes.include?(value)
68
+ @mode = value
69
+ else
70
+ raise "Unsupported mode: #{value}"
71
+ end
72
+ end
73
+
74
+ def log_file_path
75
+ @log_file_path || nil
76
+ end
77
+
78
+ def log_adapter
79
+ @log_adapter || :file
80
+ end
81
+
82
+ end
83
+ end
@@ -0,0 +1,112 @@
1
+ require 'json'
2
+ require 'yaml'
3
+ require 'fileutils'
4
+ require 'rufus-scheduler'
5
+ require 'active_record'
6
+
7
+ module Zabbix
8
+
9
+ # Base class for processing and delivering the results to an endpoint
10
+ class Monitor
11
+
12
+ # Schedule the data collector
13
+ # @return [void]
14
+ def schedule
15
+ Rufus::Scheduler.new.tap do |scheduler|
16
+ scheduler.every config.rate do
17
+ scheduled_collect_data
18
+ end
19
+ end.join
20
+ end
21
+
22
+ # Loops through all rules and process the result
23
+ # @return [void]
24
+ def collect_data
25
+ Zabbix.logger.info '[Monitor] collecting data'
26
+ current_zabbix_rule = nil
27
+ config.rules.each do |rule|
28
+ current_zabbix_rule = rule
29
+ value = eval rule[:command]
30
+ process_data rule[:zabbix_key], value
31
+ end
32
+ rescue Exception => e
33
+ message = "#{current_zabbix_rule[:zabbix_key]} command: #{current_zabbix_rule[:command]} with message: #{e.message}"
34
+ Zabbix.logger.error "[Monitor] failed collecting data for rule: #{message}"
35
+ end
36
+
37
+ private
38
+
39
+ # @return [Zabbix::Config] the zabbix-monitor config
40
+ def config
41
+ Zabbix.config
42
+ end
43
+
44
+ # Process the result for a rule based on the mode specified in the config
45
+ #
46
+ # @param key [String] zabbix key
47
+ # @param value [String] the result from the rule's command
48
+ #
49
+ # @return [void]
50
+ def process_data key, value
51
+ case config.mode
52
+ when :push
53
+ to_zabbix key, value
54
+ when :file
55
+ to_file key, value
56
+ when :stdout
57
+ to_stdout key, value
58
+ end
59
+ end
60
+
61
+ # Use +zabbix_sender+ command to send each result to the Zabbix server
62
+ #
63
+ # @param key [String] zabbix key
64
+ # @param value [String] the result from the rule's command
65
+ #
66
+ # @return [void]
67
+ def to_zabbix key, value
68
+ result = `zabbix_sender -c #{config.config_file_path} -k #{key} -o #{value}`
69
+ case $?.to_i
70
+ when 0 # SUCCESS
71
+ Zabbix.logger.info "[Monitor] successfully sent rule: '#{key}' with value: '#{value}' to zabbix server"
72
+ else
73
+ Zabbix.logger.error "[Monitor] failed sending rule: '#{key}' with value: '#{value}' to zabbix server"
74
+ end
75
+ end
76
+
77
+ # Writes the result to a file
78
+ #
79
+ # @param key [String] zabbix key
80
+ # @param value [String] the result from the rule's command
81
+ #
82
+ # @return [void]
83
+ def to_file key, value
84
+ filename = 'tmp/zabbix-stats.yml'
85
+ Dir.mkdir 'tmp' unless Dir.exists? 'tmp'
86
+ if File.exists? filename
87
+ yml = YAML::load_file(filename)
88
+ else
89
+ yml = {'statistics' => {'created_at' => Time.now.to_i}}
90
+ end
91
+ yml['statistics'][key] = value
92
+
93
+ File.open(filename, 'w') { |file| file.write yml.to_yaml }
94
+ end
95
+
96
+ # Prints the result of the monitored rule to stdout
97
+ #
98
+ # @param key [String] zabbix key
99
+ # @param value [String] the result from the rule's command
100
+ #
101
+ # @return [void]
102
+ def to_stdout key, value
103
+ $stdout.puts "#{key}: #{value}"
104
+ end
105
+
106
+ def scheduled_collect_data
107
+ ActiveRecord::Base.connection_pool.with_connection do
108
+ collect_data
109
+ end
110
+ end
111
+ end
112
+ end
@@ -0,0 +1,23 @@
1
+ require 'yaml'
2
+
3
+ module Zabbix
4
+
5
+ # The +Zabbix::Reader+ object used to get values from the monitor file
6
+ class Reader
7
+
8
+ def initialize
9
+ filename = 'tmp/zabbix-stats.yml'
10
+ raise FileNotFoundError, 'Monitoring file not found' if !File.exists?(filename)
11
+ @file = YAML.load_file(filename)
12
+ end
13
+
14
+ # Get a value from the Zabbix monitor file
15
+ #
16
+ # @param key [String] zabbix key
17
+ #
18
+ # @return [String] The monitoring value
19
+ def get_value key
20
+ @file['statistics'][key]
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,18 @@
1
+ require 'spec_helper'
2
+
3
+ describe Zabbix::Config do
4
+
5
+ let(:logger) { Zabbix.logger }
6
+ let(:config) { Zabbix::Config.new }
7
+
8
+ describe '#mode' do
9
+ it 'raises an unsupported mode for a invalid mode' do
10
+ expect { config.mode = :wrong }
11
+ .to raise_error(StandardError, 'Unsupported mode: wrong')
12
+ end
13
+ it 'raises an unsupported mode for a empty mode' do
14
+ expect { config.mode = '' }
15
+ .to raise_error(StandardError, 'Unsupported mode: ')
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,174 @@
1
+ require 'spec_helper'
2
+
3
+ describe Zabbix::Monitor do
4
+ let(:logger) { Zabbix.logger }
5
+ let(:monitor) { Zabbix::Monitor.new }
6
+ let(:config) { Zabbix::Config.new }
7
+
8
+ before :each do
9
+ allow(Zabbix).to receive(:config).and_return(config)
10
+ end
11
+
12
+ describe "#config" do
13
+ it 'returns the Zabbix monitor instance config' do
14
+ expect(Zabbix).to receive(:config)
15
+ monitor.send(:config)
16
+ end
17
+ end
18
+
19
+ describe '#scheduled_collect_data' do
20
+ it 'calls the #collect_data with an ActiveRecord connection from the pool' do
21
+ fake_connection = double
22
+ allow(fake_connection).to receive(:with_connection).and_yield
23
+ allow(ActiveRecord::Base).to receive(:connection_pool).and_return fake_connection
24
+ expect(monitor).to receive(:collect_data).once
25
+ monitor.send(:scheduled_collect_data)
26
+ end
27
+ end
28
+
29
+ describe '#schedule' do
30
+ let(:fake_rufus) { double }
31
+ let(:fake_collect_data) { double }
32
+
33
+ it 'schedule the data collector to run every minute' do
34
+ allow(fake_collect_data).to receive(:join)
35
+ allow(fake_rufus).to receive(:every).and_yield
36
+
37
+ expect_any_instance_of(Rufus::Scheduler).to receive(:tap).and_yield fake_rufus
38
+ expect(monitor).to receive(:scheduled_collect_data).once.and_return fake_collect_data
39
+ monitor.schedule
40
+ end
41
+ end
42
+
43
+ describe "#collect_data" do
44
+ # 'process data'
45
+ # 'raise exception invalid rule, invalid command, no command'
46
+ describe "one rule" do
47
+ before :each do
48
+ allow(config).to receive(:rules).and_return([
49
+ { :command => 'cmd', :zabbix_key => 'some.key' }
50
+ ])
51
+ end
52
+ it 'executes the command once and passes it to process' do
53
+ expect(monitor).to receive(:eval).once.and_return("result")
54
+ expect(monitor).to receive(:process_data).once.with('some.key', 'result')
55
+ monitor.collect_data
56
+ end
57
+ it 'catches the exception if command can not be excuted' do
58
+ exception = Exception.new("some error description")
59
+ expect(monitor).to receive(:eval).and_raise(exception)
60
+ expect(monitor).not_to receive(:process_data)
61
+ expect(logger).to receive(:error).with(/some.key command: cmd with message: some error description/)
62
+ monitor.collect_data
63
+ end
64
+ end
65
+ describe "two rules" do
66
+ before :each do
67
+ rules = [
68
+ { :command => 'cmd', :zabbix_key => 'some.key' },
69
+ { :command => 'cmd', :zabbix_key => 'another.key' }
70
+ ]
71
+ allow(config).to receive(:rules).and_return rules
72
+ end
73
+ it 'executes the command once and passes it to process' do
74
+ expect(monitor).to receive(:eval).twice.and_return("result")
75
+ expect(monitor).to receive(:process_data).once.with('some.key', 'result')
76
+ expect(monitor).to receive(:process_data).once.with('another.key', 'result')
77
+ monitor.collect_data
78
+ end
79
+ end
80
+ end
81
+
82
+ describe "#process_data" do
83
+ it 'triggers the #to_zabbix for :push' do
84
+ config.mode = :push
85
+
86
+ expect(monitor).to receive(:to_zabbix).once.with(1, 2)
87
+ monitor.send(:process_data, 1, 2)
88
+ end
89
+ it 'triggers the #to_file for :file' do
90
+ config.mode = :file
91
+
92
+ expect(monitor).to receive(:to_file).once.with(1, 2)
93
+ monitor.send(:process_data, 1, 2)
94
+ end
95
+ it 'triggers the #stdout for :stdout' do
96
+ config.mode = :stdout
97
+
98
+ expect(monitor).to receive(:to_stdout).once.with(1, 2)
99
+ monitor.send(:process_data, 1, 2)
100
+ end
101
+ end
102
+
103
+ describe "#to_zabbix" do
104
+ before do
105
+ config.config_file_path = '/zabbix.conf'
106
+ config.host_name = 'servername'
107
+ end
108
+ it 'executes the zabbix_sender command with the correct arguments' do
109
+ expect(monitor).to receive(:'`').once.with('zabbix_sender -c /zabbix.conf -s "servername" -k key -o value')
110
+ allow(monitor).to receive(:puts)
111
+ monitor.send(:to_zabbix, 'key', 'value')
112
+ end
113
+ it 'outputs GREAT if the command is executed without errors' do
114
+ allow(monitor).to receive(:'`').and_return(`(exit 0)`)
115
+ expect(logger).to receive(:info).with(/successfully sent rule: 'key' with value: 'value' to zabbix server: 'servername'/)
116
+ monitor.send(:to_zabbix, 'key', 'value')
117
+ end
118
+ it 'outputs BUMMER if the command is executed with an error' do
119
+ allow(monitor).to receive(:'`').and_return(`(exit 1)`)
120
+ expect(logger).to receive(:error).with(/failed sending rule: 'key' with value: 'value' to zabbix server: 'servername'/)
121
+ monitor.send(:to_zabbix, 'key', 'value')
122
+ end
123
+ end
124
+
125
+ describe "#to_file" do
126
+ before :each do
127
+ allow(File).to receive(:exists?).and_return false
128
+ allow(File).to receive(:open).with('tmp/zabbix-stats.yml', 'w')
129
+ end
130
+ it 'creates the tmp folder if it does not exist' do
131
+ expect(Dir).to receive(:mkdir).once.with('tmp')
132
+ expect(Dir).to receive(:exists?).once.with('tmp').and_return(false)
133
+ monitor.send(:to_file, 'key', 'value')
134
+ end
135
+ it 'will not create the tmp folder if it already exists' do
136
+ expect(Dir).not_to receive(:mkdir).with('tmp')
137
+ expect(Dir).to receive(:exists?).once.with('tmp').and_return(true)
138
+ monitor.send(:to_file, 'key', 'value')
139
+ end
140
+ before :each do
141
+ allow(Dir).to receive(:exists?).and_return true
142
+ end
143
+ describe 'writeing and reading' do
144
+ it 'writes the result to "tmp/zabbix-stats.yml"' do
145
+ allow(File).to receive(:exists?).and_return false
146
+ file = double('file')
147
+ yml = {'statistics' => {'created_at' => Time.now.to_i, 'key' => 'value'}}
148
+
149
+ expect(File).to receive(:open).with('tmp/zabbix-stats.yml', 'w').and_yield(file)
150
+ expect(file).to receive(:write).with(yml.to_yaml)
151
+ monitor.send(:to_file, 'key', 'value')
152
+ end
153
+ it 'adds the key and value to the output file if it already exists' do
154
+ allow(File).to receive(:exists?).and_return true
155
+ file = double('file')
156
+ yml = {'statistics' => {'created_at' => Time.now.to_i, 'old_key' => 'old_value'}}
157
+
158
+ expect(YAML).to receive(:load_file).once.with('tmp/zabbix-stats.yml').and_return(yml)
159
+ expect(File).to receive(:open).with('tmp/zabbix-stats.yml', 'w').and_yield(file)
160
+
161
+ yml['statistics']['key'] = 'value'
162
+ expect(file).to receive(:write).with(yml.to_yaml)
163
+ monitor.send(:to_file, 'key', 'value')
164
+ end
165
+ end
166
+ end
167
+
168
+ describe "#to_stdout" do
169
+ it 'receives the key and value as a puts command' do
170
+ expect(STDOUT).to receive(:puts).with('key: the value')
171
+ monitor.send(:to_stdout, 'key', 'the value')
172
+ end
173
+ end
174
+ end
@@ -0,0 +1,39 @@
1
+ require 'spec_helper'
2
+
3
+ describe Zabbix::Reader do
4
+
5
+ before :each do
6
+ @filename = 'tmp/zabbix-stats.yml'
7
+ # File.open(@filename, 'w') { |file| file.write({'statistics' => {'test' => 'OK'}}.to_yaml) } unless File.exists?(@filename)
8
+ end
9
+
10
+ describe 'initialize' do
11
+ it 'raises an error when the file can\'t be found' do
12
+ expect(File).to receive(:exists?).with(@filename).and_return(false)
13
+ expect{ Zabbix::Reader.new }.to raise_error(Zabbix::FileNotFoundError, 'Monitoring file not found')
14
+ end
15
+
16
+ it 'reads the monitoring file from tmp' do
17
+ expect(File).to receive(:exists?).with(@filename).and_return(true)
18
+ expect(YAML).to receive(:load_file).with(@filename)
19
+ Zabbix::Reader.new
20
+ end
21
+ end
22
+
23
+ describe 'get_value' do
24
+ before :each do
25
+ expect(File).to receive(:exists?).and_return true
26
+ expect(YAML).to receive(:load_file).and_return({'statistics' => {'test' => 'OK'}})
27
+ end
28
+ let(:reader) { Zabbix::Reader.new }
29
+
30
+ it 'returns the requested value' do
31
+ expect(reader.get_value 'test').to eq('OK')
32
+ end
33
+
34
+ it 'returns nil when the key can\'t be found' do
35
+ expect(reader.get_value 'missing').to be_nil
36
+ end
37
+ end
38
+
39
+ end
@@ -0,0 +1,20 @@
1
+ require 'pry'
2
+ require 'simplecov'
3
+ require "codeclimate-test-reporter"
4
+
5
+ CodeClimate::TestReporter.start
6
+ SimpleCov.start do
7
+ add_filter '/spec/'
8
+ end
9
+
10
+ require 'zabbix'
11
+
12
+ RSpec.configure do |config|
13
+ # configure yell logger's ENV and remove the logs files afterwards
14
+ ENV['YELL_ENV'] = 'test'
15
+
16
+ config.before :each do
17
+ log_path = File.expand_path("../log", File.dirname(__FILE__))
18
+ Dir[log_path + "/test*.log" ].each { |f| File.delete f }
19
+ end
20
+ end
@@ -0,0 +1,56 @@
1
+ require 'spec_helper'
2
+
3
+ describe Zabbix do
4
+ before :each do
5
+ # reset config
6
+ Zabbix.send(:config) { nil }
7
+ end
8
+
9
+ describe "#configure" do
10
+ describe "basic config vars and behaviour" do
11
+
12
+ it 'creates a new config for the Zabbix monitor instance' do
13
+ expect(Zabbix.config).to be_kind_of(Zabbix::Config)
14
+ end
15
+ it 'set the correct config values' do
16
+ Zabbix.configure do |config|
17
+ config.config_file_path = '/etc/zabbix/zabbix_agentd.conf'
18
+ config.host_name = 'servername'
19
+ config.mode = :push
20
+ end
21
+
22
+ expect(Zabbix.config.config_file_path).to eq '/etc/zabbix/zabbix_agentd.conf'
23
+ expect(Zabbix.config.log_file_path).to be_nil
24
+ expect(Zabbix.config.host_name).to eq 'servername'
25
+ expect(Zabbix.config.mode).to eq :push
26
+ pending 'should rules be initialized as an empty array?'
27
+ expect(Zabbix.config.rules.count).to eq 0
28
+ end
29
+ it 'returns the correct log_file_path if specified' do
30
+ Zabbix.configure do |config|
31
+ config.log_file_path = '/var/log/monitor.log'
32
+ end
33
+ expect(Zabbix.config.log_file_path).to eq '/var/log/monitor.log'
34
+ end
35
+ end
36
+
37
+ describe "rules" do
38
+ it 'has one rule' do
39
+ rule = { :command => 'a', :zabbix_key => 'a' }
40
+ Zabbix.configure do |config|
41
+ config.rules = [rule]
42
+ end
43
+ expect(Zabbix.config.rules).to eq [rule]
44
+ end
45
+ it 'has two rules' do
46
+ ruleA = { :command => 'a', :zabbix_key => 'a' }
47
+ ruleB = { :command => 'b', :zabbix_key => 'b' }
48
+ Zabbix.configure do |config|
49
+ config.rules = [ruleA, ruleB]
50
+ end
51
+ expect(Zabbix.config.rules).to eq [ruleA, ruleB]
52
+ end
53
+ it 'validates if the format of a rule from config is valid'
54
+ end
55
+ end
56
+ end
@@ -0,0 +1,33 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = 'zabbix-monitor-modded'
7
+ spec.version = '0.0.3'
8
+ spec.authors = ['Robert Jan de Gelder', 'Manuel van Rijn', 'Stuart Speidel']
9
+ spec.email = ['r.degelder@sping.nl', 'm.vanrijn@sping.nl', '']
10
+ spec.description = 'Zabbix application monitoring'
11
+ spec.summary = 'Let the Zabbix agent read your application monitoring, modded to allow modifation of rate and not using a hardcoded server name'
12
+ spec.homepage = 'http://rubygems.org/gems/zabbix-monitor'
13
+ spec.license = 'MIT'
14
+
15
+ spec.files = `git ls-files`.split($/)
16
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
17
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
18
+ spec.require_paths = ['lib']
19
+
20
+ spec.add_dependency 'rufus-scheduler', '~> 3.0'
21
+ spec.add_dependency 'yell', '~> 2.0'
22
+ spec.add_dependency 'dante', '~> 0.2.0'
23
+ spec.add_dependency 'activerecord', '~> 3.2'
24
+
25
+ spec.add_development_dependency 'rake','>=10.4.2'
26
+ spec.add_development_dependency 'bundler', '~> 1.3'
27
+ spec.add_development_dependency 'rspec', '~> 3.1'
28
+ spec.add_development_dependency 'pry','~>0.10.1'
29
+ spec.add_development_dependency 'pry-nav','~>0.2.4'
30
+ spec.add_development_dependency 'yard','~>0.8.7.6'
31
+ spec.add_development_dependency 'simplecov','~>0.10.0'
32
+ spec.add_development_dependency 'codeclimate-test-reporter','~>0.4.7'
33
+ end
metadata ADDED
@@ -0,0 +1,247 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: zabbix-monitor-modded
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.3
5
+ platform: ruby
6
+ authors:
7
+ - Robert Jan de Gelder
8
+ - Manuel van Rijn
9
+ - Stuart Speidel
10
+ autorequire:
11
+ bindir: bin
12
+ cert_chain: []
13
+ date: 2015-08-21 00:00:00.000000000 Z
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: rufus-scheduler
17
+ requirement: !ruby/object:Gem::Requirement
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: '3.0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ requirements:
26
+ - - ~>
27
+ - !ruby/object:Gem::Version
28
+ version: '3.0'
29
+ - !ruby/object:Gem::Dependency
30
+ name: yell
31
+ requirement: !ruby/object:Gem::Requirement
32
+ requirements:
33
+ - - ~>
34
+ - !ruby/object:Gem::Version
35
+ version: '2.0'
36
+ type: :runtime
37
+ prerelease: false
38
+ version_requirements: !ruby/object:Gem::Requirement
39
+ requirements:
40
+ - - ~>
41
+ - !ruby/object:Gem::Version
42
+ version: '2.0'
43
+ - !ruby/object:Gem::Dependency
44
+ name: dante
45
+ requirement: !ruby/object:Gem::Requirement
46
+ requirements:
47
+ - - ~>
48
+ - !ruby/object:Gem::Version
49
+ version: 0.2.0
50
+ type: :runtime
51
+ prerelease: false
52
+ version_requirements: !ruby/object:Gem::Requirement
53
+ requirements:
54
+ - - ~>
55
+ - !ruby/object:Gem::Version
56
+ version: 0.2.0
57
+ - !ruby/object:Gem::Dependency
58
+ name: activerecord
59
+ requirement: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ~>
62
+ - !ruby/object:Gem::Version
63
+ version: '3.2'
64
+ type: :runtime
65
+ prerelease: false
66
+ version_requirements: !ruby/object:Gem::Requirement
67
+ requirements:
68
+ - - ~>
69
+ - !ruby/object:Gem::Version
70
+ version: '3.2'
71
+ - !ruby/object:Gem::Dependency
72
+ name: rake
73
+ requirement: !ruby/object:Gem::Requirement
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: 10.4.2
78
+ type: :development
79
+ prerelease: false
80
+ version_requirements: !ruby/object:Gem::Requirement
81
+ requirements:
82
+ - - ! '>='
83
+ - !ruby/object:Gem::Version
84
+ version: 10.4.2
85
+ - !ruby/object:Gem::Dependency
86
+ name: bundler
87
+ requirement: !ruby/object:Gem::Requirement
88
+ requirements:
89
+ - - ~>
90
+ - !ruby/object:Gem::Version
91
+ version: '1.3'
92
+ type: :development
93
+ prerelease: false
94
+ version_requirements: !ruby/object:Gem::Requirement
95
+ requirements:
96
+ - - ~>
97
+ - !ruby/object:Gem::Version
98
+ version: '1.3'
99
+ - !ruby/object:Gem::Dependency
100
+ name: rspec
101
+ requirement: !ruby/object:Gem::Requirement
102
+ requirements:
103
+ - - ~>
104
+ - !ruby/object:Gem::Version
105
+ version: '3.1'
106
+ type: :development
107
+ prerelease: false
108
+ version_requirements: !ruby/object:Gem::Requirement
109
+ requirements:
110
+ - - ~>
111
+ - !ruby/object:Gem::Version
112
+ version: '3.1'
113
+ - !ruby/object:Gem::Dependency
114
+ name: pry
115
+ requirement: !ruby/object:Gem::Requirement
116
+ requirements:
117
+ - - ~>
118
+ - !ruby/object:Gem::Version
119
+ version: 0.10.1
120
+ type: :development
121
+ prerelease: false
122
+ version_requirements: !ruby/object:Gem::Requirement
123
+ requirements:
124
+ - - ~>
125
+ - !ruby/object:Gem::Version
126
+ version: 0.10.1
127
+ - !ruby/object:Gem::Dependency
128
+ name: pry-nav
129
+ requirement: !ruby/object:Gem::Requirement
130
+ requirements:
131
+ - - ~>
132
+ - !ruby/object:Gem::Version
133
+ version: 0.2.4
134
+ type: :development
135
+ prerelease: false
136
+ version_requirements: !ruby/object:Gem::Requirement
137
+ requirements:
138
+ - - ~>
139
+ - !ruby/object:Gem::Version
140
+ version: 0.2.4
141
+ - !ruby/object:Gem::Dependency
142
+ name: yard
143
+ requirement: !ruby/object:Gem::Requirement
144
+ requirements:
145
+ - - ~>
146
+ - !ruby/object:Gem::Version
147
+ version: 0.8.7.6
148
+ type: :development
149
+ prerelease: false
150
+ version_requirements: !ruby/object:Gem::Requirement
151
+ requirements:
152
+ - - ~>
153
+ - !ruby/object:Gem::Version
154
+ version: 0.8.7.6
155
+ - !ruby/object:Gem::Dependency
156
+ name: simplecov
157
+ requirement: !ruby/object:Gem::Requirement
158
+ requirements:
159
+ - - ~>
160
+ - !ruby/object:Gem::Version
161
+ version: 0.10.0
162
+ type: :development
163
+ prerelease: false
164
+ version_requirements: !ruby/object:Gem::Requirement
165
+ requirements:
166
+ - - ~>
167
+ - !ruby/object:Gem::Version
168
+ version: 0.10.0
169
+ - !ruby/object:Gem::Dependency
170
+ name: codeclimate-test-reporter
171
+ requirement: !ruby/object:Gem::Requirement
172
+ requirements:
173
+ - - ~>
174
+ - !ruby/object:Gem::Version
175
+ version: 0.4.7
176
+ type: :development
177
+ prerelease: false
178
+ version_requirements: !ruby/object:Gem::Requirement
179
+ requirements:
180
+ - - ~>
181
+ - !ruby/object:Gem::Version
182
+ version: 0.4.7
183
+ description: Zabbix application monitoring
184
+ email:
185
+ - r.degelder@sping.nl
186
+ - m.vanrijn@sping.nl
187
+ - ''
188
+ executables:
189
+ - zabbix_reader
190
+ extensions: []
191
+ extra_rdoc_files: []
192
+ files:
193
+ - .gitignore
194
+ - .travis.yml
195
+ - .yardopts
196
+ - CHANGELOG.md
197
+ - Gemfile
198
+ - LICENSE.txt
199
+ - README.md
200
+ - Rakefile
201
+ - TODO.md
202
+ - bin/zabbix_reader
203
+ - lib/tasks/zabbix.rb
204
+ - lib/zabbix.rb
205
+ - lib/zabbix/capistrano.rb
206
+ - lib/zabbix/config.rb
207
+ - lib/zabbix/monitor.rb
208
+ - lib/zabbix/reader.rb
209
+ - log/.gitkeep
210
+ - spec/config_spec.rb
211
+ - spec/monitor_spec.rb
212
+ - spec/reader_spec.rb
213
+ - spec/spec_helper.rb
214
+ - spec/zabbix_spec.rb
215
+ - zabbix-monitor-modded.gemspec
216
+ homepage: http://rubygems.org/gems/zabbix-monitor
217
+ licenses:
218
+ - MIT
219
+ metadata: {}
220
+ post_install_message:
221
+ rdoc_options: []
222
+ require_paths:
223
+ - lib
224
+ required_ruby_version: !ruby/object:Gem::Requirement
225
+ requirements:
226
+ - - ! '>='
227
+ - !ruby/object:Gem::Version
228
+ version: '0'
229
+ required_rubygems_version: !ruby/object:Gem::Requirement
230
+ requirements:
231
+ - - ! '>='
232
+ - !ruby/object:Gem::Version
233
+ version: '0'
234
+ requirements: []
235
+ rubyforge_project:
236
+ rubygems_version: 2.4.8
237
+ signing_key:
238
+ specification_version: 4
239
+ summary: Let the Zabbix agent read your application monitoring, modded to allow modifation
240
+ of rate and not using a hardcoded server name
241
+ test_files:
242
+ - spec/config_spec.rb
243
+ - spec/monitor_spec.rb
244
+ - spec/reader_spec.rb
245
+ - spec/spec_helper.rb
246
+ - spec/zabbix_spec.rb
247
+ has_rdoc: