summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/custodian/alerter.rb63
-rwxr-xr-xt/test-alerter.rb27
2 files changed, 88 insertions, 2 deletions
diff --git a/lib/custodian/alerter.rb b/lib/custodian/alerter.rb
index 69de28e..f5caa6a 100644
--- a/lib/custodian/alerter.rb
+++ b/lib/custodian/alerter.rb
@@ -11,6 +11,10 @@ require 'socket'
#
# This class encapsulates the raising and clearing of alerts via Mauve.
#
+# There is a helper method to update any alerts with details of whether the
+# affected host is inside/outside the Bytemark network.
+#
+#
class Alerter
@@ -68,13 +72,48 @@ class Alerter
#
+ # Resolve an IP address
+ #
+ def document_address( address )
+
+ raise ArgumentError, "Address must not be nil" if ( address.nil? )
+
+ begin
+ Resolv.new.getname(address)
+ rescue
+ nil
+ end
+ end
+
+
+
+ #
# Raise the alert.
#
def raise( detail )
+ #
+ # Is this alert affecting a machine inside/outside our network
+ #
inside = expand_inside_bytemark( @details["target_host"] )
+ #
+ # Document the hostname if the alert relates to an IP address.
+ #
+ resolved = ""
+ if ( ( @details["target_host"] =~ /^([0-9]+)\.([0-9]+)\.([0-9]+)\.([0-9]+)$/ ) ||
+ ( @details["target_host"] =~ /^([0-9a-f:]+)$/ ) )
+
+ resolved = document_address( @details["target_host"] )
+ if ( resolved.nil? )
+ resolved = ""
+ else
+ resolved = "The IP address #{@details["target_host"]} resolves to #{resolved}."
+ end
+ end
+
+
update = Mauve::Proto::AlertUpdate.new
update.alert = []
update.source = "custodian"
@@ -90,7 +129,7 @@ class Alerter
alert.subject = @details['target_host']
alert.summary = @details['test_alert']
- alert.detail = "#{inside} <p>The #{@details['test_type']} test failed against #{@details['target_host']}: #{detail}</p>"
+ alert.detail = "#{inside} <p>The #{@details['test_type']} test failed against #{@details['target_host']}: #{detail}</p><p>#{resolved}</p>"
alert.raise_time = Time.now.to_i
update.alert << alert
@@ -103,8 +142,28 @@ class Alerter
#
def clear
+ #
+ # Is this alert affecting a machine inside/outside our network
+ #
inside = expand_inside_bytemark( @details["target_host"] )
+
+ #
+ # Document the hostname if the alert relates to an IP address.
+ #
+ resolved = ""
+ if ( ( @details["target_host"] =~ /^([0-9]+)\.([0-9]+)\.([0-9]+)\.([0-9]+)$/ ) ||
+ ( @details["target_host"] =~ /^([0-9a-f:]+)$/ ) )
+
+ resolved = document_address( @details["target_host"] )
+ if ( resolved.nil? )
+ resolved = ""
+ else
+ resolved = "The IP address #{@details["target_host"]} resolves to #{resolved}."
+ end
+ end
+
+
update = Mauve::Proto::AlertUpdate.new
update.alert = []
update.source = "custodian"
@@ -121,7 +180,7 @@ class Alerter
alert.subject = @details['target_host']
alert.summary = @details['test_alert']
- alert.detail = "#{inside} <p>The #{@details['test_type']} test succeeded against #{@details['target_host']}</p>"
+ alert.detail = "#{inside} <p>The #{@details['test_type']} test succeeded against #{@details['target_host']}</p><p>#{resolved}</p>"
alert.clear_time = Time.now.to_i
update.alert << alert
diff --git a/t/test-alerter.rb b/t/test-alerter.rb
index 88dc786..97e19b5 100755
--- a/t/test-alerter.rb
+++ b/t/test-alerter.rb
@@ -92,6 +92,33 @@ class TestAlerter < Test::Unit::TestCase
+ #
+ # Test documentation-detection.
+ #
+ def test_locations_inside_outside
+
+ obj = Alerter.new( nil )
+
+ assert_raise ArgumentError do
+ obj.document_address( nil )
+ end
+
+ #
+ # IPv6 lookup
+ #
+ details = obj.document_address( "2001:41c8:125:46::22" )
+ assert( details =~ /ssh.steve.org.uk/i )
+ #
+ # IPv4 lookup
+ #
+ details = obj.document_address( "80.68.85.48" )
+ assert( details =~ /ssh.steve.org.uk/i )
+ #
+ # Bogus lookup - should return nil.
+ #
+ details = obj.document_address( "800.683.853.348" )
+ assert( details.nil? )
+ end
end