Skip to content

Commit

Permalink
[webui] Refactoring user requests datatables
Browse files Browse the repository at this point in the history
- Moved logic from controller to RequestsDatatable class
- Fix request sorting ordering by column (introduced by 509370a)
Fixes #2572
  • Loading branch information
ChrisBr committed Feb 16, 2017
1 parent 0e59d1e commit 4f07d4c
Show file tree
Hide file tree
Showing 20 changed files with 428 additions and 120 deletions.
1 change: 1 addition & 0 deletions src/api/app/assets/javascripts/webui/application.js.erb
Expand Up @@ -38,6 +38,7 @@
//= require webui/application/attribute
//= require webui/application/main
//= require webui/application/repository_tab
//= require webui/application/user
<% require_asset 'webui/application/image_templates' if Feature.active?(:image_templates) %>

function remove_dialog() {
Expand Down
32 changes: 32 additions & 0 deletions src/api/app/assets/javascripts/webui/application/user.js
@@ -0,0 +1,32 @@
$( document ).ready(function() {
var url = $('.requests-datatable').first().data('source');
var options = {
order: [[0,'desc']],
info: false,
columnDefs: [
// We only allow ordering for created, requester and priority.
// Columns: created, source, target, requester, type, priority.
{ orderable: false, targets: [1,2,4,6,] }
],
paging: 25,
pagingType: "full_numbers",
processing: true,
serverSide: true,
ajax: {
url: url,
data: { dataTableId: null }
}
};

options.ajax.data.dataTableId = 'requests_in_table';
$('#requests_in_table').dataTable(options);

options.ajax.data.dataTableId = 'requests_out_table';
$('#requests_out_table').dataTable(options);

options.ajax.data.dataTableId = 'requests_declined_table';
$('#requests_declined_table').dataTable(options);

options.ajax.data.dataTableId = 'all_requests_table';
$('#all_requests_table').dataTable(options);
});
41 changes: 1 addition & 40 deletions src/api/app/controllers/webui/user_controller.rb
Expand Up @@ -2,7 +2,7 @@
require 'event'

class Webui::UserController < Webui::WebuiController
before_action :check_display_user, only: [:show, :edit, :requests, :list_my, :delete, :save, :confirm, :admin, :lock]
before_action :check_display_user, only: [:show, :edit, :list_my, :delete, :save, :confirm, :admin, :lock]
before_action :require_login, only: [:edit, :save, :notifications, :update_notifications, :index]
before_action :require_admin, only: [:edit, :delete, :lock, :confirm, :admin, :index]

Expand Down Expand Up @@ -71,45 +71,6 @@ def home
end
end

# Request from the user
def requests
sortable_fields = {
0 => :created_at,
3 => :creator,
5 => :priority
}
sorting_field = sortable_fields[params['order[0][column]'].to_i]
sorting_field ||= :created_at
sorting_dir = params['order[0][dir]'].try(:to_sym)
sorting_dir = :asc unless ["asc", "desc"].include?(params['order[0][dir]'])
search = params[:search] ? params[:search].permit![:value] : ""
request_methods = {
'all_requests_table' => :requests,
'requests_out_table' => :outgoing_requests,
'requests_declined_table' => :declined_requests,
'requests_in_table' => :incoming_requests,
'reviews_in_table' => :involved_reviews
}
# Depending on the table that is requesting we call the appropiate user method
request_method = request_methods[params[:dataTableId]] || :requests
@requests = @displayed_user.send(request_method, search)
@requests_count = @requests.count
@requests = @requests.offset(params[:start].to_i).limit(params[:length].to_i).reorder(sorting_field => sorting_dir)
respond_to do |format|
# For jquery dataTable
format.json {
render_json_response_for_dataTable(
draw: params[:draw].to_i + 1,
total_records_count: @displayed_user.send(request_method).count,
total_filtered_records_count: @requests_count,
records: @requests.includes(:bs_request_actions)
) do |request|
render_to_string(partial: "shared/single_request.json", locals: { req: request, no_target: true, hide_state: true }).to_s.split(',')
end
}
end
end

def save
unless User.current.is_admin?
if User.current != @displayed_user
Expand Down
14 changes: 14 additions & 0 deletions src/api/app/controllers/webui/users/bs_requests_controller.rb
@@ -0,0 +1,14 @@
module Webui
module Users
class BsRequestsController < WebuiController
before_action :check_display_user

def index
@requests_data_table = BsRequest::DataTable.new(params, @displayed_user)
respond_to do |format|
format.json
end
end
end
end
end
20 changes: 0 additions & 20 deletions src/api/app/controllers/webui/webui_controller.rb
Expand Up @@ -114,26 +114,6 @@ def valid_xml_id(rawid)

protected

# Renders a json response for jquery dataTables
def render_json_response_for_dataTable(options)
options[:draw] ||= 1
options[:total_records_count] ||= 0
options[:total_displayed_records] ||= 0
response = {
draw: options[:draw].to_i,
recordsTotal: options[:total_records_count].to_i,
recordsFiltered: options[:total_filtered_records_count].to_i,
data: options[:records].map do |record|
if block_given?
yield record
else
record
end
end
}
render json: Yajl::Encoder.encode(response)
end

def require_login
if User.current.nil? || User.current.is_nobody?
render(text: 'Please login') && (return false) if request.xhr?
Expand Down
12 changes: 12 additions & 0 deletions src/api/app/helpers/webui/request_helper.rb
Expand Up @@ -81,4 +81,16 @@ def priority_number(prio)
"4"
end
end

def target_project_link(row)
result = ''
if row.target_project
if row.target_package && row.source_package != row.target_package
result = project_or_package_link(project: row.target_project, package: row.target_package, trim_to: 40, short: true)
else
result = project_or_package_link(project: row.target_project, trim_to: 40, short: true)
end
end
result
end
end
8 changes: 4 additions & 4 deletions src/api/app/helpers/webui/webui_helper.rb
Expand Up @@ -36,7 +36,7 @@ def user_icon(user, size = 20, css_class = nil, alt = nil)
user = User.find_by_login!(user) unless user.is_a? User
alt ||= user.realname
alt = user.login if alt.empty?
image_tag(url_for(controller: :user, action: :user_icon, icon: user.login, size: size),
image_tag(url_for(controller: '/webui/user', action: :user_icon, icon: user.login, size: size),
width: size, height: size, alt: alt, class: css_class)
end

Expand Down Expand Up @@ -300,13 +300,13 @@ def link_to_package(prj, pkg, opts)
opts[:short] = true # for project
out += link_to_project(prj, opts) + ' / ' +
link_to_if(pkg, opts[:package_text],
{ controller: 'package', action: 'show',
{ controller: '/webui/package', action: 'show',
project: opts[:project],
package: opts[:package] }, { class: 'package', title: opts[:package] })
if opts[:rev] && pkg
out += ' ('.html_safe +
link_to("revision #{elide(opts[:rev], 10)}",
{ controller: 'package', action: 'show',
{ controller: '/webui/package', action: 'show',
project: opts[:project], package: opts[:package], rev: opts[:rev] },
{ class: 'package', title: opts[:rev] }) + ')'.html_safe
end
Expand All @@ -322,7 +322,7 @@ def link_to_project(prj, opts)
end
project_text = opts[:trim_to].nil? ? opts[:project_text] : elide(opts[:project_text], opts[:trim_to])
out + link_to_if(prj, project_text,
{ controller: 'project', action: 'show', project: opts[:project] },
{ controller: '/webui/project', action: 'show', project: opts[:project] },
{ class: 'project', title: opts[:project] })
end

Expand Down
77 changes: 77 additions & 0 deletions src/api/app/models/bs_request/data_table.rb
@@ -0,0 +1,77 @@
class BsRequest
class DataTable
def initialize(params, user)
@params = params
@user = user
end

def rows
requests.map { |request| BsRequest::DataTableRow.new(request) }
end

def draw
@params[:draw].to_i + 1
end

def records_total
requests_query.count
end

def count_requests
requests_query(search).count
end

private

def requests
@requests ||= fetch_requests
end

def requests_query(search = nil)
request_methods = {
'all_requests_table' => :requests,
'requests_out_table' => :outgoing_requests,
'requests_declined_table' => :declined_requests,
'requests_in_table' => :incoming_requests,
'reviews_in_table' => :involved_reviews
}

request_method = request_methods[@params[:dataTableId]] || :requests
@user.send(request_method, search)
end

def fetch_requests
requests_query(search).offset(offset).limit(limit).reorder(sort_column => sort_direction).includes(:bs_request_actions)
end

def search
@params[:search] ? @params[:search][:value] : ''
end

def offset
@params[:start].to_i
end

def limit
@params[:length].to_i
end

def order_params
@params.fetch(:order, {}).fetch('0', {})
end

def sort_column
# defaults to :created_at
{
0 => :created_at,
3 => :creator,
5 => :priority
}[order_params.fetch(:column, nil).to_i]
end

def sort_direction
# defaults to :desc
order_params[:dir].try(:to_sym) == :asc ? :asc : :desc
end
end
end
36 changes: 36 additions & 0 deletions src/api/app/models/bs_request/data_table_row.rb
@@ -0,0 +1,36 @@
class BsRequest
class DataTableRow
attr_accessor :request
delegate :created_at, :number, :creator, :priority, to: :request

def initialize(request)
@request = request
end

def source_package
cache[:source_package]
end

def source_project
cache[:source_project]
end

def request_type
cache[:request_type]
end

def target_project
cache[:target_project]
end

def target_package
cache[:target_package]
end

private

def cache
@cache ||= ApplicationController.helpers.common_parts(request)
end
end
end
33 changes: 0 additions & 33 deletions src/api/app/views/shared/_single_request.json.erb

This file was deleted.

11 changes: 11 additions & 0 deletions src/api/app/views/webui/user/_requests.html.haml
@@ -0,0 +1,11 @@
%table.requests-datatable.compact{ 'data-source' => user_requests_path(@displayed_user), id: id, width: '100%'}
%thead
%tr
%th Created
%th Source
%th Target
%th Requester
%th Type
%th Priority
%th
%tbody
16 changes: 8 additions & 8 deletions src/api/app/views/webui/user/show.html.erb
Expand Up @@ -148,23 +148,23 @@
<div id="requests">
<div class="box-header header-tabs">
<ul>
<li><a href="#requests_in" title="Requests that <%= @displayed_user.login %> has to merge">Incoming Requests</a></li>
<li><a href="#requests_out" title="Requests that <%= @displayed_user.login %> has sent">Outgoing Requests</a></li>
<li><a href="#requests_declined" title="Requests from <%= @displayed_user.login %> that are declined">Declined Requests</a></li>
<li><a href="#all_requests" title="All Requests from <%= @displayed_user.login %>">All Requests</a></li>
<li><a id="requests_in_tab" href="#requests_in" title="Requests that <%= @displayed_user.login %> has to merge">Incoming Requests</a></li>
<li><a id="requests_out_tab" href="#requests_out" title="Requests that <%= @displayed_user.login %> has sent">Outgoing Requests</a></li>
<li><a id="requests_declined_tab" href="#requests_declined" title="Requests from <%= @displayed_user.login %> that are declined">Declined Requests</a></li>
<li><a id="all_requests_tab" href="#all_requests" title="All Requests from <%= @displayed_user.login %>">All Requests</a></li>
</ul>
</div>
<div id="requests_in" class="tab">
<%= render(:partial => 'shared/requests', :locals => { :request_table_id => 'requests_in_table', :hide_state => true, :serverProcessing => true }) %>
<%= render(partial: 'requests', locals: { id: 'requests_in_table' }) %>
</div>
<div id="requests_out" class="tab">
<%= render(:partial => 'shared/requests', :locals => { :request_table_id => 'requests_out_table', :hide_state => true, :serverProcessing => true }) %>
<%= render(partial: 'requests', locals: { id: 'requests_out_table' }) %>
</div>
<div id="requests_declined" class="tab">
<%= render(:partial => 'shared/requests', :locals => { :request_table_id => 'requests_declined_table', :hide_state => true, :serverProcessing => true }) %>
<%= render(partial: 'requests', locals: { id: 'requests_declined_table' }) %>
</div>
<div id="all_requests" class="tab">
<%= render(:partial => 'shared/requests', :locals => { :request_table_id => 'all_requests_table', :hide_state => true, :serverProcessing => true }) %>
<%= render(partial: 'requests', locals: { id: 'all_requests_table' }) %>
</div>
</div>
</div>
Expand Down

0 comments on commit 4f07d4c

Please sign in to comment.