From 5dc550172d22e0fe095d7f00cdc848f716b0fda0 Mon Sep 17 00:00:00 2001 From: Vladimir Krylov Date: Wed, 4 Nov 2015 16:23:01 +0200 Subject: [PATCH] add sorting to contact domains --- app/helpers/application_helper.rb | 12 ++++++++++ app/models/contact.rb | 23 ++++++++++++++----- .../admin/contacts/partials/_domains.haml | 8 +++---- 3 files changed, 33 insertions(+), 10 deletions(-) diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 7a75ff78f..dea4f9228 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -55,4 +55,16 @@ module ApplicationHelper username ||= '' username.split(':').last.to_s.strip end + + def custom_sort_link(title, param_name) + sort = params.fetch(:sort, {})[param_name] + order = {"asc"=>"desc", "desc"=>"asc"}[sort] || "asc" + + # binding.pry + if params.fetch(:sort, {}).include?(param_name) + title += (sort == "asc" ? " ▲" : " ▼") + end + + link_to(title, url_for(sort: {param_name => order}), class: "sort_link #{order}") + end end diff --git a/app/models/contact.rb b/app/models/contact.rb index e6a741192..722f7e170 100644 --- a/app/models/contact.rb +++ b/app/models/contact.rb @@ -353,18 +353,29 @@ class Contact < ActiveRecord::Base # what we can do load firstly by registrant # if total is smaller than needed, the load more # we also need to sort by valid_to - def all_domains(page: nil, per: nil) - sql = %Q{id IN ( + def all_domains(page: nil, per: nil, params: {}) + sql = %Q{domains.id IN ( select domain_id from domain_contacts where contact_id=#{id} UNION select id from domains where registrant_id=#{id} )} + sorts = params.fetch(:sort, {}).first || [] + sort = Domain.column_names.include?(sorts.first) ? sorts.first : "valid_to" + order = {"asc"=>"desc", "desc"=>"asc"}[sorts.second] || "desc" - # sql = Domain.joins(:domain_contacts).where(domain_contacts: {contact_id: id}).select("#{Domain.table_name}.*".freeze, "'domain_contacts' AS style"). - # union(registrant_domains.select("#{Domain.table_name}.*".freeze, "'registrant_domains' AS style")).to_sql - # merged_sql = "select #{Domain.column_names.join(',')}, array_agg (t.style) over (partition by t.id) style from (#{sql} limit #{per.to_i}) t" - domains = Domain.where(sql).order("valid_to DESC NULLS LAST").includes(:registrar).page(page).per(per) + + domains = Domain.where(sql).includes(:registrar).page(page).per(per) + if sorts.first == "registrar_name".freeze + # using small rails hack to generate outer join + domains = domains.includes(:registrar).where.not(registrars: {id: nil}).order("registrars.name #{order} NULLS LAST") + else + domains = domains.order("#{sort} #{order} NULLS LAST") + end + + + + # adding roles. Need here to make faster sqls domain_c = Hash.new([]) registrant_domains.where(id: domains.map(&:id)).each{|d| domain_c[d.id] |= ["Registrant"].freeze } DomainContact.where(contact_id: id, domain_id: domains.map(&:id)).each{|d| domain_c[d.domain_id] |= [d.type] } diff --git a/app/views/admin/contacts/partials/_domains.haml b/app/views/admin/contacts/partials/_domains.haml index f99c0926d..32dd163da 100644 --- a/app/views/admin/contacts/partials/_domains.haml +++ b/app/views/admin/contacts/partials/_domains.haml @@ -1,13 +1,13 @@ -- domains = @contact.all_domains(page: params[:domain_page], per: 20) +- domains = @contact.all_domains(page: params[:domain_page], per: 20, params: params) #contacts.panel.panel-default .panel-heading= t(:domains) .table-responsive %table.table.table-hover.table-bordered.table-condensed %thead %tr - %th{class: 'col-xs-3'}= t(:domain_name) - %th{class: 'col-xs-3'}= t(:registrar) - %th{class: 'col-xs-3'}= t(:valid_to) + %th{class: 'col-xs-3'}=custom_sort_link t(:domain_name), :name + %th{class: 'col-xs-3'}=custom_sort_link t(:registrar), :registrar_name + %th{class: 'col-xs-3'}=custom_sort_link t(:valid_to), :valid_to %th{class: 'col-xs-3'}= t(:roles) %tbody - domains.each do |x|