ransack 1.2.3 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +3 -4
  3. data/CONTRIBUTING.md +12 -4
  4. data/Gemfile +4 -5
  5. data/README.md +160 -55
  6. data/lib/ransack.rb +1 -1
  7. data/lib/ransack/adapters/active_record/3.0/context.rb +16 -0
  8. data/lib/ransack/adapters/active_record/3.1/context.rb +24 -0
  9. data/lib/ransack/adapters/active_record/base.rb +6 -0
  10. data/lib/ransack/adapters/active_record/context.rb +49 -1
  11. data/lib/ransack/configuration.rb +23 -6
  12. data/lib/ransack/constants.rb +46 -45
  13. data/lib/ransack/context.rb +19 -2
  14. data/lib/ransack/helpers/form_builder.rb +5 -4
  15. data/lib/ransack/helpers/form_helper.rb +34 -14
  16. data/lib/ransack/locale/hu.yml +70 -0
  17. data/lib/ransack/locale/nl.yml +70 -0
  18. data/lib/ransack/nodes/attribute.rb +2 -2
  19. data/lib/ransack/nodes/condition.rb +29 -12
  20. data/lib/ransack/nodes/grouping.rb +6 -6
  21. data/lib/ransack/nodes/node.rb +1 -1
  22. data/lib/ransack/nodes/value.rb +1 -1
  23. data/lib/ransack/predicate.rb +4 -5
  24. data/lib/ransack/ransacker.rb +1 -1
  25. data/lib/ransack/search.rb +39 -13
  26. data/lib/ransack/translate.rb +7 -8
  27. data/lib/ransack/version.rb +1 -1
  28. data/ransack.gemspec +5 -5
  29. data/spec/ransack/adapters/active_record/base_spec.rb +78 -35
  30. data/spec/ransack/adapters/active_record/context_spec.rb +58 -15
  31. data/spec/ransack/configuration_spec.rb +18 -18
  32. data/spec/ransack/dependencies_spec.rb +1 -1
  33. data/spec/ransack/helpers/form_builder_spec.rb +29 -29
  34. data/spec/ransack/helpers/form_helper_spec.rb +14 -1
  35. data/spec/ransack/nodes/condition_spec.rb +21 -2
  36. data/spec/ransack/predicate_spec.rb +49 -9
  37. data/spec/ransack/search_spec.rb +178 -143
  38. data/spec/ransack/translate_spec.rb +1 -1
  39. data/spec/spec_helper.rb +1 -0
  40. data/spec/support/schema.rb +26 -21
  41. metadata +15 -11
@@ -46,7 +46,7 @@ module Ransack
46
46
  should match /sort_link desc/
47
47
  }
48
48
  it {
49
- should match /Full Name ▼/
49
+ should match /Full Name ▼/
50
50
  }
51
51
  end
52
52
 
@@ -71,6 +71,19 @@ module Ransack
71
71
  }
72
72
  end
73
73
 
74
+ describe '#sort_link works even if search params are a blank string' do
75
+ before { @controller.view_context.params[:q] = '' }
76
+ specify {
77
+ expect {
78
+ @controller.view_context.sort_link(
79
+ Person.search(@controller.view_context.params[:q]),
80
+ :name,
81
+ :controller => 'people'
82
+ )
83
+ }.not_to raise_error
84
+ }
85
+ end
86
+
74
87
  describe '#sort_link with default search_key defined as string' do
75
88
  subject {
76
89
  @controller.view_context.sort_link(
@@ -7,9 +7,28 @@ module Ransack
7
7
  context 'with multiple values and an _any predicate' do
8
8
  subject { Condition.extract(Context.for(Person), 'name_eq_any', Person.first(2).map(&:name)) }
9
9
 
10
- specify { subject.values.should have(2).values }
10
+ specify { expect(subject.values.size).to eq(2) }
11
11
  end
12
12
 
13
+ context 'with an invalid predicate' do
14
+ subject { Condition.extract(Context.for(Person), 'name_invalid', Person.first.name) }
15
+
16
+ context "when ignore_unknown_conditions is false" do
17
+ before do
18
+ Ransack.configure { |config| config.ignore_unknown_conditions = false }
19
+ end
20
+
21
+ specify { expect { subject }.to raise_error ArgumentError }
22
+ end
23
+
24
+ context "when ignore_unknown_conditions is true" do
25
+ before do
26
+ Ransack.configure { |config| config.ignore_unknown_conditions = true }
27
+ end
28
+
29
+ specify { subject.should be_nil }
30
+ end
31
+ end
13
32
  end
14
33
  end
15
- end
34
+ end
@@ -15,7 +15,7 @@ module Ransack
15
15
 
16
16
  it "escapes '%', '.' and '\\\\' in value" do
17
17
  subject.send(:"#{method}=", '%._\\')
18
- subject.result.to_sql.should match(regexp)
18
+ expect(subject.result.to_sql).to match(regexp)
19
19
  end
20
20
  end
21
21
 
@@ -24,25 +24,25 @@ module Ransack
24
24
  @s.awesome_eq = true
25
25
  field = "#{quote_table_name("people")}.#{
26
26
  quote_column_name("awesome")}"
27
- @s.result.to_sql.should match /#{field} = #{
27
+ expect(@s.result.to_sql).to match /#{field} = #{
28
28
  ActiveRecord::Base.connection.quoted_true}/
