Skip to content

Commit 5d4dd07

Browse files
committed
[#75510] Add spec coverage for filter input forms
Adds 47 specs across 6 form classes and a shared context. Covers TextForm, ListForm, DateForm, BooleanForm, AutocompleteForm, and AddFilterForm with assertions on rendered structure, data attributes, and operator routing. https://community.openproject.org/wp/75510
1 parent a5ee2b5 commit 5d4dd07

7 files changed

Lines changed: 543 additions & 0 deletions

File tree

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
require "spec_helper"
32+
33+
RSpec.describe Filters::Inputs::AddFilterForm, type: :forms do
34+
include ViewComponent::TestHelpers
35+
36+
let(:query) { UserQuery.new }
37+
let(:allowed_filters) { query.available_advanced_filters }
38+
let(:active_filter_names) { [] }
39+
40+
def render_add_filter_form(allowed_filters: self.allowed_filters,
41+
active_filter_names: self.active_filter_names)
42+
form_class = described_class
43+
render_in_view_context(form_class, allowed_filters, active_filter_names) do |form_class, allowed_filters, active_filter_names|
44+
primer_form_with(url: "/test", method: :post) do |f|
45+
render(form_class.new(f, allowed_filters:, active_filter_names:))
46+
end
47+
end
48+
end
49+
50+
subject(:rendered_form) do
51+
render_add_filter_form
52+
page
53+
end
54+
55+
it "renders a select named add_filter_select" do
56+
expect(rendered_form).to have_select "add_filter_select"
57+
end
58+
59+
it "has the addFilterSelect Stimulus target" do
60+
expect(rendered_form).to have_element :select,
61+
"data-filter--filters-form-target": "addFilterSelect"
62+
end
63+
64+
it "includes a blank prompt option" do
65+
select = rendered_form.find(:select, "add_filter_select")
66+
expect(select).to have_selector :option, text: I18n.t(:actionview_instancetag_blank_option)
67+
end
68+
69+
it "lists all allowed filters as options" do
70+
expect(rendered_form).to have_select "add_filter_select" do |select|
71+
allowed_filters.each do |af|
72+
expect(select).to have_selector :option, text: af.human_name
73+
end
74+
end
75+
end
76+
77+
context "with active filters" do
78+
let(:active_filter_names) { [:login] }
79+
80+
it "disables the active filter option" do
81+
select = rendered_form.find(:select, "add_filter_select")
82+
login_option = select.find(:option, text: "Username")
83+
expect(login_option).to be_disabled
84+
end
85+
86+
it "does not disable inactive filter options" do
87+
select = rendered_form.find(:select, "add_filter_select")
88+
status_option = select.find(:option, text: "Status")
89+
expect(status_option).not_to be_disabled
90+
end
91+
end
92+
end
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
require "spec_helper"
32+
33+
RSpec.describe Filters::Inputs::AutocompleteForm, type: :forms do
34+
include_context "with rendered filter input form"
35+
36+
let(:query) { UserQuery.new }
37+
let(:filter) do
38+
query.available_advanced_filters.detect { |af| af.name == :login }
39+
end
40+
let(:additional_attributes) do
41+
{
42+
autocomplete_options: {
43+
component: "opce-autocompleter",
44+
resource: "users",
45+
searchKey: "login"
46+
}
47+
}
48+
end
49+
50+
it_behaves_like "rendering filter row"
51+
it_behaves_like "rendering operator select"
52+
it_behaves_like "hidden when inactive"
53+
54+
it "renders an autocompleter component" do
55+
expect(rendered_form).to have_element "opce-autocompleter", visible: :all
56+
end
57+
58+
it "marks the wrapper as filter-autocomplete" do
59+
expect(rendered_form).to have_element "data-filter-name": "login",
60+
"data-filter-autocomplete": "true",
61+
visible: :all
62+
end
63+
64+
it "renders the autocompleter as multiple" do
65+
expect(rendered_form).to have_element "opce-autocompleter",
66+
"data-multiple": "true",
67+
visible: :all
68+
end
69+
end
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
require "spec_helper"
32+
33+
RSpec.describe Filters::Inputs::BooleanForm, type: :forms do
34+
include_context "with rendered filter input form"
35+
36+
let(:query) { UserQuery.new }
37+
let(:filter) do
38+
query.available_advanced_filters.detect { |af| af.name == :blocked }
39+
end
40+
41+
it_behaves_like "rendering filter row"
42+
it_behaves_like "hidden when inactive"
43+
44+
it "includes the operator select (hidden by Primer)" do
45+
expect(rendered_form).to have_select "operator_blocked", visible: :all
46+
end
47+
48+
it "renders a segmented control with Yes and No" do
49+
expect(rendered_form).to have_element "data-filter-name": "blocked" do |row|
50+
expect(row).to have_button I18n.t("general_text_Yes")
51+
expect(row).to have_button I18n.t("general_text_No")
52+
end
53+
end
54+
end
Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
require "spec_helper"
32+
33+
RSpec.describe Filters::Inputs::DateForm, type: :forms do
34+
include_context "with rendered filter input form"
35+
36+
let!(:date_field) { create(:user_custom_field, field_format: "date") }
37+
let(:query) { UserQuery.new }
38+
let(:filter) do
39+
f = query.available_advanced_filters.detect { |af| af.name == :"cf_#{date_field.id}" }
40+
f.operator = operator
41+
f.values = values
42+
f
43+
end
44+
45+
it_behaves_like "rendering filter row" do
46+
let(:operator) { "=d" }
47+
let(:values) { [Date.current.iso8601] }
48+
end
49+
50+
it_behaves_like "rendering operator select" do
51+
let(:operator) { "=d" }
52+
let(:values) { [Date.current.iso8601] }
53+
end
54+
55+
it_behaves_like "hidden when inactive" do
56+
let(:operator) { "=d" }
57+
let(:values) { [Date.current.iso8601] }
58+
end
59+
60+
context "with a days operator (>t-)" do
61+
let(:operator) { ">t-" }
62+
let(:values) { ["7"] }
63+
64+
it "renders a days number input" do
65+
expect(rendered_form).to have_element :input,
66+
"data-filter--filters-form-target": "days",
67+
type: "number",
68+
visible: :all
69+
end
70+
end
71+
72+
context "with an on-date operator (=d)" do
73+
let(:operator) { "=d" }
74+
let(:values) { [Date.current.iso8601] }
75+
76+
it "renders the value container with the filter name" do
77+
expect(rendered_form).to have_element "data-filter--filters-form-target": /filterValueContainer/,
78+
"data-filter-name": filter.name.to_s,
79+
visible: :all
80+
end
81+
82+
it "hides the days input" do
83+
days_input = rendered_form.find(:element, "data-filter--filters-form-target": "days", visible: :all)
84+
expect(days_input["hidden"]).to eq("hidden")
85+
end
86+
end
87+
88+
context "with a between-dates operator (<>d)" do
89+
let(:operator) { "<>d" }
90+
let(:values) { [1.week.ago.to_date.iso8601, Date.current.iso8601] }
91+
92+
it "renders the value container with the filter name" do
93+
expect(rendered_form).to have_element "data-filter--filters-form-target": /filterValueContainer/,
94+
"data-filter-name": filter.name.to_s,
95+
visible: :all
96+
end
97+
98+
it "hides the days input" do
99+
days_input = rendered_form.find(:element, "data-filter--filters-form-target": "days", visible: :all)
100+
expect(days_input["hidden"]).to eq("hidden")
101+
end
102+
end
103+
end
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
require "spec_helper"
32+
33+
RSpec.describe Filters::Inputs::ListForm, type: :forms do
34+
include_context "with rendered filter input form"
35+
36+
let(:query) { UserQuery.new }
37+
let(:filter) do
38+
query.available_advanced_filters.detect { |af| af.name == :status }
39+
end
40+
41+
it_behaves_like "rendering filter row"
42+
it_behaves_like "rendering operator select"
43+
it_behaves_like "hidden when inactive"
44+
45+
it "renders an autocompleter component" do
46+
expect(rendered_form).to have_element "opce-autocompleter", visible: :all
47+
end
48+
49+
it "marks the autocompleter as multiple" do
50+
expect(rendered_form).to have_element "opce-autocompleter",
51+
"data-multiple": "true",
52+
visible: :all
53+
end
54+
55+
it "sets data-filter-autocomplete on the wrapper" do
56+
expect(rendered_form).to have_element "data-filter-name": "status",
57+
"data-filter-autocomplete": "true",
58+
visible: :all
59+
end
60+
61+
context "with additional autocomplete options" do
62+
let(:additional_attributes) { { autocomplete_options: { appendTo: "#dialog" } } }
63+
64+
it "merges the appendTo option into the autocompleter" do
65+
autocompleter = rendered_form.find(:element, "opce-autocompleter", visible: :all)
66+
expect(autocompleter["data-append-to"]).to be_json_eql(%("#dialog"))
67+
end
68+
end
69+
end

0 commit comments

Comments
 (0)