Scott Seago
2009-Jan-12 15:19 UTC
[Ovirt-devel] [PATCH] Add task list to dashboard (revised)
Refactored task list functionality to allow for the dashboard-level task list. The dashboard task list shows all tasks initiated by the logged-in user, and is filterable by task type and state. revised to fix a couple bugs found by lutter Signed-off-by: Scott Seago <sseago at redhat.com> --- src/app/controllers/dashboard_controller.rb | 41 +++++++--- src/app/controllers/hardware_controller.rb | 12 +--- src/app/controllers/pool_controller.rb | 41 ++-------- src/app/controllers/task_actions.rb | 50 ++++++++++++ src/app/models/task.rb | 13 +++ src/app/views/dashboard/index.html.erb | 38 ++------- src/app/views/hardware/show_tasks.rhtml | 84 ++------------------ src/app/views/layouts/_navigation_tabs.rhtml | 20 ++++- src/app/views/resources/show_tasks.rhtml | 68 ++-------------- src/app/views/task/_grid.rhtml | 2 +- .../show_tasks.rhtml => task/_show.rhtml} | 60 +++++++------- 11 files changed, 170 insertions(+), 259 deletions(-) create mode 100644 src/app/controllers/task_actions.rb copy src/app/views/{hardware/show_tasks.rhtml => task/_show.rhtml} (56%) diff --git a/src/app/controllers/dashboard_controller.rb b/src/app/controllers/dashboard_controller.rb index c4830df..00398a5 100644 --- a/src/app/controllers/dashboard_controller.rb +++ b/src/app/controllers/dashboard_controller.rb @@ -18,19 +18,36 @@ # also available at http://www.gnu.org/copyleft/gpl.html. class DashboardController < ApplicationController + + include TaskActions + def tasks_query_obj + Task + end + def tasks_conditions + {:user => get_login_user} + end + def index - @default_pool = HardwarePool.get_default_pool - set_perms(@default_pool) - #remove these soon - @hardware_pools = HardwarePool.find(:all) - @available_hosts = Host.find(:all) - @available_storage_volumes = StorageVolume.find(:all) - @storage_pools = StoragePool.find(:all) - @hosts = Host.find(:all) - @storage_volumes = StorageVolume.find(:all) - @vms = Vm.find(:all) - if params[:ajax] - render :layout => 'tabs-and-content' #:template => 'hardware/show.html.erb' + @task_types = Task::TASK_TYPES_OPTIONS + show_tasks + end + + def show + respond_to do |format| + format.html { + render :layout => 'tabs-and-content' if params[:ajax] + render :layout => 'help-and-content' if params[:nolayout] + } + format.xml { + render :xml => @pool.to_xml(XML_OPTS) + } end end + + def tasks_internal + @task_type = params[:task_type] + @task_type ||="" + super + end + end diff --git a/src/app/controllers/hardware_controller.rb b/src/app/controllers/hardware_controller.rb index 4dda736..7be67cc 100644 --- a/src/app/controllers/hardware_controller.rb +++ b/src/app/controllers/hardware_controller.rb @@ -116,17 +116,7 @@ class HardwareController < PoolController end def show_tasks - @task_types = [["VM Task", "VmTask"], - ["Host Task", "HostTask"], - ["Storage Task", "StorageTask"], - ["Storage Volume Task", "StorageVolumeTask", "break"], - ["Show All", ""]] - super - end - - def tasks_internal - @task_type = params[:task_type] - @task_type ||="" + @task_types = Task::TASK_TYPES_OPTIONS super end diff --git a/src/app/controllers/pool_controller.rb b/src/app/controllers/pool_controller.rb index 03d1316..b8d0f10 100644 --- a/src/app/controllers/pool_controller.rb +++ b/src/app/controllers/pool_controller.rb @@ -31,6 +31,14 @@ class PoolController < ApplicationController :include => [ :storage_pools, :hosts, :quota ] } + include TaskActions + def tasks_query_obj + @pool.tasks + end + def tasks_conditions + {} + end + def show respond_to do |format| format.html { @@ -58,39 +66,6 @@ class PoolController < ApplicationController [:grid_id, :uid, :user_role, :source]) end - def show_tasks - @task_states = [["Queued", Task::STATE_QUEUED], - ["Running", Task::STATE_RUNNING], - ["Paused", Task::STATE_PAUSED], - ["Finished", Task::STATE_FINISHED], - ["Failed", Task::STATE_FAILED], - ["Canceled", Task::STATE_CANCELED, "break"], - ["Show All", ""]] - params[:page]=1 - params[:sortname]="tasks.created_at" - params[:sortorder]="desc" - @tasks = tasks_internal - show - end - - def tasks - render :json => tasks_internal.to_json - end - - def tasks_internal - @task_state = params[:task_state] - @task_state ||=Task::STATE_QUEUED - conditions = {} - conditions[:type] = @task_type unless @task_type.empty? - conditions[:state] = @task_state unless @task_state.empty? - find_opts = {:include => [:storage_pool, :host, :vm]} - find_opts[:conditions] = conditions unless conditions.empty? - attr_list = [] - attr_list << :id if params[:checkboxes] - attr_list += [:type_label, :task_obj, :action, :state, :user, :created_at, :args, :message] - json_hash(@pool.tasks, attr_list, [:all], find_opts) - end - def hosts_json(args) attr_list = [] attr_list << :id if params[:checkboxes] diff --git a/src/app/controllers/task_actions.rb b/src/app/controllers/task_actions.rb new file mode 100644 index 0000000..d71c11e --- /dev/null +++ b/src/app/controllers/task_actions.rb @@ -0,0 +1,50 @@ +# +# Copyright (C) 2009 Red Hat, Inc. +# Written by Scott Seago <sseago at redhat.com> +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; version 2 of the License. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, +# MA 02110-1301, USA. A copy of the GNU General Public License is +# also available at http://www.gnu.org/copyleft/gpl.html. +module TaskActions + def show_tasks + @task_states = Task::TASK_STATES_OPTIONS + params[:page]=1 + params[:sortname]="tasks.created_at" + params[:sortorder]="desc" + @tasks = tasks_internal + show + end + + def tasks + render :json => tasks_internal.to_json + end + + def tasks_internal + @task_state = params[:task_state] + @task_state ||=Task::STATE_QUEUED + @task_type = params[:task_type] + @task_type ||="" + conditions = tasks_conditions + conditions[:type] = @task_type unless @task_type.empty? + conditions[:state] = @task_state unless @task_state.empty? + find_opts = {:include => [:storage_pool, :host, :vm]} + find_opts[:conditions] = conditions unless conditions.empty? + attr_list = [] + attr_list << :id if params[:checkboxes] + attr_list += [:type_label, :task_obj, :action, :state, :user, :created_at, :args, :message] + json_hash(tasks_query_obj, attr_list, [:all], find_opts) + end + + +end diff --git a/src/app/models/task.rb b/src/app/models/task.rb index f231c18..4d16e01 100644 --- a/src/app/models/task.rb +++ b/src/app/models/task.rb @@ -45,6 +45,19 @@ class Task < ActiveRecord::Base COMPLETED_STATES = [STATE_FINISHED, STATE_FAILED, STATE_CANCELED] WORKING_STATES = [STATE_QUEUED, STATE_RUNNING, STATE_PAUSED] + TASK_TYPES_OPTIONS = [["VM Task", "VmTask"], + ["Host Task", "HostTask"], + ["Storage Task", "StorageTask"], + ["Storage Volume Task", "StorageVolumeTask", "break"], + ["Show All", ""]] + TASK_STATES_OPTIONS = [["Queued", Task::STATE_QUEUED], + ["Running", Task::STATE_RUNNING], + ["Paused", Task::STATE_PAUSED], + ["Finished", Task::STATE_FINISHED], + ["Failed", Task::STATE_FAILED], + ["Canceled", Task::STATE_CANCELED, "break"], + ["Show All", ""]] + def cancel self[:state] = STATE_CANCELED save! diff --git a/src/app/views/dashboard/index.html.erb b/src/app/views/dashboard/index.html.erb index 8815ebc..c361e55 100644 --- a/src/app/views/dashboard/index.html.erb +++ b/src/app/views/dashboard/index.html.erb @@ -1,31 +1,7 @@ - <td id="right"> - <div class="tools"> - - <h3>Actions</h3> - - <div class="actions"> - <div><%= link_to_if @can_set_perms, 'User Permissions', { :controller => 'permission', :action => 'new', :pool_id => @default_pool }, { :class => "edit" } %></div> - <table> - <tr><td><%= pluralize @default_pool.permissions.super_admins.size, "Super Admin" %></td></tr> - <tr><td><%= pluralize @default_pool.permissions.admins.size, "Administrator" %></td></tr> - <tr><td><%= pluralize @default_pool.permissions.users.size, "User" %></td></tr> - <tr><td><%= pluralize @default_pool.permissions.monitors.size, "Monitor" %></td></tr> - </table> - </div> - - <% if @can_modify %> - <h3>Networks</h3> - <a href="<%= url_for :controller => 'network', :action => 'list' %>"> - View / Edit - </a> - <% end %> - - </div> <!-- end #tools --> - </td> - - - -<%- content_for :title do -%> -<%= _("Dashboard") %> -<%- end -%> - + <%= render :partial => "/task/show", :locals => { :task_types => @task_types, + :task_states => @task_states, + :task_type => @task_type, + :task_state => @task_state, + :tasks => @tasks, + :action => 'index', + :pool => nil } %> diff --git a/src/app/views/hardware/show_tasks.rhtml b/src/app/views/hardware/show_tasks.rhtml index e49086c..87ea13f 100644 --- a/src/app/views/hardware/show_tasks.rhtml +++ b/src/app/views/hardware/show_tasks.rhtml @@ -1,77 +1,7 @@ -<div id="toolbar_nav"> - <ul> - <li> - <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> Type <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> - <ul> - <% @task_types.each_index { |index| %> - <li onclick="apply_task_filter('<%=@task_types[index][1]%>','<%=@task_state%>');";" - <% if (index == @task_types.length - 1) or @task_types[index].length == 3 %> - style="border-bottom: 1px solid #CCCCCC;" - <% end %> - > -<!-- < % = image_tag ... --> - <%= @task_type == @task_types[index][1] ? "X" : " " %> - <%=@task_types[index][0]%> - </li> - <% } %> - </ul> - </li> - <li> - <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> State <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> - <ul> - <% @task_states.each_index { |index| %> - <li onclick="apply_task_filter('<%=@task_type%>','<%=@task_states[index][1]%>');";" - <% if (index == @task_states.length - 1) or @task_states[index].length == 3 %> - style="border-bottom: 1px solid #CCCCCC;" - <% end %> - > -<!-- < % = image_tag ... --> - <%= @task_state == @task_states[index][1] ? "X" : " " %> - <%=@task_states[index][0]%> - </li> - <% } %> - </ul> - </li> - </ul> -</div> - -<script type="text/javascript"> - var $tabs - function apply_task_filter(task_type, task_state) - { - $tabs.tabs("url", $tabs.data("selected.tabs"), - "<%= url_for :action => 'show_tasks', :id => @pool.id, - :nolayout => :true %>" + - "&task_type=" + task_type + "&task_state=" + task_state); - $tabs.tabs("load", $tabs.data("selected.tabs")); - } -</script> - -<div class="panel_header"></div> -<% if @tasks[:rows].size != 0 %> - <div class="data_section"> - <%= render :partial => "/task/grid", :locals => { :table_id => "tasks_grid", - :task_type => @task_type, - :task_state => @task_state, - :pool => @pool, - :checkboxes => false, - :on_select => "tasks_grid_select" } %> - </div> -<!-- do we have a selection here? - <div class="selection_detail" id="hosts_selection"> - <div class="selection_left"> - <div>Select a host above.</div> - </div> - </div> --> -<% else %> - <div class="data_section"> - <div class="no-grid-items"> - <%= image_tag 'no-grid-items.png', :style => 'float: left;' %> - - <div class="no-grid-items-text"> - No tasks found. <br/><br/> - <%= image_tag "icon_addhost.png", :style=>"vertical-align:middle;" %> - </div> - </div> - </div> -<% end %> + <%= render :partial => "/task/show", :locals => { :task_types => @task_types, + :task_states => @task_states, + :task_type => @task_type, + :task_state => @task_state, + :tasks => @tasks, + :action => 'show_tasks', + :pool => @pool } %> diff --git a/src/app/views/layouts/_navigation_tabs.rhtml b/src/app/views/layouts/_navigation_tabs.rhtml index dd50820..6619efc 100644 --- a/src/app/views/layouts/_navigation_tabs.rhtml +++ b/src/app/views/layouts/_navigation_tabs.rhtml @@ -3,7 +3,7 @@ $(document).ready(function(){ $tabs = $("#hardware_nav_tabs").tabs({ pool_type: "hardware", - selected: <%if params[:tab]%><%=params[:tab]%><%else%>1<%end%> + selected: <%if params[:tab]%><%=params[:tab]%><%else%>0<%end%> }); }); </script> @@ -20,7 +20,7 @@ $(document).ready(function(){ $tabs = $("#resources_nav_tabs").tabs({ pool_type: "resource", - selected: <%if params[:tab]%><%=params[:tab]%><%else%>1<%end%> + selected: <%if params[:tab]%><%=params[:tab]%><%else%>0<%end%> }); }); </script> @@ -35,7 +35,7 @@ $(document).ready(function(){ $tabs = $("#smart_pools_nav_tabs").tabs({ pool_type: "smart", - selected: <%if params[:tab]%><%=params[:tab]%><%else%>1<%end%> + selected: <%if params[:tab]%><%=params[:tab]%><%else%>0<%end%> }); }); </script> @@ -48,7 +48,19 @@ <li id="nav_access"> <%= link_to "User Access", {:action => 'show_users', :id => @pool.id, :nolayout => :true}, :title => "content area" %></li> </ul> <% elsif controller.controller_name == "search" %> - <ul id="resources_nav_tabs" class="ui-tabs-nav"> + <ul id="search_nav_tabs" class="ui-tabs-nav"> <li id="nav_search" class="ui-tabs-selected"><a href="#">Search Results</a></li> </ul> +<% elsif controller.controller_name == "dashboard" %> + <script> + $(document).ready(function(){ + $tabs = $("#dashboard_nav_tabs").tabs({ + pool_type: "hardware", + selected: <%if params[:tab]%><%=params[:tab]%><%else%>0<%end%> + }); + }); + </script> + <ul id="dashboard_nav_tabs" class="ui-tabs-nav"> + <li id="nav_summary" class="ui-tabs-selected"><%= link_to "Tasks", {:action => 'index', :nolayout => :true}, :title => "content area" %></li> + </ul> <% end %> \ No newline at end of file diff --git a/src/app/views/resources/show_tasks.rhtml b/src/app/views/resources/show_tasks.rhtml index 6c92779..87ea13f 100644 --- a/src/app/views/resources/show_tasks.rhtml +++ b/src/app/views/resources/show_tasks.rhtml @@ -1,61 +1,7 @@ -<div id="toolbar_nav"> - <ul> - <li> - <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> State <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> - <ul> - <% @task_states.each_index { |index| %> - <li onclick="apply_task_state_filter('<%=@task_states[index][1]%>');";" - <% if (index == @task_states.length - 1) or @task_states[index].length == 3 %> - style="border-bottom: 1px solid #CCCCCC;" - <% end %> - > -<!-- < % = image_tag ... --> - <%= @task_state == @task_states[index][1] ? "X" : " " %> - <%=@task_states[index][0]%> - </li> - <% } %> - </ul> - </li> - </ul> -</div> - -<script type="text/javascript"> - var $tabs - function apply_task_state_filter(task_state) - { - $tabs.tabs("url", $tabs.data("selected.tabs"), - "<%= url_for :action => 'show_tasks', :id => @pool.id, - :nolayout => :true %>" + - "&task_state=" + task_state); - $tabs.tabs("load", $tabs.data("selected.tabs")); - } -</script> - -<div class="panel_header"></div> -<% if @tasks[:rows].size != 0 %> - <div class="data_section"> - <%= render :partial => "/task/grid", :locals => { :table_id => "vm_tasks_grid", - :task_type => nil, - :task_state => @task_state, - :pool => @pool, - :checkboxes => false, - :on_select => "vm_tasks_grid_select" } %> - </div> -<!-- do we have a selection here? - <div class="selection_detail" id="hosts_selection"> - <div class="selection_left"> - <div>Select a host above.</div> - </div> - </div> --> -<% else %> - <div class="data_section"> - <div class="no-grid-items"> - <%= image_tag 'no-grid-items.png', :style => 'float: left;' %> - - <div class="no-grid-items-text"> - No tasks found. <br/><br/> - <%= image_tag "icon_addhost.png", :style=>"vertical-align:middle;" %> - </div> - </div> - </div> -<% end %> + <%= render :partial => "/task/show", :locals => { :task_types => @task_types, + :task_states => @task_states, + :task_type => @task_type, + :task_state => @task_state, + :tasks => @tasks, + :action => 'show_tasks', + :pool => @pool } %> diff --git a/src/app/views/task/_grid.rhtml b/src/app/views/task/_grid.rhtml index cab99e5..3c17ac5 100644 --- a/src/app/views/task/_grid.rhtml +++ b/src/app/views/task/_grid.rhtml @@ -9,7 +9,7 @@ ( { url: '<%= url_for :action => "tasks", - :id => pool.id %>', + :id => pool %>', params: [{name: "task_type", value: '<%=task_type%>'}, {name: "task_state", value: '<%=task_state%>'} <%=", {name: 'checkboxes', value: #{checkboxes}}" if checkboxes%>], diff --git a/src/app/views/hardware/show_tasks.rhtml b/src/app/views/task/_show.rhtml similarity index 56% copy from src/app/views/hardware/show_tasks.rhtml copy to src/app/views/task/_show.rhtml index e49086c..340ce6c 100644 --- a/src/app/views/hardware/show_tasks.rhtml +++ b/src/app/views/task/_show.rhtml @@ -1,33 +1,36 @@ <div id="toolbar_nav"> - <ul> - <li> - <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> Type <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> - <ul> - <% @task_types.each_index { |index| %> - <li onclick="apply_task_filter('<%=@task_types[index][1]%>','<%=@task_state%>');";" - <% if (index == @task_types.length - 1) or @task_types[index].length == 3 %> - style="border-bottom: 1px solid #CCCCCC;" - <% end %> - > -<!-- < % = image_tag ... --> - <%= @task_type == @task_types[index][1] ? "X" : " " %> - <%=@task_types[index][0]%> - </li> - <% } %> - </ul> - </li> + <ul> + <%if task_types %> + <li> + <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> Type <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> + <ul> + <% task_types.each_index { |index| %> + <li onclick="apply_task_filter('<%=task_types[index][1]%>','<%=task_state%>');";" + <% if (index == task_types.length - 1) or task_types[index].length == 3 %> + style="border-bottom: 1px solid #CCCCCC;" + <% end %> + > + <!-- < % = image_tag ... --> + <%= task_type == task_types[index][1] ? "X" : " " %> + <%=task_types[index][0]%> + </li> + <% } %> + </ul> + </li> + <% end %> + <li> <%= image_tag "icon_move.png", :style => "vertical-align:middle;" %> State <%= image_tag "icon_toolbar_arrow.gif", :style => "vertical-align:middle;" %> <ul> - <% @task_states.each_index { |index| %> - <li onclick="apply_task_filter('<%=@task_type%>','<%=@task_states[index][1]%>');";" - <% if (index == @task_states.length - 1) or @task_states[index].length == 3 %> + <% task_states.each_index { |index| %> + <li onclick="apply_task_filter('<%=task_type%>','<%=task_states[index][1]%>');";" + <% if (index == task_states.length - 1) or task_states[index].length == 3 %> style="border-bottom: 1px solid #CCCCCC;" <% end %> > <!-- < % = image_tag ... --> - <%= @task_state == @task_states[index][1] ? "X" : " " %> - <%=@task_states[index][0]%> + <%= task_state == task_states[index][1] ? "X" : " " %> + <%=task_states[index][0]%> </li> <% } %> </ul> @@ -40,7 +43,7 @@ function apply_task_filter(task_type, task_state) { $tabs.tabs("url", $tabs.data("selected.tabs"), - "<%= url_for :action => 'show_tasks', :id => @pool.id, + "<%= url_for :action => action, :id => pool, :nolayout => :true %>" + "&task_type=" + task_type + "&task_state=" + task_state); $tabs.tabs("load", $tabs.data("selected.tabs")); @@ -48,12 +51,12 @@ </script> <div class="panel_header"></div> -<% if @tasks[:rows].size != 0 %> +<% if tasks[:rows].size != 0 %> <div class="data_section"> <%= render :partial => "/task/grid", :locals => { :table_id => "tasks_grid", - :task_type => @task_type, - :task_state => @task_state, - :pool => @pool, + :task_type => task_type, + :task_state => task_state, + :pool => pool, :checkboxes => false, :on_select => "tasks_grid_select" } %> </div> @@ -69,8 +72,7 @@ <%= image_tag 'no-grid-items.png', :style => 'float: left;' %> <div class="no-grid-items-text"> - No tasks found. <br/><br/> - <%= image_tag "icon_addhost.png", :style=>"vertical-align:middle;" %> + No tasks found. </div> </div> </div> -- 1.6.0.6
Jason Guiditta
2009-Jan-12 19:15 UTC
[Ovirt-devel] [PATCH] Add task list to dashboard (revised)
On Mon, 2009-01-12 at 15:19 +0000, Scott Seago wrote:> Refactored task list functionality to allow for the dashboard-level task list. > The dashboard task list shows all tasks initiated by the logged-in user, and is > filterable by task type and state. > > revised to fix a couple bugs found by lutter >Almost ACK. I have attached a few fixes. They correct both the 'double render', and fix the dashboard link so it doesn't reload the whole page (making you lose state on your nav tree). Also added a little cleanup bit making the correct thing show as current (blue background). -j -------------- next part -------------- A non-text attachment was scrubbed... Name: sseago-tasklist-update.patch Type: text/x-patch Size: 6571 bytes Desc: not available URL: <http://listman.redhat.com/archives/ovirt-devel/attachments/20090112/7d0a29bb/attachment.bin>