29
29
  end
30
30
 
31
31
  it 'generates an equality condition for boolean false' do
32
32
  @s.awesome_eq = false
33
33
  field = "#{quote_table_name("people")}.#{quote_column_name("awesome")}"
34
- @s.result.to_sql.should match /#{field} = #{
34
+ expect(@s.result.to_sql).to match /#{field} = #{
35
35
  ActiveRecord::Base.connection.quoted_false}/
36
36
  end
37
37
 
38
38
  it 'does not generate a condition for nil' do
39
39
  @s.awesome_eq = nil
40
- @s.result.to_sql.should_not match /WHERE/
40
+ expect(@s.result.to_sql).not_to match /WHERE/
41
41
  end
42
42
  end
43
43
 
44
44
  describe 'cont' do
45
-
45
+
46
46
  it_has_behavior 'wildcard escaping', :name_cont,
47
47
  (if ActiveRecord::Base.connection.adapter_name == "PostgreSQL"
48
48
  /"people"."name" ILIKE '%\\%\\._\\\\%'/
@@ -57,7 +57,7 @@ module Ransack
57
57
  it 'generates a LIKE query with value surrounded by %' do
58
58
  @s.name_cont = 'ric'
59
59
  field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
60
- @s.result.to_sql.should match /#{field} I?LIKE '%ric%'/
60
+ expect(@s.result.to_sql).to match /#{field} I?LIKE '%ric%'/
61
61
  end
62
62
  end
63
63
 
@@ -76,7 +76,7 @@ module Ransack
76
76
  it 'generates a NOT LIKE query with value surrounded by %' do
77
77
  @s.name_not_cont = 'ric'
78
78
  field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
79
- @s.result.to_sql.should match /#{field} NOT I?LIKE '%ric%'/
79
+ expect(@s.result.to_sql).to match /#{field} NOT I?LIKE '%ric%'/
80
80
  end
81
81
  end
82
82
 
@@ -84,7 +84,13 @@ module Ransack
84
84
  it 'generates a value IS NULL query' do
85
85
  @s.name_null = true
86
86
  field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
87
- @s.result.to_sql.should match /#{field} IS NULL/
87
+ expect(@s.result.to_sql).to match /#{field} IS NULL/
88
+ end
89
+
90
+ it 'generates a value IS NOT NULL query when assigned false' do
91
+ @s.name_null = false
92
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
93
+ expect(@s.result.to_sql).to match /#{field} IS NOT NULL/
88
94
  end
89
95
  end
90
96
 
@@ -92,7 +98,41 @@ module Ransack
92
98
  it 'generates a value IS NOT NULL query' do
93
99
  @s.name_not_null = true
94
100
  field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
95
- @s.result.to_sql.should match /#{field} IS NOT NULL/
101
+ expect(@s.result.to_sql).to match /#{field} IS NOT NULL/
102
+ end
103
+
104
+ it 'generates a value IS NULL query when assigned false' do
105
+ @s.name_not_null = false
106
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
107
+ expect(@s.result.to_sql).to match /#{field} IS NULL/
108
+ end
109
+ end
110
+
111
+ describe 'present' do
112
+ it %q[generates a value IS NOT NULL AND value != '' query] do
113
+ @s.name_present = true
114
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
115
+ expect(@s.result.to_sql).to match /#{field} IS NOT NULL AND #{field} != ''/
116
+ end
117
+
118
+ it %q[generates a value IS NULL OR value = '' query when assigned false] do
119
+ @s.name_present = false
120
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
121
+ expect(@s.result.to_sql).to match /#{field} IS NULL OR #{field} = ''/
122
+ end
123
+ end
124
+
125
+ describe 'blank' do
126
+ it %q[generates a value IS NULL OR value = '' query] do
127
+ @s.name_blank = true
128
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
129
+ expect(@s.result.to_sql).to match /#{field} IS NULL OR #{field} = ''/
130
+ end
131
+
132
+ it %q[generates a value IS NOT NULL AND value != '' query when assigned false] do
133
+ @s.name_blank = false
134
+ field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
135
+ expect(@s.result.to_sql).to match /#{field} IS NOT NULL AND #{field} != ''/
96
136
  end
97
137
  end
98
138
  end
@@ -4,104 +4,116 @@ module Ransack
4
4
  describe Search do
5
5
  describe '#initialize' do
6
6
  it "removes empty conditions before building" do
7
- Search.any_instance.should_receive(:build).with({})
7
+ expect_any_instance_of(Search).to receive(:build).with({})
8
8
  Search.new(Person, :name_eq => '')
9
9
  end
10
10
 
11
11
  it "keeps conditions with a false value before building" do
12
- Search.any_instance.should_receive(:build).with({"name_eq" => false})
12
+ expect_any_instance_of(Search).to receive(:build)
13
+ .with({ "name_eq" => false })
13
14
  Search.new(Person, :name_eq => false)
14
15
  end
15
16
 
16
17
  it "keeps conditions with a value before building" do
17
- Search.any_instance.should_receive(:build).with({"name_eq" => 'foobar'})
18
+ expect_any_instance_of(Search).to receive(:build)
19
+ .with({ "name_eq" => 'foobar' })
18
20
  Search.new(Person, :name_eq => 'foobar')
19
21
  end
20
22
 
21
23
  it "removes empty suffixed conditions before building" do
22
- Search.any_instance.should_receive(:build).with({})
24
+ expect_any_instance_of(Search).to receive(:build).with({})
23
25
  Search.new(Person, :name_eq_any => [''])
24
26
  end
25
27
 
26
28
  it "keeps suffixed conditions with a false value before building" do
27
- Search.any_instance.should_receive(:build).with({"name_eq_any" => [false]})
29
+ expect_any_instance_of(Search).to receive(:build)
30
+ .with({ "name_eq_any" => [false] })
28
31
  Search.new(Person, :name_eq_any => [false])
29
32
  end
30
33
 
31
34
  it "keeps suffixed conditions with a value before building" do
32
- Search.any_instance.should_receive(:build).with({"name_eq_any" => ['foobar']})
35
+ expect_any_instance_of(Search).to receive(:build)
36
+ .with({ "name_eq_any" => ['foobar'] })
33
37
  Search.new(Person, :name_eq_any => ['foobar'])
34
38
  end
35
39
 
36
-
37
- end
38
-
39
- describe '#initialize' do
40
40
  it 'does not raise exception for string :params argument' do
41
- lambda { Search.new(Person, '') }.should_not raise_error
41
+ expect { Search.new(Person, '') }.not_to raise_error
42
+ end
43
+
44
+ it 'accepts a context option' do
45
+ shared_context = Context.for(Person)
46
+ search1 = Search.new(Person, {"name_eq" => "A"}, context: shared_context)
47
+ search2 = Search.new(Person, {"name_eq" => "B"}, context: shared_context)
48
+ expect(search1.context).to be search2.context
42
49
  end
43
50
  end
44
51
 
45
52
  describe '#build' do
46
53
  it 'creates conditions for top-level attributes' do
47
- search = Search.new(Person, name_eq: 'Ernie')
54
+ search = Search.new(Person, :name_eq => 'Ernie')
48
55
  condition = search.base[:name_eq]
49
- condition.should be_a Nodes::Condition
50
- condition.predicate.name.should eq 'eq'
51
- condition.attributes.first.name.should eq 'name'
52
- condition.value.should eq 'Ernie'
56
+ expect(condition).to be_a Nodes::Condition
57
+ expect(condition.predicate.name).to eq 'eq'
58
+ expect(condition.attributes.first.name).to eq 'name'
59
+ expect(condition.value).to eq 'Ernie'
53
60
  end
54
61
 
55
62
  it 'creates conditions for association attributes' do
56
- search = Search.new(Person, children_name_eq: 'Ernie')
63
+ search = Search.new(Person, :children_name_eq => 'Ernie')
57
64
  condition = search.base[:children_name_eq]
58
- condition.should be_a Nodes::Condition
59
- condition.predicate.name.should eq 'eq'
60
- condition.attributes.first.name.should eq 'children_name'
61
- condition.value.should eq 'Ernie'
65
+ expect(condition).to be_a Nodes::Condition
66
+ expect(condition.predicate.name).to eq 'eq'
67
+ expect(condition.attributes.first.name).to eq 'children_name'
68
+ expect(condition.value).to eq 'Ernie'
62
69
  end
63
70
 
64
71
  it 'creates conditions for polymorphic belongs_to association attributes' do
65
- search = Search.new(Note, notable_of_Person_type_name_eq: 'Ernie')
72
+ search = Search.new(Note, :notable_of_Person_type_name_eq => 'Ernie')
66
73
  condition = search.base[:notable_of_Person_type_name_eq]
67
- condition.should be_a Nodes::Condition
68
- condition.predicate.name.should eq 'eq'
69
- condition.attributes.first.name.should eq 'notable_of_Person_type_name'
70
- condition.value.should eq 'Ernie'
74
+ expect(condition).to be_a Nodes::Condition
75
+ expect(condition.predicate.name).to eq 'eq'
76
+ expect(condition.attributes.first.name).to eq 'notable_of_Person_type_name'
77
+ expect(condition.value).to eq 'Ernie'
71
78
  end
72
79
 
73
80
  it 'creates conditions for multiple polymorphic belongs_to association attributes' do
74
81
  search = Search.new(Note,
75
- notable_of_Person_type_name_or_notable_of_Article_type_title_eq: 'Ernie')
82
+ :notable_of_Person_type_name_or_notable_of_Article_type_title_eq => 'Ernie')
76
83
  condition = search.
