diff options
author | Patrick J Cherry <patrick@bytemark.co.uk> | 2011-08-23 18:35:48 +0100 |
---|---|---|
committer | Patrick J Cherry <patrick@bytemark.co.uk> | 2011-08-23 18:35:48 +0100 |
commit | 1a636d2c97368bc4c4019f4ddcff991ec5eccbce (patch) | |
tree | b8101b2739ddfed34f3f80b5c89fa15de5470739 | |
parent | f9bab2fc3dcef0b452782de662ee7739a547079a (diff) |
Added events viewer
* Fixes #1286
* Version bump
-rw-r--r-- | debian/changelog | 6 | ||||
-rw-r--r-- | lib/mauve/alert.rb | 12 | ||||
-rw-r--r-- | lib/mauve/history.rb | 33 | ||||
-rw-r--r-- | lib/mauve/version.rb | 2 | ||||
-rw-r--r-- | lib/mauve/web_interface.rb | 148 | ||||
-rw-r--r-- | static/stylesheets/mauve.css | 18 | ||||
-rw-r--r-- | views/_events_calendar.haml | 11 | ||||
-rw-r--r-- | views/_events_calendar_day.haml | 14 | ||||
-rw-r--r-- | views/_events_calendar_week.haml | 2 | ||||
-rw-r--r-- | views/_events_form.haml | 13 | ||||
-rw-r--r-- | views/_navbar.haml | 2 | ||||
l--------- | views/events.haml | 1 | ||||
-rw-r--r-- | views/events_calendar.haml | 11 | ||||
-rw-r--r-- | views/events_list.haml | 18 |
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} + ← Previous Month + = @month.strftime("%b %Y") + %a{:href => "/events/calendar/#{(@month+31.days).strftime("%Y-%m")}?"+request.query_string} + Next month → += 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} + ← Previous day + = @start.strftime("%Y-%m-%d") + %a{:href => "/events/list/#{(@start+1.day+10).strftime("%Y-%m-%d")}?"+request.query_string} + Next day → + | + %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. |