#! /usr/bin/env ruby # # nginx-metrics # # DESCRIPTION: # Pull nginx metrics for backends through stub status module # # OUTPUT: # metric data # # PLATFORMS: # Linux # # DEPENDENCIES: # gem: sensu-plugin # # USAGE: # metrics-nginx.rb -h hostname -p port -q status_path # metrics-nginx.rb -u http://hostname:port/status_path # # NOTES: # # LICENSE: # Copyright 2012 Pete Shima # Released under the same terms as Sensu (the MIT license); see LICENSE # for details. # require 'sensu-plugin/metric/cli' require 'net/https' require 'uri' require 'socket' # # Nginx Metrics # class NginxMetrics < Sensu::Plugin::Metric::CLI::Graphite option :url, short: '-u URL', long: '--url URL', description: 'Full URL to nginx status page, example: https://yoursite.com/nginx_status This ignores ALL other options EXCEPT --scheme' option :hostname, short: '-h HOSTNAME', long: '--host HOSTNAME', description: 'Nginx hostname', default: 'localhost' option :port, short: '-p PORT', long: '--port PORT', description: 'Nginx port', default: '80' option :path, short: '-q STATUSPATH', long: '--statspath STATUSPATH', description: 'Path to your stub status module', default: 'nginx_status' option :hostheader, long: '--hostheader HOSTHEADER', description: 'Set the Host header to this string' option :scheme, description: 'Metric naming scheme, text to prepend to metric', short: '-s SCHEME', long: '--scheme SCHEME', default: "#{Socket.gethostname}.nginx" # Main function # def run found = false attempts = 0 until found || attempts >= 10 attempts += 1 if config[:url] uri = URI.parse(config[:url]) http = Net::HTTP.new(uri.host, uri.port) if uri.scheme == 'https' http.use_ssl = true http.verify_mode = OpenSSL::SSL::VERIFY_NONE end request = Net::HTTP::Get.new(uri.request_uri) if config[:hostheader] request['Host'] = config[:hostheader] end response = http.request(request) if response.code == '200' found = true elsif !response.header['location'].nil? config[:url] = response.header['location'] end else response = Net::HTTP.start(config[:hostname], config[:port]) do |connection| request = Net::HTTP::Get.new("/#{config[:path]}") connection.request(request) end end end # #YELLOW response.body.split(/\r?\n/).each do |line| if line =~ /^Active connections:\s+(\d+)/ connections = line.match(/^Active connections:\s+(\d+)/).to_a output "#{config[:scheme]}.active_connections", connections[1] end if line =~ /^\s+(\d+)\s+(\d+)\s+(\d+)/ requests = line.match(/^\s+(\d+)\s+(\d+)\s+(\d+)/).to_a output "#{config[:scheme]}.accepts", requests[1] output "#{config[:scheme]}.handled", requests[2] output "#{config[:scheme]}.requests", requests[3] end if line =~ /^Reading:\s+(\d+).*Writing:\s+(\d+).*Waiting:\s+(\d+)/ queue = line.match(/^Reading:\s+(\d+).*Writing:\s+(\d+).*Waiting:\s+(\d+)/).to_a output "#{config[:scheme]}.reading", queue[1] output "#{config[:scheme]}.writing", queue[2] output "#{config[:scheme]}.waiting", queue[3] end end ok end end