77
84
  base[:notable_of_Person_type_name_or_notable_of_Article_type_title_eq]
78
- condition.should be_a Nodes::Condition
79
- condition.predicate.name.should eq 'eq'
80
- condition.attributes.first.name.should eq 'notable_of_Person_type_name'
81
- condition.attributes.last.name.should eq 'notable_of_Article_type_title'
82
- condition.value.should eq 'Ernie'
85
+ expect(condition).to be_a Nodes::Condition
86
+ expect(condition.predicate.name).to eq 'eq'
87
+ expect(condition.attributes.first.name).to eq 'notable_of_Person_type_name'
88
+ expect(condition.attributes.last.name).to eq 'notable_of_Article_type_title'
89
+ expect(condition.value).to eq 'Ernie'
83
90
  end
84
91
 
85
92
  it 'discards empty conditions' do
86
- search = Search.new(Person, children_name_eq: '')
93
+ search = Search.new(Person, :children_name_eq => '')
87
94
  condition = search.base[:children_name_eq]
88
- condition.should be_nil
95
+ expect(condition).to be_nil
96
+ end
97
+
98
+ it 'accepts base grouping condition as an option' do
99
+ expect(Nodes::Grouping).to receive(:new).with(kind_of(Context), 'or')
100
+ Search.new(Person, {}, { grouping: 'or' })
89
101
  end
