aboutsummaryrefslogtreecommitdiff
path: root/lib/mauve
diff options
context:
space:
mode:
Diffstat (limited to 'lib/mauve')
-rw-r--r--lib/mauve/alert.rb22
-rw-r--r--lib/mauve/alert_changed.rb10
-rw-r--r--lib/mauve/alert_group.rb12
-rw-r--r--lib/mauve/auth_bytemark.rb2
-rw-r--r--lib/mauve/datamapper.rb3
-rw-r--r--lib/mauve/history.rb10
-rw-r--r--lib/mauve/http_server.rb1
-rw-r--r--lib/mauve/mauve_thread.rb11
-rw-r--r--lib/mauve/notification.rb5
-rw-r--r--lib/mauve/notifier.rb5
-rw-r--r--lib/mauve/notifiers/email.rb17
-rw-r--r--lib/mauve/notifiers/sms_aql.rb5
-rw-r--r--lib/mauve/notifiers/xmpp-smack.rb395
-rw-r--r--lib/mauve/notifiers/xmpp.rb26
-rw-r--r--lib/mauve/people_list.rb9
-rw-r--r--lib/mauve/person.rb50
-rw-r--r--lib/mauve/processor.rb23
-rw-r--r--lib/mauve/sender.rb1
-rw-r--r--lib/mauve/server.rb7
-rw-r--r--lib/mauve/timer.rb6
-rw-r--r--lib/mauve/udp_server.rb8
-rw-r--r--lib/mauve/web_interface.rb23
22 files changed, 132 insertions, 519 deletions
diff --git a/lib/mauve/alert.rb b/lib/mauve/alert.rb
index bea2fc4..164139b 100644
--- a/lib/mauve/alert.rb
+++ b/lib/mauve/alert.rb
@@ -104,7 +104,7 @@ module Mauve
default_scope(:default).update(:order => [:source, :importance])
def logger
- Log4r::Logger.new(self.class.to_s)
+ @logger ||= self.class.logger
end
def time_relative(secs)
@@ -186,7 +186,7 @@ module Mauve
if @changes_before_save.has_key?(:update_type) or (self.update_type == "raised" and is_a_change)
self.notify
- h = History.new(:alert => self, :type => "update")
+ h = History.new(:alert_id => self.id, :type => "update")
if self.update_type == "acknowledged"
h.event = "ACKNOWLEDGED by #{self.acknowledged_by} until #{self.will_unacknowledge_at}"
@@ -200,7 +200,9 @@ module Mauve
end
- h.save
+ if !h.save
+ logger.error "Unable to save history due to #{h.errors.inspect}"
+ end
end
true
@@ -244,7 +246,6 @@ module Mauve
# Don't clear will_clear_at
self.update_type = "raised" if self.update_type.nil? or self.update_type != "changed" or self.original_attributes[Alert.properties[:update_type]] == "cleared"
- logger.debug("saving #{self.inspect}")
logger.error("Couldn't save #{self}") unless save
end
@@ -384,8 +385,6 @@ module Mauve
time_offset = (reception_time - transmission_time).round
- logger.debug("Update received from a host #{time_offset}s behind") if time_offset.abs > 5
-
#
# Make sure there is no HTML in the update source.
#
@@ -457,13 +456,14 @@ module Mauve
#
# Set the subject
#
- if alert.subject and !alert.subject.empty?
+ if alert.subject and !alert.subject.empty?
alert_db.subject = Alert.remove_html(alert.subject)
- else
+
+ elsif alert_db.subject.nil?
#
# Use the source, Luke, but only when the subject hasn't already been set.
#
- alert_db.subject = alert_db.source if alert_db.subject.nil?
+ alert_db.subject = alert_db.source
end
alert_db.summary = Alert.remove_html(alert.summary) if alert.summary && !alert.summary.empty?
@@ -501,7 +501,7 @@ module Mauve
#
if update.replace
alert_ids_mentioned = update.alert.map { |alert| alert.id }
- logger.debug "Replacing all alerts from #{update.source} except "+alert_ids_mentioned.join(",")
+ logger.info "Replacing all alerts from #{update.source} except "+alert_ids_mentioned.join(",")
all(:source => update.source,
:alert_id.not => alert_ids_mentioned,
:cleared_at => nil
@@ -513,7 +513,7 @@ module Mauve
end
def logger
- Log4r::Logger.new("Mauve::Alert")
+ Log4r::Logger.new(self.to_s)
end
end
end
diff --git a/lib/mauve/alert_changed.rb b/lib/mauve/alert_changed.rb
index 0b0f72a..740b9dc 100644
--- a/lib/mauve/alert_changed.rb
+++ b/lib/mauve/alert_changed.rb
@@ -39,7 +39,7 @@ module Mauve
)
if old_changed
if !old_changed.update(:remind_at => nil)
- logger.error "Couldn't save #{old_changed}, will get duplicate reminders"
+ logger.info "Couldn't save #{old_changed}, will get duplicate reminders"
end
end
end
@@ -74,7 +74,7 @@ module Mauve
previous.was_relevant_when_raised?
else
# a bug, but hardly inconceivable :)
- logger.warn("Could not see that #{alert} was raised with #{person} "+
+ logger.info("Could not see that #{alert} was raised with #{person} "+
"but further updates exist (e.g. #{self}) "+
"- you may see spurious notifications as a result")
true
@@ -86,18 +86,18 @@ module Mauve
#
def remind
unless alert.is_a?(Alert)
- logger.debug "#{self.inspect} lost alert #{alert_id}. Killing self."
+ logger.info "#{self.inspect} lost alert #{alert_id}. Killing self."
destroy!
return false
end
- logger.debug "Reminding someone about #{self.inspect}"
+ logger.info "Reminding someone about #{self.inspect}"
alert_group = AlertGroup.matches(alert)[0]
if !alert_group || alert.acknowledged?
- logger.debug((alert_group ?
+ logger.info((alert_group ?
"Alert already acknowledged" :
"No alert group matches any more"
) + ", no reminder due"
diff --git a/lib/mauve/alert_group.rb b/lib/mauve/alert_group.rb
index 75f97fd..bfdb3cf 100644
--- a/lib/mauve/alert_group.rb
+++ b/lib/mauve/alert_group.rb
@@ -40,17 +40,15 @@ module Mauve
# Make sure we've got a matching group
#
if groups.empty?
- logger.warn "no groups found for #{alert}"
+ logger.warn "no groups found for #{alert}!"
next
end
#
- # Notify just the group that thinks this alert is the most urgent.
+ # Notify just the first group
#
- logger.warn "Found #{groups.length} matching groups for #{alert}" if groups.length > 1
-
this_group = groups.first
- logger.info("notifying group #{this_group} of #{alert} (matching #{this_group.level})")
+ logger.info("notifying group #{this_group} of #{alert}")
this_group.notify(alert)
end
end
@@ -103,7 +101,7 @@ module Mauve
def matches_alert?(alert)
unless alert.is_a?(Alert)
- logger.warn "Got given a #{alert.class} instead of an Alert!"
+ logger.error "Got given a #{alert.class} instead of an Alert!"
logger.debug caller.join("\n")
return false
end
@@ -126,7 +124,7 @@ module Mauve
# If there are no notifications defined.
#
if notifications.nil?
- logger.warn("No notifications found for #{alert}")
+ logger.warn("No notifications found for #{self.inspect}")
return
end
diff --git a/lib/mauve/auth_bytemark.rb b/lib/mauve/auth_bytemark.rb
index 2273c36..c0834e0 100644
--- a/lib/mauve/auth_bytemark.rb
+++ b/lib/mauve/auth_bytemark.rb
@@ -46,7 +46,7 @@ class AuthBytemark
Mauve::Server.instance.logger.warn "Fault code is #{fault.faultCode} stating #{fault.faultString}"
return false
rescue Exception => ex
- Mauve::Server.instance.logger.warn "Caught #{ex.to_s} whilst trying to loging for #{login}"
+ Mauve::Server.instance.logger.error "Caught #{ex.to_s} whilst trying to loging for #{login}"
Mauve::Server.instance.logger.debug ex.backtrace.join("\n")
return false
end
diff --git a/lib/mauve/datamapper.rb b/lib/mauve/datamapper.rb
index 27d89a3..f46536e 100644
--- a/lib/mauve/datamapper.rb
+++ b/lib/mauve/datamapper.rb
@@ -11,3 +11,6 @@ require 'dm-migrations'
require 'dm-validations'
require 'dm-timestamps'
+
+# DataMapper::Model.raise_on_save_failure = true
+
diff --git a/lib/mauve/history.rb b/lib/mauve/history.rb
index 6c4969b..1c2cdf4 100644
--- a/lib/mauve/history.rb
+++ b/lib/mauve/history.rb
@@ -12,10 +12,16 @@ module Mauve
property :id, Serial
property :alert_id, Integer, :required => true
property :type, String, :required => true, :default => "unknown"
- property :event, Text, :required => true
- property :created_at, DateTime
+ property :event, Text, :required => true, :default => "Nothing set"
+ property :created_at, DateTime, :required => true
belongs_to :alert
+
+ before :valid?, :set_created_at
+
+ def set_created_at(context = :default)
+ self.created_at = Time.now unless self.created_at.is_a?(Time) or self.created_at.is_a?(DateTime)
+ end
def logger
Log4r::Logger.new self.class.to_s
diff --git a/lib/mauve/http_server.rb b/lib/mauve/http_server.rb
index 21c89e5..cb705ea 100644
--- a/lib/mauve/http_server.rb
+++ b/lib/mauve/http_server.rb
@@ -87,6 +87,7 @@ module Mauve
attr_accessor :session_secret
def initialize
+ super
@port = 1288
@ip = "127.0.0.1"
@document_root = "/usr/share/mauvealert"
diff --git a/lib/mauve/mauve_thread.rb b/lib/mauve/mauve_thread.rb
index 79e742a..1aa8619 100644
--- a/lib/mauve/mauve_thread.rb
+++ b/lib/mauve/mauve_thread.rb
@@ -6,6 +6,7 @@ module Mauve
class MauveThread
def initialize
+ @thread = nil
end
def logger
@@ -58,7 +59,7 @@ module Mauve
end
def frozen?
- @frozen and @thread.stop?
+ defined? @frozen and @frozen and @thread.stop?
end
def thaw
@@ -86,6 +87,10 @@ module Mauve
@thread.is_a?(Thread) and @thread.alive?
end
+ def stop?
+ @thread.is_a?(Thread) and @thread.stop?
+ end
+
def join(ok_exceptions=[])
@thread.join if @thread.is_a?(Thread)
end
@@ -94,6 +99,10 @@ module Mauve
@thread.raise(ex)
end
+ def backtrace
+ @thread.backtrace if @thread.is_a?(Thread)
+ end
+
def restart
self.stop
self.start
diff --git a/lib/mauve/notification.rb b/lib/mauve/notification.rb
index 2f77a13..ed96f7e 100644
--- a/lib/mauve/notification.rb
+++ b/lib/mauve/notification.rb
@@ -44,10 +44,7 @@ module Mauve
plus_one_week = MauveTime.now + 604800 # ish
while offset < plus_one_week
offset += interval
- if DuringRunner.new(offset, @alert, &@during).now?
- @logger.debug("Found reminder time of #{offset}")
- return offset
- end
+ return offset if DuringRunner.new(offset, @alert, &@during).now?
end
@logger.info("Could not find a reminder time less than a week "+
"for #{@alert}.")
diff --git a/lib/mauve/notifier.rb b/lib/mauve/notifier.rb
index 90df895..e62f7f4 100644
--- a/lib/mauve/notifier.rb
+++ b/lib/mauve/notifier.rb
@@ -13,6 +13,7 @@ module Mauve
attr_accessor :sleep_interval
def initialize
+ super
end
def main_loop
@@ -22,9 +23,7 @@ module Mauve
sz = Server.notification_buffer_size
return if sz == 0
-
- logger.debug("Notifier buffer is #{sz} in length")
-
+
my_threads = []
sz.times do
person, *args = Server.notification_pop
diff --git a/lib/mauve/notifiers/email.rb b/lib/mauve/notifiers/email.rb
index 129afec..77b10f1 100644
--- a/lib/mauve/notifiers/email.rb
+++ b/lib/mauve/notifiers/email.rb
@@ -7,17 +7,9 @@ module Mauve
module Notifiers
module Email
-
- class Default
+ class Default
attr_reader :name
- attr :server, true
- attr :port, true
- attr :username, true
- attr :password, true
- attr :login_method, true
- attr :from, true
- attr :subject_prefix, true
- attr :email_suffix, true
+ attr_writer :server, :port, :password, :login_method, :from, :subject_prefix, :email_suffix
def username=(username)
@login_method ||= :plain
@@ -47,20 +39,15 @@ module Mauve
message = prepare_message(destination, alert, all_alerts, conditions)
args = [@server, @port]
args += [@username, @password, @login_method.to_sym] if @login_method
- history = Mauve::History.new(:alert => alert, :type => :notification)
begin
Net::SMTP.start(*args) do |smtp|
smtp.send_message(message, @from, destination)
end
- history.event = "Sent mail to #{destination}."
- history.save
true
rescue StandardError => ex
logger.error "SMTP failure: #{ex.to_s}"
logger.debug ex.backtrace.join("\n")
- history.event = "Failed to send mail to #{destination} due to #{ex.to_s}"
- history.save
false
end
end
diff --git a/lib/mauve/notifiers/sms_aql.rb b/lib/mauve/notifiers/sms_aql.rb
index b295e6c..dbda229 100644
--- a/lib/mauve/notifiers/sms_aql.rb
+++ b/lib/mauve/notifiers/sms_aql.rb
@@ -41,17 +41,12 @@ module Mauve
'Content-Length' => opts_string.length.to_s
})
- history = Mauve::History.new(:alert => alert, :type => :notification)
if response.kind_of?(Net::HTTPSuccess)
- history.event = "Sent SMS via AQL to #{destination}"
- history.save
#
# Woo -- return true!
#
true
else
- history.event = "Failed to send SMS via AQL to #{destination} due to #{response.class.to_s}"
- history.save
false
end
end
diff --git a/lib/mauve/notifiers/xmpp-smack.rb b/lib/mauve/notifiers/xmpp-smack.rb
deleted file mode 100644
index a160a35..0000000
--- a/lib/mauve/notifiers/xmpp-smack.rb
+++ /dev/null
@@ -1,395 +0,0 @@
-# encoding: utf-8
-
-# Ruby.
-require 'pp'
-require 'log4r'
-require 'monitor'
-
-# Java. Note that paths are mangeled in jmauve_starter.
-require 'java'
-require 'smack.jar'
-require 'smackx.jar'
-include_class "org.jivesoftware.smack.XMPPConnection"
-include_class "org.jivesoftware.smackx.muc.MultiUserChat"
-include_class "org.jivesoftware.smack.RosterListener"
-
-module Mauve
-
- module Notifiers
-
- module Xmpp
-
- class XMPPSmackException < StandardError
- end
-
- ## Main wrapper to smack java library.
- #
- # @author Yann Golanski
- # @see http://www.igniterealtime.org/builds/smack/docs/3.1.0/javadoc/
- #
- # This is a singleton which is not idea but works well for mauve's
- # configuration file set up.
- #
- # In general, this class is meant to be intialized then the method
- # create_slave_thread must be called. The latter will spawn a new
- # thread that will do the connecting and sending of messages to
- # the XMPP server. Once this is done, messages can be send via the
- # send_msg() method. Those will be queued and depending on the load,
- # should be send quickly enough. This is done so that the main thread
- # can not worry about sending messages and can do important work.
- #
- # @example
- # bot = Mauve::Notifiers::Xmpp::XMPPSmack.new()
- # bot.run_slave_thread("chat.bytemark.co.uk", 'mauvealert', 'TopSecret')
- # msg = "What fresh hell is this? -- Dorothy Parker."
- # bot.send_msg("yann@chat.bytemark.co.uk", msg)
- # bot.send_msg("muc:test@conference.chat.bytemark.co.uk", msg)
- #
- # @FIXME This won't quiet work with how mauve is set up.
- #
- class XMPPSmack
-
- # Globals are evil.
- @@instance = nil
-
- # Default constructor.
- #
- # A queue (@queue) is used to pass information between master/slave.
- def initialize ()
- extend(MonitorMixin)
- @logger = Log4r::Logger.new "mauve::XMPP_smack<#{Process.pid}>"
- @queue = Queue.new
- @xmpp = nil
- @name = "mauve alert"
- @slave_thread = nil
- @regexp_muc = Regexp.compile(/^muc\:/)
- @regexp_tail = Regexp.compile(/\/.*$/)
- @jid_created_chat = Hash.new()
- @separator = '<->'
- @logger.info("Created XMPPSmack singleton")
- end
-
- # Returns the instance of the XMPPSmack singleton.
- #
- # @param [String] login The JID as a full address.
- # @param [String] pwd The password corresponding to the JID.
- # @return [XMPPSmack] The singleton instance.
- def self.instance (login, pwd)
- if true == @@instance.nil?
- @@instance = XMPPSmack.new
- jid, tmp = login.split(/@/)
- srv, name = tmp.split(/\//)
- name = "Mauve Alert Bot" if true == name.nil?
- @@instance.run_slave_thread(srv, jid, pwd, name)
- sleep 5 # FIXME: This really should be synced... But how?
- end
- return @@instance
- end
-
- # Create the thread that sends messages to the server.
- #
- # @param [String] srv The server address.
- # @param [String] jid The JID.
- # @param [String] pwd The password corresponding to the JID.
- # @param [String] name The bot name.
- # @return [NULL] nada
- def run_slave_thread (srv, jid, pwd, name)
- @srv = srv
- @jid = jid
- @pwd = pwd
- @name = name
- @logger.info("Creating slave thread on #{@jid}@#{@srv}/#{@name}.")
- @slave_thread = Thread.new do
- self.create_slave_thread()
- end
- return nil
- end
-
- # Returns whether instance is connected and authenticated.
- #
- # @return [Boolean] True or false.
- def is_connected_and_authenticated? ()
- return false if true == @xmpp.nil?
- return (@xmpp.isConnected() and @xmpp.isAuthenticated())
- end
-
- # Creates the thread that does the actual sending to XMPP.
- # @return [NULL] nada
- def create_slave_thread ()
- begin
- @logger.info("Slave thread is now alive.")
- self.open()
- loop do
- rcp, msg = @queue.deq().split(@separator, 2)
- @logger.debug("New message for '#{rcp}' saying '#{msg}'.")
- if rcp.match(@regexp_muc)
- room = rcp.gsub(@regexp_muc, '').gsub(@regexp_tail, '')
- self.send_to_muc(room, msg)
- else
- self.send_to_jid(rcp, msg)
- end
- end
- rescue XMPPSmackException
- @logger.fatal("Something is wrong")
- ensure
- @logger.info("XMPP bot disconnect.")
- @xmpp.disconnect()
- end
- return nil
- end
-
- # Send a message to the recipient.
- #
- # @param [String] rcp The recipent MUC or JID.
- # @param [String] msg The message.
- # @return [NULL] nada
- def send_msg(rcp, msg)
- #if @slave_thread.nil? or not self.is_connected_and_authenticated?()
- # str = "There is either no slave thread running or a disconnect..."
- # @logger.warn(str)
- # self.reconnect()
- #end
- @queue.enq(rcp + @separator + msg)
- return nil
- end
-
- # Sends a message to a room.
- #
- # @param [String] room The name of the room.
- # @param [String] mgs The message to send.
- # @return [NULL] nada
- def send_to_muc (room, msg)
- if not @jid_created_chat.has_key?(room)
- @jid_created_chat[room] = MultiUserChat.new(@xmpp, room)
- @jid_created_chat[room].join(@name)
- end
- @logger.debug("Sending to MUC '#{room}' message '#{msg}'.")
- @jid_created_chat[room].sendMessage(msg)
- return nil
- end
-
- # Sends a message to a jid.
- #
- # Do not destroy the chat, we can reuse it when the user log back in again.
- # Maybe?
- #
- # @param [String] jid The JID of the recipient.
- # @param [String] mgs The message to send.
- # @return [NULL] nada
- def send_to_jid (jid, msg)
- if true == jid_is_available?(jid)
- if not @jid_created_chat.has_key?(jid)
- @jid_created_chat[jid] = @xmpp.getChatManager.createChat(jid, nil)
- end
- @logger.debug("Sending to JID '#{jid}' message '#{msg}'.")
- @jid_created_chat[jid].sendMessage(msg)
- end
- return nil
- end
-
- # Check to see if the jid is available or not.
- #
- # @param [String] jid The JID of the recipient.
- # @return [Boolean] Whether we can send a message or not.
- def jid_is_available?(jid)
- if true == @xmpp.getRoster().getPresence(jid).isAvailable()
- @logger.debug("#{jid} is available. Status is " +
- "#{@xmpp.getRoster().getPresence(jid).getStatus()}")
- return true
- else
- @logger.warn("#{jid} is not available. Status is " +
- "#{@xmpp.getRoster().getPresence(jid).getStatus()}")
- return false
- end
- end
-
- # Opens a connection to the xmpp server at given port.
- #
- # @return [NULL] nada
- def open()
- @logger.info("XMPP bot is being created.")
- self.open_connection()
- self.open_authentication()
- self.create_roster()
- sleep 5
- return nil
- end
-
- # Connect to server.
- #
- # @return [NULL] nada
- def open_connection()
- @xmpp = XMPPConnection.new(@srv)
- if false == self.connect()
- str = "Connection refused"
- @logger.error(str)
- raise XMPPSmackException.new(str)
- end
- @logger.debug("XMPP bot connected successfully.")
- return nil
- end
-
- # Authenticat connection.
- #
- # @return [NULL] nada
- def open_authentication()
- if false == self.login(@jid, @pwd)
- str = "Authentication failed"
- @logger.error(str)
- raise XMPPSmackException.new(str)
- end
- @logger.debug("XMPP bot authenticated successfully.")
- return nil
- end
-
- # Create a new roster and listener.
- #
- # @return [NULL] nada
- def create_roster
- @xmpp.getRoster().addRosterListener(RosterListener.new())
- @xmpp.getRoster().reload()
- @xmpp.getRoster().getPresence(@xmpp.getUser).setStatus(
- "Purple alert! Purple alert!")
- @logger.debug("XMPP bot roster aquired successfully.")
- return nil
- end
-
- # Connects to the server.
- #
- # @return [Boolean] true (aka sucess) or false (aka failure).
- def connect ()
- @xmpp.connect()
- return @xmpp.isConnected()
- end
-
- # Login onto the server.
- #
- # @param [String] jid The JID.
- # @param [String] pwd The password corresponding to the JID.
- # @return [Boolean] true (aka sucess) or false (aka failure).
- def login (jid, pwd)
- @xmpp.login(jid, pwd, @name)
- return @xmpp.isAuthenticated()
- end
-
- # Reconnects in case of errors.
- #
- # @return [NULL] nada
- def reconnect()
- @xmpp.disconnect
- @slave_thread = Thread.new do
- self.create_slave_thread()
- end
- return nil
- end
-
- def presenceChanged ()
- end
-
- end # XMPPSmack
-
-
- ## This is the class that gets called in person.rb.
- #
- # This class is a wrapper to XMPPSmack which does the hard work. It is
- # done this way to conform to the mauve configuration file way of
- # defining notifications.
- #
- # @author Yann Golanski
- class Default
-
- # Name of the class.
- attr_reader :name
-
- # Atrtribute.
- attr_accessor :jid
-
- # Atrtribute.
- attr_accessor :password
-
- # Atrtribute.
- attr_accessor :initial_jid
-
- # Atrtribute.
- attr_accessor :initial_messages
-
- # Default constructor.
- #
- # @param [String] name The name of the notifier.
- def initialize (name)
- extend(MonitorMixin)
- @name = name
- @logger = Log4r::Logger.new "mauve::XMPP_default<#{Process.pid}>"
- end
-
- # Sends a message to the relevant jid or muc.
- #
- # We have no way to know if a messages was recieved, only that
- # we send it.
- #
- # @param [String] destionation
- # @param [Alert] alert A mauve alert class
- # @param [Array] all_alerts subset of current alerts
- # @param [Hash] conditions Supported conditions, see above.
- # @return [Boolean] Whether a message can be send or not.
- def send_alert(destination, alert, all_alerts, conditions = nil)
- synchronize {
- client = XMPPSmack.instance(@jid, @password)
- if not destination.match(/^muc:/)
- if false == client.jid_is_available?(destination.gsub(/^muc:/, ''))
- return false
- end
- end
- client.send_msg(destination, convert_alert_to_message(alert))
- return true
- }
- end
-
- # Takes an alert and converts it into a message.
- #
- # @param [Alert] alert The alert to convert.
- # @return [String] The message, either as HTML.
- def convert_alert_to_message(alert)
- arr = alert.summary_three_lines
- str = arr[0] + ": " + arr[1]
- str += " -- " + arr[2] if false == arr[2].nil?
- str += "."
- return str
- #return alert.summary_two_lines.join(" -- ")
- #return "<p>" + alert.summary_two_lines.join("<br />") + "</p>"
- end
-
- # This is so unit tests can run fine.
- include Debug
-
- end # Default
-
- end
- end
-end
-
-# This is a simple example of usage. Run with:
-# ../../../jmauve_starter.rb xmpp-smack.rb
-# Clearly, the mauve jabber password is not correct.
-#
-# /!\ WARNING: DO NOT COMMIT THE REAL PASSWORD TO MERCURIAL!!!
-#
-def send_msg()
- bot = Mauve::Notifiers::Xmpp::XMPPSmack.instance(
- "mauvealert@chat.bytemark.co.uk/testing1234", '')
- msg = "What fresh hell is this? -- Dorothy Parker."
- bot.send_msg("yann@chat.bytemark.co.uk", msg)
- bot.send_msg("muc:test@conference.chat.bytemark.co.uk", msg)
- sleep 2
-end
-
-if __FILE__ == './'+$0
- Thread.abort_on_exception = true
- logger = Log4r::Logger.new('mauve')
- logger.level = Log4r::DEBUG
- logger.add Log4r::Outputter.stdout
- send_msg()
- send_msg()
- logger.info("START")
- logger.info("END")
-end
diff --git a/lib/mauve/notifiers/xmpp.rb b/lib/mauve/notifiers/xmpp.rb
index c4e1785..8131096 100644
--- a/lib/mauve/notifiers/xmpp.rb
+++ b/lib/mauve/notifiers/xmpp.rb
@@ -66,10 +66,10 @@ module Mauve
include Jabber
# Atrtribute.
- attr_reader :name
+ attr_reader :name, :jid
# Atrtribute.
- attr_accessor :jid, :password
+ attr_accessor :password
def initialize(name)
Jabber::logger = self.logger
@@ -80,7 +80,7 @@ module Mauve
@mucs = {}
@roster = nil
@closing = false
-
+ @client = nil
end
def logger
@@ -93,7 +93,7 @@ module Mauve
end
def connect
- logger.info "Jabber starting connection to #{@jid}"
+ logger.debug "Starting connection to #{@jid}"
# Make sure we're disconnected.
self.close if @client.is_a?(Client)
@@ -110,7 +110,6 @@ module Mauve
# already
@roster.add_subscription_request_callback do |ri, presence|
Thread.new do
- logger.debug "Known? #{is_known_contact?(presence.from).inspect}"
if is_known_contact?(presence.from)
logger.info("Accepting subscription request from #{presence.from}")
@roster.accept_subscription(presence.from)
@@ -127,10 +126,11 @@ module Mauve
end
@roster.wait_for_roster
- logger.debug "Jabber authenticated, setting presence"
@client.send(Presence.new(nil, "Woo!").set_type(nil))
+ logger.info "Connected as #{@jid}"
+
@client.on_exception do |ex, stream, where|
#
# The XMPP4R exception clauses in Stream all close the stream, so
@@ -203,17 +203,7 @@ module Mauve
alert.to_s
end
- history = Mauve::History.new(:alert_id => alert.id, :type => :notification)
-
- if send_message(destination_jid, txt)
- history.event = "Sent XMPP message to #{destination_jid}"
- history.save
- true
- else
- history.event = "Failed to send XMPP message to #{destination_jid}"
- history.save
- false
- end
+ send_message(destination_jid, txt)
end
# Sends a message to the destionation.
@@ -297,12 +287,12 @@ module Mauve
end
if !@mucs[jid.strip].active?
- logger.info("Joining #{jid}")
#
# Make sure we have a resource.
#
@mucs[jid.strip].join(jid, password)
+ logger.info("Joined #{jid}")
else
logger.debug("Already joined #{jid}.")
end
diff --git a/lib/mauve/people_list.rb b/lib/mauve/people_list.rb
index 23e0c1e..32e0708 100644
--- a/lib/mauve/people_list.rb
+++ b/lib/mauve/people_list.rb
@@ -34,11 +34,16 @@ module Mauve
# Return the array of people
#
def people
- logger.warn "No-one found in the people list for #{self.label}" if self.list.empty?
- list.collect do |name|
+ l = list.collect do |name|
Configuration.current.people.has_key?(name) ? Configuration.current.people[name] : nil
end.reject{|person| person.nil?}
+ #
+ # Hmm.. no-one in the list?!
+ #
+ logger.warn "No-one found in the people list for #{self.label}" if l.empty?
+
+ l
end
end
diff --git a/lib/mauve/person.rb b/lib/mauve/person.rb
index 0290faf..cf29ff9 100644
--- a/lib/mauve/person.rb
+++ b/lib/mauve/person.rb
@@ -63,9 +63,13 @@ module Mauve
# and turn them into false.
#
res = notification_method.send_alert(destination, @alert, @other_alerts, conditions)
+
#
# Log the result
- logger.debug "Notification " + (res ? "succeeded" : "failed" ) + " for #{@person.username} using notifier '#{name}' to '#{destination}'"
+ note = "#{@alert.update_type.upcase}: notification " + (res ? "succeeded" : "failed" ) + " for #{@person.username} using notifier '#{name}' to '#{destination}'."
+ logger.info note
+ h = History.new(:alert_id => @alert.id, :type => "notification", :event => note)
+ logger.error "Unable to save history due to #{h.errors.inspect}" if !h.save
res
end
@@ -144,7 +148,6 @@ module Mauve
end
def remind(alert, level)
- logger.debug("Reminder for #{alert} send at level #{level}.")
send_alert(level, alert)
end
@@ -153,45 +156,45 @@ module Mauve
#
def send_alert(level, alert)
now = MauveTime.now
- suppressed_changed = nil
+
threshold_breached = @notification_thresholds.any? do |period, previous_alert_times|
first = previous_alert_times.first
first.is_a?(MauveTime) and (now - first) < period
end
- this_alert_suppressed = false
+ was_suppressed = self.suppressed?
if Server.instance.started_at > alert.updated_at.to_time and (Server.instance.started_at + Server.instance.initial_sleep) > MauveTime.now
- logger.warn("Alert last updated in prior run of mauve -- ignoring for initial sleep period.")
- this_alert_suppressed = true
- elsif threshold_breached
- unless suppressed?
- logger.warn("Suspending notifications to #{username} until further notice.")
- suppressed_changed = true
- end
+ logger.info("Alert last updated in prior run of mauve -- ignoring for initial sleep period.")
+ return
+ end
+
+ if threshold_breached
+ logger.info("Suspending notifications to #{username} until further notice.") unless was_suppressed
@suppressed = true
+
else
- if suppressed?
- suppressed_changed = false
- logger.warn "Starting to send notifications again for #{username}."
- else
- logger.info "Notifying #{username} of #{alert} at level #{level}"
- end
+ logger.info "Starting to send notifications again for #{username}." if was_suppressed
@suppressed = false
+
end
- return if suppressed? or this_alert_suppressed
+ #
+ # We only suppress notifications if we were suppressed before we started,
+ # and are still suppressed.
+ #
+ return if was_suppressed and self.suppressed?
- Server.notification_push([self, level, alert, suppressed_changed])
+ Server.notification_push([self, level, alert, was_suppressed])
end
- def do_send_alert(level, alert, suppressed_changed)
+ def do_send_alert(level, alert, was_suppressed)
result = NotificationCaller.new(
self,
alert,
current_alerts,
Configuration.current.notification_methods,
- :suppressed_changed => suppressed_changed
+ :was_suppressed => was_suppressed
).instance_eval(&__send__(level))
if result
@@ -205,10 +208,9 @@ module Mauve
@notification_thresholds[period].push MauveTime.now
@notification_thresholds[period].shift
end
-
- logger.info("Notification for #{username} of #{alert} at level #{level} has been successful")
+ true
else
- logger.error("Failed to notify #{username} about #{alert} at level #{level}")
+ false
end
end
diff --git a/lib/mauve/processor.rb b/lib/mauve/processor.rb
index 083b9a1..f36dacb 100644
--- a/lib/mauve/processor.rb
+++ b/lib/mauve/processor.rb
@@ -11,9 +11,7 @@ module Mauve
attr_accessor :transmission_cache_expire_time, :sleep_interval
def initialize
- # Set the logger up
- @logger = Log4r::Logger.new(self.class.to_s)
-
+ super
#
# Set up the transmission id cache
#
@@ -22,10 +20,11 @@ module Mauve
@transmission_cache_checked_at = Time.now
end
- def main_loop
-
- logger.info("Buffer has packets waiting...") if Server.packet_buffer_size > 0
+ def logger
+ @logger ||= Log4r::Logger.new(self.class.to_s)
+ end
+ def main_loop
#
# Only do the loop a maximum of 10 times every @sleep_interval seconds
#
@@ -39,7 +38,9 @@ module Mauve
Timer.instance.freeze unless Timer.instance.frozen?
- @logger.debug("Got #{data.inspect} from #{client.inspect}")
+ raise ArgumentError, "arse"
+
+ logger.debug("Got #{data.inspect} from #{client.inspect}")
ip_source = "#{client[3]}:#{client[1]}"
update = Proto::AlertUpdate.new
@@ -48,14 +49,14 @@ module Mauve
update.parse_from_string(data)
if @transmission_id_cache[update.transmission_id.to_s]
- @logger.debug("Ignoring duplicate transmission id #{update.transmission_id}")
+ logger.info("Ignoring duplicate transmission id #{update.transmission_id}")
#
# Continue with next packet.
#
next
end
- @logger.debug "Update #{update.transmission_id} sent at #{update.transmission_time} from "+
+ logger.info "Update #{update.transmission_id} sent at #{update.transmission_time} from "+
"'#{update.source}'@#{ip_source} alerts #{update.alert.length}"
Alert.receive_update(update, received_at)
@@ -64,10 +65,10 @@ module Mauve
NotImplementedError,
DataObjects::IntegrityError => ex
- @logger.error "#{ex} (#{ex.class}) while parsing #{data.length} bytes "+
+ logger.error "#{ex} (#{ex.class}) while parsing #{data.length} bytes "+
"starting '#{data[0..15].inspect}' from #{ip_source}"
- @logger.debug ex.backtrace.join("\n")
+ logger.debug ex.backtrace.join("\n")
ensure
@transmission_id_cache[update.transmission_id.to_s] = MauveTime.now
diff --git a/lib/mauve/sender.rb b/lib/mauve/sender.rb
index 122456c..ad047fe 100644
--- a/lib/mauve/sender.rb
+++ b/lib/mauve/sender.rb
@@ -3,7 +3,6 @@ require 'ipaddr'
require 'resolv'
require 'socket'
require 'mauve/mauve_time'
-require 'pp'
module Mauve
class Sender
diff --git a/lib/mauve/server.rb b/lib/mauve/server.rb
index 51587c0..4bd5a0f 100644
--- a/lib/mauve/server.rb
+++ b/lib/mauve/server.rb
@@ -43,7 +43,7 @@ module Mauve
# Sleep time between pooling the @buffer buffer.
@sleep = 1
- @freeze = false
+ @frozen = false
@stop = false
@stopped_at = MauveTime.now
@@ -166,7 +166,7 @@ module Mauve
begin
klass.instance.join
rescue StandardError => ex
- logger.warn "Caught #{ex.to_s} whilst checking #{klass} thread"
+ logger.error "Caught #{ex.to_s} whilst checking #{klass} thread"
logger.debug ex.backtrace.join("\n")
end
@@ -177,7 +177,8 @@ module Mauve
end
#
- # Now do the same with other threads.
+ # Now do the same with other threads. However if these ones crash, the
+ # server has to stop, as there is no method to restart them.
#
thread_list.each do |t|
diff --git a/lib/mauve/timer.rb b/lib/mauve/timer.rb
index 40abe43..f6ada88 100644
--- a/lib/mauve/timer.rb
+++ b/lib/mauve/timer.rb
@@ -14,6 +14,7 @@ module Mauve
attr_accessor :sleep_interval, :last_run_at
def initialize
+ super
@initial_sleep = 300
@initial_sleep_threshold = 300
end
@@ -29,7 +30,6 @@ module Mauve
# look for the next alert_changed object.
#
if next_alert.nil? or next_alert.due_at > MauveTime.now
- logger.debug("Next alert was #{next_alert} due at #{next_alert.due_at}") unless next_alert.nil?
next_alert_changed = AlertChanged.find_next_with_event
end
@@ -51,12 +51,12 @@ module Mauve
#
# Sleep indefinitely
#
- logger.debug("Nothing to notify about -- snoozing indefinitely.")
+ logger.info("Nothing to notify about -- snoozing indefinitely.")
else
#
# La la la nothing to do.
#
- logger.debug("Next to notify: #{next_to_notify} -- snoozing until #{next_to_notify.due_at}")
+ logger.info("Next to notify: #{next_to_notify} -- snoozing until #{next_to_notify.due_at}")
end
#
diff --git a/lib/mauve/udp_server.rb b/lib/mauve/udp_server.rb
index 59bc5bc..8649efe 100644
--- a/lib/mauve/udp_server.rb
+++ b/lib/mauve/udp_server.rb
@@ -15,6 +15,7 @@ module Mauve
attr_accessor :ip, :port, :sleep_interval
def initialize
+ super
#
# Set the logger up
#
@@ -49,7 +50,7 @@ module Mauve
@socket.bind(@ip, @port)
- logger.debug("Successfully opened UDP socket on #{@ip}:#{@port}")
+ logger.info("Successfully opened UDP socket on #{@ip}:#{@port}")
end
def close_socket
@@ -59,10 +60,11 @@ module Mauve
@socket.close
rescue IOError => ex
# Just in case there is some sort of explosion!
- logger.debug("Caught IOError #{ex.to_s}")
+ logger.error "Caught IOError #{ex.to_s}"
+ logger.debug ex.backtrace.join("\n")
end
- logger.debug("Successfully closed UDP socket")
+ logger.info("Successfully closed UDP socket")
end
def main_loop
diff --git a/lib/mauve/web_interface.rb b/lib/mauve/web_interface.rb
index 3770924..4594e10 100644
--- a/lib/mauve/web_interface.rb
+++ b/lib/mauve/web_interface.rb
@@ -185,6 +185,7 @@ EOF
n_hours = params[:n_hours] || 2
type_hours = params[:type_hours] || "daylight"
alerts = params[:alerts] || []
+ note = params[:note] || nil
n_hours = (n_hours.to_i > 188 ? 188 : n_hours.to_i)
@@ -196,18 +197,28 @@ EOF
succeeded = []
failed = []
-
+
alerts.each do |k,v|
begin
a = Alert.get!(k.to_i)
rescue DataMapper::ObjectNotFoundError => ex
failed << ex
+ next
end
+ logger.debug "arse"
+
begin
a.acknowledge!(@person, ack_until)
+ logger.debug note
+ unless note.to_s.empty?
+ h = History.new(:alert_id => a.id, :type => "note", :event => note.to_s)
+ logger.debug h.errors unless h.save
+ end
succeeded << a
rescue StandardError => ex
+ logger.error "Caught #{ex.to_s} when trying to save #{a.inspect}"
+ logger.debug ex.backtrace.join("\n")
failed << ex
end
end
@@ -454,14 +465,15 @@ EOF
result = begin
auth.authenticate(usr,pwd)
rescue Exception => ex
- @logger.debug "Caught exception during Bytemark auth for #{usr} (#{ex.to_s})"
+ logger.error "Caught exception during Bytemark auth for #{usr} (#{ex.to_s})"
+ logger.debug ex.backtrace.join("\n")
false
end
if true == result
return true
else
- @logger.debug "Bytemark authentication failed for #{usr}"
+ logger.warn "Bytemark authentication failed for #{usr}"
end
#
@@ -472,14 +484,15 @@ EOF
Digest::SHA1.hexdigest(params['password']) == Configuration.current.people[usr].password
end
rescue Exception => ex
- @logger.debug "Caught exception during local auth for #{usr} (#{ex.to_s})"
+ logger.error "Caught exception during local auth for #{usr} (#{ex.to_s})"
+ logger.debug ex.backtrace.join("\n")
false
end
if true == result
return true
else
- @logger.debug "Local authentication failed for #{usr}"
+ logger.warn "Local authentication failed for #{usr}"
end
#