aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--debian/changelog6
-rw-r--r--lib/mauve/alert.rb12
-rw-r--r--lib/mauve/history.rb33
-rw-r--r--lib/mauve/version.rb2
-rw-r--r--lib/mauve/web_interface.rb148
-rw-r--r--static/stylesheets/mauve.css18
-rw-r--r--views/_events_calendar.haml11
-rw-r--r--views/_events_calendar_day.haml14
-rw-r--r--views/_events_calendar_week.haml2
-rw-r--r--views/_events_form.haml13
-rw-r--r--views/_navbar.haml2
l---------views/events.haml1
-rw-r--r--views/events_calendar.haml11
-rw-r--r--views/events_list.haml18
14 files changed, 272 insertions, 19 deletions
diff --git a/debian/changelog b/debian/changelog
index 21f2cbc..184cb6c 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,3 +1,9 @@
+mauvealert (3.4.4) stable; urgency=low
+
+ * Added events calendar
+
+ -- Patrick J Cherry <patrick@bytemark.co.uk> Tue, 23 Aug 2011 18:24:52 +0100
+
mauvealert (3.4.3) stable; urgency=low
* Fixed notification race-conditions.
diff --git a/lib/mauve/alert.rb b/lib/mauve/alert.rb
index c294e8c..75aa35e 100644
--- a/lib/mauve/alert.rb
+++ b/lib/mauve/alert.rb
@@ -60,10 +60,10 @@ module Mauve
include DataMapper::Resource
property :id, Serial
- property :alert_id, String, :required => true, :unique_index => :alert_index, :length=>256
- property :source, String, :required => true, :unique_index => :alert_index, :length=>512
- property :subject, String, :length=>512
- property :summary, String, :length=>1024
+ property :alert_id, String, :required => true, :unique_index => :alert_index, :length=>256, :lazy => false
+ property :source, String, :required => true, :unique_index => :alert_index, :length=>512, :lazy => false
+ property :subject, String, :length=>512, :lazy => false
+ property :summary, String, :length=>1024, :lazy => false
property :detail, Text, :length=>65535
property :importance, Integer, :default => 50
@@ -71,8 +71,8 @@ module Mauve
property :cleared_at, Time
property :updated_at, Time
property :acknowledged_at, Time
- property :acknowledged_by, String
- property :update_type, String
+ property :acknowledged_by, String, :lazy => false
+ property :update_type, String, :lazy => false
property :will_clear_at, Time
property :will_raise_at, Time
diff --git a/lib/mauve/history.rb b/lib/mauve/history.rb
index 91a6fdc..74c5e3a 100644
--- a/lib/mauve/history.rb
+++ b/lib/mauve/history.rb
@@ -10,8 +10,8 @@ module Mauve
property :alert_id, Integer, :key => true
property :history_id, Integer, :key => true
- belongs_to :alert
- belongs_to :history
+ belongs_to :alert
+ belongs_to :history
def self.migrate!
#
@@ -53,8 +53,8 @@ module Mauve
# If these properties change.. then the migration above will break horribly. FIXME.
#
property :id, Serial
- property :type, String, :required => true, :default => "unknown"
- property :event, Text, :required => true, :default => "Nothing set"
+ property :type, String, :required => true, :default => "unknown", :lazy => false
+ property :event, Text, :required => true, :default => "Nothing set", :lazy => false
property :created_at, Time, :required => true
has n, :alerts, :through => :alerthistory
@@ -88,9 +88,32 @@ module Mauve
def set_created_at(context = :default)
self.created_at = Time.now unless self.created_at.is_a?(Time)
end
-
+
public
+ #
+ # Blasted datamapper not eager-loading my model.
+ #
+ def add_to_cached_alerts(a)
+ @cached_alerts ||= []
+ if a.is_a?(Array) and a.all?{|m| m.is_a?(Alert)}
+ @cached_alerts += a
+ elsif a.is_a?(Alert)
+ @cached_alerts << a
+ else
+ raise ArgumentError, "#{a.inspect} not an Alert"
+ end
+ end
+
+ def alerts
+ @cached_alerts ||= super
+ end
+
+ def reload
+ @cached_alerts = nil
+ super
+ end
+
def logger
Log4r::Logger.new self.class.to_s
end
diff --git a/lib/mauve/version.rb b/lib/mauve/version.rb
index 7e94be0..7571fea 100644
--- a/lib/mauve/version.rb
+++ b/lib/mauve/version.rb
@@ -1,5 +1,5 @@
module Mauve
- VERSION="3.4.3"
+ VERSION="3.4.4"
end
diff --git a/lib/mauve/web_interface.rb b/lib/mauve/web_interface.rb
index fb82f2e..386dfac 100644
--- a/lib/mauve/web_interface.rb
+++ b/lib/mauve/web_interface.rb
@@ -394,13 +394,92 @@ EOF
end
########################################################################
-
- get '/events' do
- find_active_alerts
- find_recent_alerts
- haml :events
+
+
+
+ get '/events/alert/:id' do
+
end
-
+
+ get '/events/calendar' do
+ redirect "/events/calendar/"+Time.now.strftime("%Y-%m")
+ end
+
+ get '/events/calendar/:start' do
+
+ #
+ # Sort out the parameters
+ #
+
+ #
+ # Start must be a Monday
+ #
+ if params[:start] =~ /\A(\d{4,4})-(\d{1,2})/
+ @month = Time.local($1.to_i,$2.to_i,1,0,0,0,0)
+ else
+ t = Time.now
+ @month = Time.local(t.year, t.month, 1, 0, 0, 0, 0)
+ end
+
+ start = @month
+ finish = start + 31.days
+
+ start -= (start.wday == 0 ? 6 : (start.wday - 1)).day
+ finish -= finish.day if finish.month == @month.month+1
+ finish += (finish.wday == 0 ? 0 : (7 - finish.wday)).days
+
+ weeks = ((finish - start)/1.week).ceil
+
+ query = {:history => {}}
+ query[:history][:created_at.gte] = start
+ query[:history][:created_at.lt] = finish
+
+ #
+ # Now sort events into a per-week per-weekday array. Have to use the
+ # proc syntax here to prevent an array of pointers being created..?!
+ #
+ @events = find_events(query)
+ @events_by_week = Array.new(weeks){ Array.new(7) { Array.new } }
+
+ @events.each do |event|
+ event_week = ((event.created_at - start)/(7.days)).floor
+ event_day = (event.created_at.wday == 0 ? 6 : (event.created_at.wday - 1))
+ @events_by_week[event_week] ||= Array.new(7) { Array.new }
+ @events_by_week[event_week][event_day] << event
+ end
+
+ #
+ # Make sure we have all our weeks filled out.
+ #
+ @events_by_week.each_with_index do |e, i|
+ @events_by_week[i] = Array.new(7) { Array.new } if e.nil?
+ end
+
+ @today = start
+ haml :events_calendar
+ end
+
+ get '/events/list' do
+ redirect "/events/list/"+Time.now.strftime("%Y-%m-%d")
+ end
+
+ get '/events/list/:start' do
+ if params[:start] =~ /\A(\d{4,4})-(\d{1,2})-(\d{1,2})\Z/
+ @start = Time.local($1.to_i,$2.to_i,$3.to_i,0,0,0,0)
+ else
+ t = Time.now
+ @start = Time.local(t.year, t.month, t.day, 0,0,0,0)
+ end
+
+ query = {:history => {}}
+ query[:history][:created_at.gte] = @start
+ query[:history][:created_at.lt] = @start + 1.day
+
+ @events = find_events(query)
+
+ haml :events_list
+ end
+
########################################################################
helpers do
@@ -475,6 +554,63 @@ EOF
list[@cycle]
end
+ def find_events(query = Hash.new)
+
+ if params["history"]
+ query[:history] ||= Hash.new
+
+ if params["history"]["type"] and !params["history"]["type"].empty?
+ query[:history][:type] = params["history"]["type"]
+ end
+ end
+
+ if !query[:history] or !query[:history][:type]
+ query[:history] ||= Hash.new
+ query[:history][:type] = "update"
+
+ params["history"] ||= Hash.new
+ params["history"]["type"] = "update"
+ end
+
+ if params["alert"]
+ query[:alert] ||= Hash.new
+
+ if params["alert"]["subject"] and !params["alert"]["subject"].empty?
+ query[:alert][:subject.like] = params["alert"]["subject"]
+ end
+
+ if params["alert"]["source"] and !params["alert"]["source"].empty?
+ query[:alert][:source.like] = params["alert"]["source"]
+ end
+
+ if params["alert"]["id"] and !params["alert"]["id"].empty?
+ query[:alert][:id] = params["alert"]["id"]
+ end
+ end
+
+ #
+ #
+ # THIS IS NOT EAGER LOADING. But I've no idea how the best way would be to do it.
+ #
+ alert_histories = AlertHistory.all(query)
+
+ histories = alert_histories.history.to_a
+ alerts = alert_histories.alert.to_a
+
+
+ alert_histories.each do |ah|
+ history = histories.find{|h| ah.history_id == h.id}
+ alert = alerts.find{|a| ah.alert_id == a.id}
+ next if alert.nil?
+ history.add_to_cached_alerts( alert )
+ end
+
+ #
+ # Present the histories in time-ascending order (which is not the default..)
+ #
+ histories.reverse
+ end
+
end
error DataMapper::ObjectNotFoundError do
diff --git a/static/stylesheets/mauve.css b/static/stylesheets/mauve.css
index 50f5da3..4649775 100644
--- a/static/stylesheets/mauve.css
+++ b/static/stylesheets/mauve.css
@@ -79,4 +79,22 @@ div.flash p {
background-color: transparent;
}
+table#events_table td {
+ width: 14%;
+ border-left: solid;
+}
+
+table#events_table td p.event_date {
+ font-weight: bold;
+ font-size: smaller;
+}
+
+p {
+ background-color: inherit;
+}
+
+.even {
+ background-color: #ddd;
+}
+
diff --git a/views/_events_calendar.haml b/views/_events_calendar.haml
new file mode 100644
index 0000000..a0ec12b
--- /dev/null
+++ b/views/_events_calendar.haml
@@ -0,0 +1,11 @@
+%table#events_table
+ %tr
+ %th Monday
+ %th Tuesday
+ %th Wednesday
+ %th Thursday
+ %th Friday
+ %th Saturday
+ %th Sunday
+ = partial("events_calendar_week", :collection => @events_by_week )
+
diff --git a/views/_events_calendar_day.haml b/views/_events_calendar_day.haml
new file mode 100644
index 0000000..9682b56
--- /dev/null
+++ b/views/_events_calendar_day.haml
@@ -0,0 +1,14 @@
+%td{:class => (@today.month % 2 == 0 ? "even" : "odd")}
+ %p.event_date
+ %a{:href => "/events/list/#{@today.strftime("%Y-%m-%d")}?#{request.query_string}"}
+ = @today.strftime(((@today - 1.day).month != @today.month) ? "%d %b" : "%d")
+ =partial("history", :collection => events_calendar_day.first(10))
+ %p
+ - if events_calendar_day.length > 10
+ There are
+ = events_calendar_day.length - 10
+ more events to display.
+ - if events_calendar_day.length > 0
+ %a{:href => "/events/list/#{@today.strftime("%Y-%m-%d")}?#{request.query_string}"}
+ Show the whole day.
+ - @today += 1.day
diff --git a/views/_events_calendar_week.haml b/views/_events_calendar_week.haml
new file mode 100644
index 0000000..dd3bb6a
--- /dev/null
+++ b/views/_events_calendar_week.haml
@@ -0,0 +1,2 @@
+%tr
+ = partial("events_calendar_day", :collection => events_calendar_week)
diff --git a/views/_events_form.haml b/views/_events_form.haml
new file mode 100644
index 0000000..8eb9112
--- /dev/null
+++ b/views/_events_form.haml
@@ -0,0 +1,13 @@
+%form{:method => "GET", :action => ""}
+ %label{:for => "subject"}
+ Subject
+ %input{:type => "text", :id => "subject", :name => "alert[subject]", :value => (params["alert"] ? params["alert"]["subject"]: "") }
+ %label{:for => "source"}
+ Source
+ %input{:type => "text", :id => "subject", :name => "alert[source]", :value => (params["alert"] ? params["alert"]["source"] : "") }
+ - Mauve::History.all(:fields => [:type], :unique => true).collect{|h| h.type}.each do |history_type|
+ %label{:for => "history_"+history_type}
+ = history_type.capitalize
+ %input{:type => "checkbox", :name => "history[type][]", :value => "#{history_type}", :checked => (params["history"] && params["history"]["type"].is_a?(Array) ? params["history"]["type"].include?(history_type) : false) }
+ %input{:type => "submit", :value => "Go!"}
+
diff --git a/views/_navbar.haml b/views/_navbar.haml
index aa2b5f5..8b16c55 100644
--- a/views/_navbar.haml
+++ b/views/_navbar.haml
@@ -18,6 +18,8 @@
Cleared (
%span#count_cleared><= @alerts_cleared.length
)
+ %li{:class => [ request.path_info =~ /^\/events/ && "nav_selected"]}
+ %a{:href => '/events/calendar'} Events
%li
%a{:href => '/logout'} Log out
%br
diff --git a/views/events.haml b/views/events.haml
deleted file mode 120000
index 3b8d2e2..0000000
--- a/views/events.haml
+++ /dev/null
@@ -1 +0,0 @@
-not_implemented.haml \ No newline at end of file
diff --git a/views/events_calendar.haml b/views/events_calendar.haml
new file mode 100644
index 0000000..e3cec5e
--- /dev/null
+++ b/views/events_calendar.haml
@@ -0,0 +1,11 @@
+%h2
+ Events Calendar
+
+%p
+ %a{:href => "/events/calendar/#{(@month-31.days).strftime("%Y-%m")}?"+request.query_string}
+ &larr; Previous Month
+ = @month.strftime("%b %Y")
+ %a{:href => "/events/calendar/#{(@month+31.days).strftime("%Y-%m")}?"+request.query_string}
+ Next month &rarr;
+= partial('events_form')
+= partial('events_calendar')
diff --git a/views/events_list.haml b/views/events_list.haml
new file mode 100644
index 0000000..008b667
--- /dev/null
+++ b/views/events_list.haml
@@ -0,0 +1,18 @@
+%h2
+ Events List
+%p
+ %a{:href => "/events/list/#{(@start-1.day-10).strftime("%Y-%m-%d")}?"+request.query_string}
+ &larr; Previous day
+ = @start.strftime("%Y-%m-%d")
+ %a{:href => "/events/list/#{(@start+1.day+10).strftime("%Y-%m-%d")}?"+request.query_string}
+ Next day &rarr;
+ |
+ %a{:href => "/events/calendar/#{@start.strftime("%Y-%m")}?"+request.query_string}
+ Calendar view
+= partial('events_form')
+- if @events.length > 0
+ = partial('history', :collection => @events)
+- else
+ %p
+ %strong
+ No events for today.