90
102
 
91
103
  it 'accepts arrays of groupings' do
92
104
  search = Search.new(Person,
93
105
  g: [
94
- { m: 'or', name_eq: 'Ernie', children_name_eq: 'Ernie' },
95
- { m: 'or', name_eq: 'Bert', children_name_eq: 'Bert' },
106
+ { :m => 'or', :name_eq => 'Ernie', :children_name_eq => 'Ernie' },
107
+ { :m => 'or', :name_eq => 'Bert', :children_name_eq => 'Bert' },
96
108
  ]
97
109
  )
98
110
  ors = search.groupings
99
- ors.should have(2).items
111
+ expect(ors.size).to eq(2)
100
112
  or1, or2 = ors
101
- or1.should be_a Nodes::Grouping
102
- or1.combinator.should eq 'or'
103
- or2.should be_a Nodes::Grouping
104
- or2.combinator.should eq 'or'
113
+ expect(or1).to be_a Nodes::Grouping
114
+ expect(or1.combinator).to eq 'or'
115
+ expect(or2).to be_a Nodes::Grouping
116
+ expect(or2.combinator).to eq 'or'
105
117
  end
106
118
 
107
119
  it 'accepts "attributes" hashes for groupings' do
@@ -112,12 +124,12 @@ module Ransack
112
124
  }
113
125
  )
114
126
  ors = search.groupings
115
- ors.should have(2).items
127
+ expect(ors.size).to eq(2)
116
128
  or1, or2 = ors
