diff --git a/app/models/queries/columns/base.rb b/app/models/queries/columns/base.rb index 03396c8591..684509d039 100644 --- a/app/models/queries/columns/base.rb +++ b/app/models/queries/columns/base.rb @@ -29,18 +29,22 @@ #++ class Queries::Columns::Base + attr_reader :groupable, + :sortable, + :association + attr_accessor :name, - :sortable, - :groupable, + :sortable_join, :summable, - :default_order, - :association + :default_order + alias_method :summable?, :summable def initialize(name, options = {}) self.name = name %i(sortable + sortable_join groupable summable association diff --git a/app/models/queries/work_packages/columns/property_column.rb b/app/models/queries/work_packages/columns/property_column.rb index ca1ae8b930..993645f1fd 100644 --- a/app/models/queries/work_packages/columns/property_column.rb +++ b/app/models/queries/work_packages/columns/property_column.rb @@ -55,10 +55,17 @@ class Queries::WorkPackages::Columns::PropertyColumn < Queries::WorkPackages::Co }, parent: { association: 'ancestors_relations', + default_order: 'asc', sortable: ["COALESCE(#{Relation.table_name}.from_id, #{WorkPackage.table_name}.id)", - "#{Relation.table_name}.hierarchy", - "#{WorkPackage.table_name}.id"], - default_order: 'asc' + "COALESCE(#{Relation.table_name}.hierarchy, 0)"], + sortable_join: <<-SQL + JOIN ( + SELECT relations.hierarchy, relations.to_id, relations.from_id from relations + JOIN ( + #{Relation.hierarchy_or_reflexive.group(:to_id).select('MAX(relations.hierarchy) hierarchy, relations.to_id').to_sql}) max_depth + ON max_depth.hierarchy = relations.hierarchy AND max_depth.to_id = relations.to_id) depth_relations + ON depth_relations.to_id = work_packages.id + SQL }, status: { association: 'status', diff --git a/app/models/query.rb b/app/models/query.rb index 4073c02c32..18dd9a301d 100644 --- a/app/models/query.rb +++ b/app/models/query.rb @@ -93,7 +93,7 @@ class Query < ActiveRecord::Base def set_default_sort return if sort_criteria.any? - self.sort_criteria = [['parent', 'asc']] + self.sort_criteria = [['parent', 'asc'], ['id', 'asc']] end def context diff --git a/app/models/query/results.rb b/app/models/query/results.rb index d4b900fbc8..76a2e68de8 100644 --- a/app/models/query/results.rb +++ b/app/models/query/results.rb @@ -75,6 +75,7 @@ class ::Query::Results .where(query.statement) .where(options[:conditions]) .includes(all_includes) + .joins(all_joins) .order(order_option) .references(:projects) end @@ -117,11 +118,11 @@ class ::Query::Results return nil unless query.grouped? group_work_packages = work_packages.select { |wp| query.group_by_column.value(wp) == group } - query.available_columns.inject({}) { |result, column| + query.available_columns.inject({}) do |result, column| sum = sum_of(column, group_work_packages) result[column] = sum unless sum.nil? result - } + end end def column_group_sums @@ -143,6 +144,10 @@ class ::Query::Results (options[:include] || [])).uniq end + def all_joins + query.sort_criteria_columns.map { |column, _direction| column.sortable_join }.compact + end + def includes_for_columns(column_names) column_names = Array(column_names) (WorkPackage.reflections.keys.map(&:to_sym) & column_names.map(&:to_sym)) diff --git a/app/models/relation.rb b/app/models/relation.rb index be052f519c..1f3d81ed1b 100644 --- a/app/models/relation.rb +++ b/app/models/relation.rb @@ -123,6 +123,10 @@ class Relation < ActiveRecord::Base .non_reflexive end + def self.hierarchy_or_reflexive + with_type_columns_0(WorkPackage._dag_options.type_columns - %i(hierarchy)) + end + def self.non_hierarchy_of_work_package(work_package) of_work_package(work_package) .non_hierarchy diff --git a/frontend/app/components/modals/sorting-modal/sorting-modal.service.html b/frontend/app/components/modals/sorting-modal/sorting-modal.service.html index 68714e7330..8aa8a6157d 100644 --- a/frontend/app/components/modals/sorting-modal/sorting-modal.service.html +++ b/frontend/app/components/modals/sorting-modal/sorting-modal.service.html @@ -9,7 +9,7 @@