Add TypeFilter for Views

pull/9896/head
Wieland Lindenthal 3 years ago
parent fbe56b9e98
commit c19cdada66
No known key found for this signature in database
GPG Key ID: 7ACCABE64832A0C6
  1. 5
      app/models/queries/views.rb
  2. 48
      app/models/queries/views/filters/type_filter.rb
  3. 4
      spec/factories/view_factory.rb
  4. 60
      spec/models/queries/views/filters/type_filter_spec.rb
  5. 38
      spec/requests/api/v3/views/index_resource_spec.rb
  6. 5
      spec/support/queries/filters/shared_filter_examples.rb

@ -27,7 +27,10 @@
#++
module Queries::Views
[Queries::Views::Filters::ProjectFilter].each do |filter|
[
Queries::Views::Filters::ProjectFilter,
Queries::Views::Filters::TypeFilter
].each do |filter|
Queries::Register.filter Queries::Views::ViewQuery,
filter
end

@ -0,0 +1,48 @@
#-- copyright
# OpenProject is an open source project management software.
# Copyright (C) 2012-2021 the OpenProject GmbH
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License version 3.
#
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
# Copyright (C) 2006-2013 Jean-Philippe Lang
# Copyright (C) 2010-2013 the ChiliProject Team
#
# 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; either version 2
# of the License, or (at your option) any later version.
#
# 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.
#
# See COPYRIGHT and LICENSE files for more details.
#++
class Queries::Views::Filters::TypeFilter < Queries::Views::Filters::ViewFilter
def type
:list_optional
end
def where
operator_strategy.sql_for_field(transformed_values, View.table_name, 'type')
end
def transformed_values
values.map { |value| value[/Views::(?<name>.*?)$/, "name"].underscore }
end
def allowed_values
Constants::Views.registered_types.map do |type|
long_name = "Views::#{type}"
[long_name, long_name]
end
end
end

@ -33,4 +33,8 @@ FactoryBot.define do
end
factory :view_work_packages_table, parent: :view
factory :view_team_planner, parent: :view do
type { 'team_planner' }
end
end

@ -0,0 +1,60 @@
#-- copyright
# OpenProject is an open source project management software.
# Copyright (C) 2012-2021 the OpenProject GmbH
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License version 3.
#
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
# Copyright (C) 2006-2013 Jean-Philippe Lang
# Copyright (C) 2010-2013 the ChiliProject Team
#
# 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; either version 2
# of the License, or (at your option) any later version.
#
# 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.
#
# See COPYRIGHT and LICENSE files for more details.
#++
require 'spec_helper'
describe Queries::Views::Filters::TypeFilter, type: :model do
let(:current_user) { FactoryBot.create(:user) }
before do
login_as(current_user)
end
it_behaves_like 'basic query filter' do
let(:class_key) { :type }
let(:type) { :list_optional }
describe '#allowed_values' do
it 'is a list of the possible values' do
expected = [
%w[Views::TeamPlanner Views::TeamPlanner],
%w[Views::WorkPackagesTable Views::WorkPackagesTable]
]
expect(instance.allowed_values).to match_array(expected)
end
end
end
it_behaves_like 'list_optional query filter' do
let(:attribute) { :type }
let(:model) { View }
let(:valid_values) { %w[Views::TeamPlanner Views::WorkPackagesTable] }
let(:transformed_values) { %w[team_planner work_packages_table] }
end
end

@ -84,6 +84,11 @@ describe ::API::V3::Views::ViewsAPI,
query: user_private_other_project_query)
end
shared_let(:user_public_project_team_planner_view) do
FactoryBot.create(:view_team_planner,
query: user_public_project_query)
end
let(:views) do
[user_private_project_view,
user_private_other_project_view,
@ -131,11 +136,38 @@ describe ::API::V3::Views::ViewsAPI,
]
end
it_behaves_like 'API V3 collection response', 2, 2, 'Views::WorkPackagesTable' do
it_behaves_like 'API V3 collection response', 2, 2, 'Views::WorkPackageTable' do
let(:elements) do
[
user_public_project_view,
user_private_project_view
user_public_project_team_planner_view
]
end
end
end
context 'with a type filter' do
let(:views) do
[
user_public_project_team_planner_view,
user_public_project_view
]
end
let(:filters) do
[
{
'type' => {
'operator' => '=',
'values' => ['Views::TeamPlanner']
}
}
]
end
it_behaves_like 'API V3 collection response', 1, 1, 'Views::TeamPlanner' do
let(:elements) do
[
user_public_project_team_planner_view
]
end
end

@ -149,13 +149,14 @@ shared_examples_for 'list_optional query filter' do
describe '#scope' do
let(:values) { valid_values }
let(:db_values) { transformed_values || valid_values }
context 'for "="' do
let(:operator) { '=' }
it 'is the same as handwriting the query' do
expected = expected_base_scope
.where(["#{expected_table_name}.#{attribute} IN (?)", values])
.where(["#{expected_table_name}.#{attribute} IN (?)", db_values])
expect(instance.scope.to_sql).to eql expected.to_sql
end
@ -167,7 +168,7 @@ shared_examples_for 'list_optional query filter' do
it 'is the same as handwriting the query' do
sql = "(#{expected_table_name}.#{attribute} IS NULL
OR #{expected_table_name}.#{attribute} NOT IN (?))".squish
expected = expected_base_scope.where([sql, values])
expected = expected_base_scope.where([sql, db_values])
expect(instance.scope.to_sql).to eql expected.to_sql
end

Loading…
Cancel
Save