117
- or1.should be_a Nodes::Grouping
118
- or1.combinator.should eq 'or'
119
- or2.should be_a Nodes::Grouping
120
- or2.combinator.should eq 'or'
129
+ expect(or1).to be_a Nodes::Grouping
130
+ expect(or1.combinator).to eq 'or'
131
+ expect(or2).to be_a Nodes::Grouping
132
+ expect(or2.combinator).to eq 'or'
121
133
  end
122
134
 
123
135
  it 'accepts "attributes" hashes for conditions' do
@@ -129,9 +141,9 @@ module Ransack
129
141
  }
130
142
  )
131
143
  conditions = search.base.conditions
132
- conditions.should have(2).items
133
- conditions.map { |c| c.class }
134
- .should eq [Nodes::Condition, Nodes::Condition]
144
+ expect(conditions.size).to eq(2)
145
+ expect(conditions.map { |c| c.class })
146
+ .to eq [Nodes::Condition, Nodes::Condition]
135
147
  end
136
148
 
137
149
  it 'creates conditions for custom predicates that take arrays' do
@@ -139,17 +151,37 @@ module Ransack
139
151
  config.add_predicate 'ary_pred', :wants_array => true
140
152
  end
141
153
 
142
- search = Search.new(Person, name_ary_pred: ['Ernie', 'Bert'])
154
+ search = Search.new(Person, :name_ary_pred => ['Ernie', 'Bert'])
143
155
  condition = search.base[:name_ary_pred]
144
- condition.should be_a Nodes::Condition
145
- condition.predicate.name.should eq 'ary_pred'
146
- condition.attributes.first.name.should eq 'name'
147
- condition.value.should eq ['Ernie', 'Bert']
156
+ expect(condition).to be_a Nodes::Condition
157
+ expect(condition.predicate.name).to eq 'ary_pred'
158
+ expect(condition.attributes.first.name).to eq 'name'
159
+ expect(condition.value).to eq ['Ernie', 'Bert']
148
160
  end
149
161
 
150
162
  it 'does not evaluate the query on #inspect' do
151
- search = Search.new(Person, children_id_in: [1, 2, 3])
152
- search.inspect.should_not match /ActiveRecord/
163
+ search = Search.new(Person, :children_id_in => [1, 2, 3])
164
+ expect(search.inspect).not_to match /ActiveRecord/
165
+ end
166
+
167
+ context 'with an invalid condition' do
168
+ subject { Search.new(Person, :unknown_attr_eq => 'Ernie') }
169
+
170
+ context "when ignore_unknown_conditions is false" do
171
+ before do
172
+ Ransack.configure { |config| config.ignore_unknown_conditions = false }
173
+ end
174
+
175
+ specify { expect { subject }.to raise_error ArgumentError }
176
+ end
177
+
178
+ context "when ignore_unknown_conditions is true" do
179
+ before do
180
+ Ransack.configure { |config| config.ignore_unknown_conditions = true }
181
+ end
182
+
183
+ specify { expect { subject }.not_to raise_error }
184
+ end
153
185
  end
154
186
  end
155
187
 
@@ -161,56 +193,59 @@ module Ransack
161
193
  "#{quote_table_name("children_people")}.#{quote_column_name("name")}"
162
194
  }
163
195
  it 'evaluates conditions contextually' do
164
- search = Search.new(Person, children_name_eq: 'Ernie')
165
- search.result.should be_an ActiveRecord::Relation
196
+ search = Search.new(Person, :children_name_eq => 'Ernie')
197
+ expect(search.result).to be_an ActiveRecord::Relation
166
198
  where = search.result.where_values.first
167
- where.to_sql.should match /#{children_people_name_field} = 'Ernie'/
199
+ expect(where.to_sql).to match /#{children_people_name_field} = 'Ernie'/
168
200
  end
169
201
 
170
202
  it 'evaluates compound conditions contextually' do
171
- search = Search.new(Person, children_name_or_name_eq: 'Ernie')
172
- search.result.should be_an ActiveRecord::Relation
203
+ search = Search.new(Person, :children_name_or_name_eq => 'Ernie')
204
+ expect(search.result).to be_an ActiveRecord::Relation
173
205
  where = search.result.where_values.first
174
- where.to_sql.should match /#{children_people_name_field
206
+ expect(where.to_sql).to match /#{children_people_name_field
175
207
  } = 'Ernie' OR #{people_name_field} = 'Ernie'/
176
208
  end
177
209
 
178
210
  it 'evaluates polymorphic belongs_to association conditions contextually' do
179
- search = Search.new(Note, notable_of_Person_type_name_eq: 'Ernie')
180
- search.result.should be_an ActiveRecord::Relation
211
+ search = Search.new(Note, :notable_of_Person_type_name_eq => 'Ernie')
212
+ expect(search.result).to be_an ActiveRecord::Relation
181
213
  where = search.result.where_values.first
182
- where.to_sql.should match /#{people_name_field} = 'Ernie'/
214
+ expect(where.to_sql).to match /#{people_name_field} = 'Ernie'/
183
215
  end
184
216
 
185
217
  it 'evaluates nested conditions' do
186
- search = Search.new(Person, children_name_eq: 'Ernie',
187
- g: [
188
- { m: 'or', name_eq: 'Ernie', children_children_name_eq: 'Ernie' }
218
+ search = Search.new(Person, :children_name_eq => 'Ernie',
219
+ :g => [
220
+ { :m => 'or',
221
+ :name_eq => 'Ernie',
222
+ :children_children_name_eq => 'Ernie'
223
+ }
189
224
  ]
190
225
  )
191
- search.result.should be_an ActiveRecord::Relation
226
+ expect(search.result).to be_an ActiveRecord::Relation
192
227
  where = search.result.where_values.first
193
- where.to_sql.should match /#{children_people_name_field} = 'Ernie'/
194
- where.to_sql.should match /#{people_name_field} = 'Ernie'/
195
- where.to_sql.should match /#{quote_table_name("children_people_2")
228
+ expect(where.to_sql).to match /#{children_people_name_field} = 'Ernie'/
229
+ expect(where.to_sql).to match /#{people_name_field} = 'Ernie'/
230
+ expect(where.to_sql).to match /#{quote_table_name("children_people_2")
196
231
  }.#{quote_column_name("name")} = 'Ernie'/
197
232
  end
198
233
 
199
234
  it 'evaluates arrays of groupings' do
200
235
  search = Search.new(Person,
201
- g: [
202
- { m: 'or', name_eq: 'Ernie', children_name_eq: 'Ernie'},
203
- { m: 'or', name_eq: 'Bert', children_name_eq: 'Bert'},
236
+ :g => [
237
+ { :m => 'or', :name_eq => 'Ernie', :children_name_eq => 'Ernie' },
238
+ { :m => 'or', :name_eq => 'Bert', :children_name_eq => 'Bert' }
204
239
  ]
205
240
  )
206
- search.result.should be_an ActiveRecord::Relation
241
+ expect(search.result).to be_an ActiveRecord::Relation
207
242
  where = search.result.where_values.first
208
243
  sql = where.to_sql
209
244
  first, second = sql.split(/ AND /)
210
- first.should match /#{people_name_field} = 'Ernie'/
211
- first.should match /#{children_people_name_field} = 'Ernie'/
212
- second.should match /#{people_name_field} = 'Bert'/
213
- second.should match /#{children_people_name_field} = 'Bert'/
245
+ expect(first).to match /#{people_name_field} = 'Ernie'/
246
+ expect(first).to match /#{children_people_name_field} = 'Ernie'/
247
+ expect(second).to match /#{people_name_field} = 'Bert'/
248
+ expect(second).to match /#{children_people_name_field} = 'Bert'/
214
249
  end
215
250
 
216
251
  it 'returns distinct records when passed :distinct => true' do
@@ -227,12 +262,12 @@ module Ransack
227
262
  else
228
263
  all_or_load, uniq_or_distinct = :load, :distinct
229
264
  end
230
- search.result.send(all_or_load).
231
- should have(9000).items
232
- search.result(:distinct => true).
233
- should have(10).items
234
- search.result.send(all_or_load).send(uniq_or_distinct).
235
- should eq search.result(:distinct => true).send(all_or_load)
265
+ expect(search.result.send(all_or_load).size)
266
+ .to eq(9000)
267
+ expect(search.result(:distinct => true).size)
268
+ .to eq(10)
269
+ expect(search.result.send(all_or_load).send(uniq_or_distinct))
270
+ .to eq search.result(:distinct => true).send(all_or_load)
236
271
  end
237
272
  end
238
273
 
@@ -243,109 +278,109 @@ module Ransack
243
278
 
244
279
  it 'creates sorts based on a single attribute/direction' do
245
280
  @s.sorts = 'id desc'
246
- @s.sorts.should have(1).item
281
+ expect(@s.sorts.size).to eq(1)
247
282
  sort = @s.sorts.first
248
- sort.should be_a Nodes::Sort
249
- sort.name.should eq 'id'
250
- sort.dir.should eq 'desc'
283
+ expect(sort).to be_a Nodes::Sort
284
+ expect(sort.name).to eq 'id'
285
+ expect(sort.dir).to eq 'desc'
251
286
  end
252
287
 
253
288
  it 'creates sorts based on a single attribute and uppercase direction' do
254
289
  @s.sorts = 'id DESC'
255
- @s.sorts.should have(1).item
290
+ expect(@s.sorts.size).to eq(1)
256
291
  sort = @s.sorts.first
257
- sort.should be_a Nodes::Sort
258
- sort.name.should eq 'id'
259
- sort.dir.should eq 'desc'
292
+ expect(sort).to be_a Nodes::Sort
293
+ expect(sort.name).to eq 'id'
294
+ expect(sort.dir).to eq 'desc'
260
295
  end
261
296
 
262
297
  it 'creates sorts based on a single attribute and without direction' do
263
298
  @s.sorts = 'id'
264
- @s.sorts.should have(1).item
299
+ expect(@s.sorts.size).to eq(1)
265
300
  sort = @s.sorts.first
266
- sort.should be_a Nodes::Sort
267
- sort.name.should eq 'id'
268
- sort.dir.should eq 'asc'
301
+ expect(sort).to be_a Nodes::Sort
302
+ expect(sort.name).to eq 'id'
303
+ expect(sort.dir).to eq 'asc'
269
304
  end
270
305
 
271
306
  it 'creates sorts based on multiple attributes/directions in array format' do
272
- @s.sorts = ['id desc', { name: 'name', dir: 'asc' }]
273
- @s.sorts.should have(2).items
307
+ @s.sorts = ['id desc', { :name => 'name', :dir => 'asc' }]
308
+ expect(@s.sorts.size).to eq(2)
274
309
  sort1, sort2 = @s.sorts
275
- sort1.should be_a Nodes::Sort
276
- sort1.name.should eq 'id'
277
- sort1.dir.should eq 'desc'
278
- sort2.should be_a Nodes::Sort
279
- sort2.name.should eq 'name'
280
- sort2.dir.should eq 'asc'
310
+ expect(sort1).to be_a Nodes::Sort
311
+ expect(sort1.name).to eq 'id'
312
+ expect(sort1.dir).to eq 'desc'
313
+ expect(sort2).to be_a Nodes::Sort
314
+ expect(sort2.name).to eq 'name'
315
+ expect(sort2.dir).to eq 'asc'
281
316
  end
282
317
 
283
318
  it 'creates sorts based on multiple attributes and uppercase directions in array format' do
284
- @s.sorts = ['id DESC', { name: 'name', dir: 'ASC' }]
285
- @s.sorts.should have(2).items
319
+ @s.sorts = ['id DESC', { :name => 'name', :dir => 'ASC' }]
320
+ expect(@s.sorts.size).to eq(2)
286
321
  sort1, sort2 = @s.sorts
287
- sort1.should be_a Nodes::Sort
288
- sort1.name.should eq 'id'
289
- sort1.dir.should eq 'desc'
290
- sort2.should be_a Nodes::Sort
291
- sort2.name.should eq 'name'
292
- sort2.dir.should eq 'asc'
322
+ expect(sort1).to be_a Nodes::Sort
323
+ expect(sort1.name).to eq 'id'
324
+ expect(sort1.dir).to eq 'desc'
325
+ expect(sort2).to be_a Nodes::Sort
326
+ expect(sort2.name).to eq 'name'
327
+ expect(sort2.dir).to eq 'asc'
293
328
  end
294
329
 
295
330
  it 'creates sorts based on multiple attributes and different directions in array format' do
296
331
  @s.sorts = ['id DESC', { name: 'name', dir: nil }]
297
- @s.sorts.should have(2).items
332
+ expect(@s.sorts.size).to eq(2)
298
333
  sort1, sort2 = @s.sorts
299
- sort1.should be_a Nodes::Sort
300
- sort1.name.should eq 'id'
301
- sort1.dir.should eq 'desc'
302
- sort2.should be_a Nodes::Sort
303
- sort2.name.should eq 'name'
304
- sort2.dir.should eq 'asc'
334
+ expect(sort1).to be_a Nodes::Sort
335
+ expect(sort1.name).to eq 'id'
336
+ expect(sort1.dir).to eq 'desc'
337
+ expect(sort2).to be_a Nodes::Sort
338
+ expect(sort2.name).to eq 'name'
339
+ expect(sort2.dir).to eq 'asc'
305
340
  end
306
341
 
307
342
  it 'creates sorts based on multiple attributes/directions in hash format' do
308
343
  @s.sorts = {
309
- '0' => { name: 'id', dir: 'desc' },
310
- '1' => { name: 'name', dir: 'asc' }
344
+ '0' => { :name => 'id', :dir => 'desc' },
345
+ '1' => { :name => 'name', :dir => 'asc' }
311
346
  }
312
- @s.sorts.should have(2).items
313
- @s.sorts.should be_all { |s| Nodes::Sort === s }
347
+ expect(@s.sorts.size).to eq(2)
348
+ expect(@s.sorts).to be_all { |s| Nodes::Sort === s }
314
349
  id_sort = @s.sorts.detect { |s| s.name == 'id' }
315
350
  name_sort = @s.sorts.detect { |s| s.name == 'name' }
316
- id_sort.dir.should eq 'desc'
317
- name_sort.dir.should eq 'asc'
351
+ expect(id_sort.dir).to eq 'desc'
352
+ expect(name_sort.dir).to eq 'asc'
318
353
  end
319
354
 
320
355
  it 'creates sorts based on multiple attributes and uppercase directions in hash format' do
321
356
  @s.sorts = {
322
- '0' => { name: 'id', dir: 'DESC' },
323
- '1' => { name: 'name', dir: 'ASC' }
357
+ '0' => { :name => 'id', :dir => 'DESC' },
358
+ '1' => { :name => 'name', :dir => 'ASC' }
324
359
  }
325
- @s.sorts.should have(2).items
326
- @s.sorts.should be_all { |s| Nodes::Sort === s }
360
+ expect(@s.sorts.size).to eq(2)
361
+ expect(@s.sorts).to be_all { |s| Nodes::Sort === s }
327
362
  id_sort = @s.sorts.detect { |s| s.name == 'id' }
328
363
  name_sort = @s.sorts.detect { |s| s.name == 'name' }
329
- id_sort.dir.should eq 'desc'
330
- name_sort.dir.should eq 'asc'
364
+ expect(id_sort.dir).to eq 'desc'
365
+ expect(name_sort.dir).to eq 'asc'
331
366
  end
332
367
 
333
368
  it 'creates sorts based on multiple attributes and different directions in hash format' do
334
369
  @s.sorts = {
335
- '0' => { name: 'id', dir: 'DESC' },
336
- '1' => { name: 'name', dir: nil }
370
+ '0' => { :name => 'id', :dir => 'DESC' },
371
+ '1' => { :name => 'name', :dir => nil }
337
372
  }
338
- @s.sorts.should have(2).items
339
- @s.sorts.should be_all { |s| Nodes::Sort === s }
373
+ expect(@s.sorts.size).to eq(2)
374
+ expect(@s.sorts).to be_all { |s| Nodes::Sort === s }
340
375
  id_sort = @s.sorts.detect { |s| s.name == 'id' }
341
376
  name_sort = @s.sorts.detect { |s| s.name == 'name' }
342
- id_sort.dir.should eq 'desc'
343
- name_sort.dir.should eq 'asc'
377
+ expect(id_sort.dir).to eq 'desc'
378
+ expect(name_sort.dir).to eq 'asc'
344
379
  end
345
380
 
346
381
  it 'overrides existing sort' do
347
382
  @s.sorts = 'id asc'
348
- @s.result.first.id.should eq 1
383
+ expect(@s.result.first.id).to eq 1
349
384
  end
350
385
  end
351
386
 
@@ -360,14 +395,14 @@ module Ransack
360
395
 
361
396
  it 'sets condition attributes when sent valid attributes' do
362
397
  @s.name_eq = 'Ernie'
363
- @s.name_eq.should eq 'Ernie'
398
+ expect(@s.name_eq).to eq 'Ernie'
364
399
  end
365
400
 
366
401
  it 'allows chaining to access nested conditions' do
367
402
  @s.groupings = [
368
- { m: 'or', name_eq: 'Ernie', children_name_eq: 'Ernie' }
403
+ { :m => 'or', :name_eq => 'Ernie', :children_name_eq => 'Ernie' }
369
404
  ]
370
- @s.groupings.first.children_name_eq.should eq 'Ernie'
405
+ expect(@s.groupings.first.children_name_eq).to eq 'Ernie'
371
406
  end
372
407
  end
373
408
  end