rd_searchlogic 3.0.0.rc

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (34) hide show
  1. data/.gitignore +7 -0
  2. data/LICENSE +20 -0
  3. data/README.rdoc +308 -0
  4. data/Rakefile +42 -0
  5. data/VERSION.yml +5 -0
  6. data/init.rb +1 -0
  7. data/lib/searchlogic/active_record/association_proxy.rb +19 -0
  8. data/lib/searchlogic/active_record/consistency.rb +49 -0
  9. data/lib/searchlogic/active_record/named_scope_tools.rb +102 -0
  10. data/lib/searchlogic/core_ext/object.rb +43 -0
  11. data/lib/searchlogic/core_ext/proc.rb +17 -0
  12. data/lib/searchlogic/named_scopes/alias_scope.rb +67 -0
  13. data/lib/searchlogic/named_scopes/association_conditions.rb +163 -0
  14. data/lib/searchlogic/named_scopes/association_ordering.rb +44 -0
  15. data/lib/searchlogic/named_scopes/conditions.rb +232 -0
  16. data/lib/searchlogic/named_scopes/or_conditions.rb +141 -0
  17. data/lib/searchlogic/named_scopes/ordering.rb +74 -0
  18. data/lib/searchlogic/rails_helpers.rb +79 -0
  19. data/lib/searchlogic/search.rb +259 -0
  20. data/lib/searchlogic.rb +89 -0
  21. data/rails/init.rb +1 -0
  22. data/spec/searchlogic/active_record/association_proxy_spec.rb +23 -0
  23. data/spec/searchlogic/active_record/consistency_spec.rb +28 -0
  24. data/spec/searchlogic/core_ext/object_spec.rb +9 -0
  25. data/spec/searchlogic/core_ext/proc_spec.rb +8 -0
  26. data/spec/searchlogic/named_scopes/alias_scope_spec.rb +23 -0
  27. data/spec/searchlogic/named_scopes/association_conditions_spec.rb +221 -0
  28. data/spec/searchlogic/named_scopes/association_ordering_spec.rb +29 -0
  29. data/spec/searchlogic/named_scopes/conditions_spec.rb +321 -0
  30. data/spec/searchlogic/named_scopes/or_conditions_spec.rb +66 -0
  31. data/spec/searchlogic/named_scopes/ordering_spec.rb +34 -0
  32. data/spec/searchlogic/search_spec.rb +459 -0
  33. data/spec/spec_helper.rb +146 -0
  34. metadata +123 -0
@@ -0,0 +1,221 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../../spec_helper")
2
+
3
+ describe Searchlogic::NamedScopes::AssociationConditions do
4
+ it "should create a named scope" do
5
+ #Company.users_username_like("bjohnson").should == User.username_like("bjohnson").merge(:joins => :users)
6
+ Company.users_username_like("bjohnson").should == Company.joins(:users).where("users.username LIKE ?", "%bjohnson%")
7
+ end
8
+
9
+ it "should create a deep named scope" do
10
+ Company.users_orders_total_greater_than(10).should == Company.joins(:users=>:orders).where('orders.total > ?', 10)
11
+ end
12
+
13
+ it "should allow the use of foreign pre-existing named scopes" do
14
+ User.scope :uname, lambda { |value| {:conditions => ["users.username = ?", value]} }
15
+ Company.users_uname("bjohnson").should == Company.joins(:users).where("users.username = ?", "bjohnson")
16
+ end
17
+
18
+ it "should allow the use of deep foreign pre-existing named scopes" do
19
+ pending
20
+ condition = "orders.id > 100"
21
+ Order.scope :big_id, :conditions => condition
22
+ Company.users_orders_big_id.should == Company.joins(:users=>:orders).where(condition)
23
+ end
24
+
25
+ # it "should allow the use of foreign pre-existing alias scopes" do
26
+ # User.alias_scope :username_has, lambda { |value| User.username_like(value) }
27
+ # Company.users_username_has("bjohnson").should == Company.joins(:users).where("user.username LIKE ?", "%bjohnson%")
28
+ # end
29
+
30
+ # it "should not raise errors for scopes that don't return anything" do
31
+ # User.alias_scope :blank_scope, lambda { |value| }
32
+ # Company.users_blank_scope("bjohnson").should == {:joins => :users}
33
+ # end
34
+
35
+ it "should ignore polymorphic associations" do
36
+ lambda { Fee.owner_created_at_gt(Time.now) }.should raise_error(NoMethodError)
37
+ end
38
+
39
+ it "should not allow named scopes on non existent association columns" do
40
+ lambda { User.users_whatever_like("bjohnson") }.should raise_error(NoMethodError)
41
+ end
42
+
43
+ it "should not allow named scopes on non existent deep association columns" do
44
+ lambda { User.users_orders_whatever_like("bjohnson") }.should raise_error(NoMethodError)
45
+ end
46
+
47
+ it "should allow named scopes to be called multiple times and reflect the value passed" do
48
+ Company.users_username_like("thunt").should eq_scope(Company.joins(:users).where("users.username LIKE ?", "%thunt%"))
49
+ Company.users_username_like("bjohnson").should eq_scope(Company.joins(:users).where("users.username LIKE ?", "%bjohnson%"))
50
+ end
51
+
52
+ it "should allow deep named scopes to be called multiple times and reflect the value passed" do
53
+ Company.users_orders_total_greater_than(10).should eq_scope(Company.joins(:users=>:orders).where('orders.total > ?', 10))
54
+ Company.users_orders_total_greater_than(20).should eq_scope(Company.joins(:users=>:orders).where('orders.total > ?', 20))
55
+ end
56
+
57
+ it "should have an arity of nil if the underlying scope has an arity of nil" do
58
+ Company.users_orders_total_null.should eq_scope(Company.joins(:users=>:orders).where("orders.total IS NULL"))
59
+ end
60
+
61
+ it "should have an arity of -1 if the underlying scope has an arity of -1" do
62
+ Company.users_id_equals_any.should eq_scope(Company.joins(:users))
63
+ Company.users_id_equals_any(1).should eq_scope(Company.joins(:users).where('users.id = ?', 1))
64
+ Company.users_id_equals_any(1,2).should eq_scope(Company.joins(:users).where('users.id = ? or users.id = ?', 1, 2))
65
+ Company.users_id_equals_any(1..10).should eq_scope(Company.joins(:users).where('users.id between ? and ?', 1, 10))
66
+ end
67
+
68
+ it "should allow aliases" do
69
+ Company.users_username_contains("bjohnson").should eq_scope(Company.joins(:users).where('users.username LIKE ?', '%bjohnson%'))
70
+ end
71
+
72
+ it "should allow deep aliases" do
73
+ Company.users_orders_total_gt(10).should eq_scope(Company.joins(:users=>:orders).where("orders.total > ?", 10))
74
+ end
75
+
76
+ it "should include optional associations" do
77
+ pending # this is a problem with using inner joins and left outer joins
78
+ Company.create
79
+ company = Company.create
80
+ user = company.users.create
81
+ order = user.orders.create(:total => 20, :taxes => 3)
82
+ Company.ascend_by_users_orders_total.all.should == Company.all
83
+ end
84
+
85
+ it "should implement exclusive scoping" do
86
+ Company.users_company_name_like('name').users_company_description_like('description').should
87
+ eq_scope(Company.joins(:users=>:company).where('companies.name like ?', '%name%').where('companies.description like ?', '%description%'))
88
+ # scope = Company.users_company_name_like("name").users_company_description_like("description")
89
+ # scope.scope(:find)[:joins].should == [
90
+ # "INNER JOIN \"users\" ON companies.id = users.company_id",
91
+ # "INNER JOIN \"companies\" companies_users ON \"companies_users\".id = \"users\".company_id"
92
+ # ]
93
+ # lambda { scope.all }.should_not raise_error
94
+ end
95
+
96
+ #TODO: re-add ascend_by_users_orders_total after fixing association_ordering
97
+ it "should not create the same join twice" do
98
+ Company.users_orders_total_gt(10).users_orders_taxes_lt(5).should eq_scope(
99
+ Company.joins(:users=>:orders).where("orders.total > ?", 10).where("orders.taxes < ?", 5)
100
+ )
101
+ # scope = Company.users_orders_total_gt(10).users_orders_taxes_lt(5).ascend_by_users_orders_total
102
+ # scope.scope(:find)[:joins].should == [
103
+ # "INNER JOIN \"users\" ON companies.id = users.company_id",
104
+ # "INNER JOIN \"orders\" ON orders.user_id = users.id"
105
+ # ]
106
+ # lambda { scope.count }.should_not raise_error
107
+ end
108
+
109
+ #TODO: fix Company.joins(:users).joins(:users=>:orders) duplicates join
110
+ it "should not create the same join twice when traveling through the duplicate join" do
111
+ pending
112
+ Company.users_username_like('bj').users_orders_total_gt(100).should eq_scope(
113
+ Company.joins(:users=>:orders).where("users.username like ?", '%bj%').where("orders.total < ?", 100)
114
+ )
115
+ # scope = Company.users_username_like("bjohnson").users_orders_total_gt(100)
116
+ # scope.scope(:find)[:joins].should == [
117
+ # "INNER JOIN \"users\" ON companies.id = users.company_id",
118
+ # "INNER JOIN \"orders\" ON orders.user_id = users.id"
119
+ # ]
120
+ # lambda { scope.count }.should_not raise_error
121
+ end
122
+
123
+ # it "should not create the same join twice when traveling through the deep duplicate join" do
124
+ # scope = Company.users_orders_total_gt(100).users_orders_line_items_price_gt(20)
125
+ # scope.scope(:find)[:joins].should == [
126
+ # "INNER JOIN \"users\" ON companies.id = users.company_id",
127
+ # "INNER JOIN \"orders\" ON orders.user_id = users.id",
128
+ # "INNER JOIN \"line_items\" ON line_items.order_id = orders.id"
129
+ # ]
130
+ # lambda { scope.all }.should_not raise_error
131
+ # end
132
+ #
133
+ it "should allow the use of :include when a join was created" do
134
+ company = Company.create
135
+ user = company.users.create
136
+ order = user.orders.create(:total => 20, :taxes => 3)
137
+ #TODO: recover after fixing ordering
138
+ # Company.users_orders_total_gt(10).users_orders_taxes_lt(5).ascend_by_users_orders_total.all(:include => :users).should == Company.all
139
+ Company.users_orders_total_gt(10).users_orders_taxes_lt(5).all(:include => :users).should =~ Company.all
140
+ end
141
+
142
+ it "should allow the use of deep :include when a join was created" do
143
+ company = Company.create
144
+ user = company.users.create
145
+ order = user.orders.create(:total => 20, :taxes => 3)
146
+ #TODO: recover after fixing ordering
147
+ # Company.users_orders_total_gt(10).users_orders_taxes_lt(5).ascend_by_users_orders_total.all(:include => {:users => :orders}).should == Company.all
148
+ Company.users_orders_total_gt(10).users_orders_taxes_lt(5).all(:include => {:users => :orders}).should =~ Company.all
149
+ end
150
+
151
+ it "should allow the use of :include when traveling through the duplicate join" do
152
+ company = Company.create
153
+ user = company.users.create(:username => "bjohnson")
154
+ order = user.orders.create(:total => 20, :taxes => 3)
155
+ #TODO: recover after fixing ordering
156
+ # Company.users_username_like("bjohnson").users_orders_taxes_lt(5).ascend_by_users_orders_total.all(:include => :users).should == Company.all
157
+ Company.users_username_like("bjohnson").users_orders_taxes_lt(5).all(:include => :users).should =~ Company.all
158
+ end
159
+
160
+ it "should allow the use of deep :include when traveling through the duplicate join" do
161
+ company = Company.create
162
+ user = company.users.create(:username => "bjohnson")
163
+ order = user.orders.create(:total => 20, :taxes => 3)
164
+ #TODO: recover after fixing ordering
165
+ # Company.users_orders_taxes_lt(50).ascend_by_users_orders_total.all(:include => {:users => :orders}).should == Company.all
166
+ Company.users_orders_taxes_lt(50).all(:include => {:users => :orders}).should =~ Company.all
167
+ end
168
+ # #NOTE: not sure this has relevance to Arel
169
+ # it "should automatically add string joins if the association condition is using strings" do
170
+ # User.scope(:orders_big_id, :joins => "INNER JOIN \"orders\" ON orders.user_id = users.id")
171
+ # Company.users_orders_big_id.should == {:joins=>[" INNER JOIN \"users\" ON users.company_id = companies.id ", " INNER JOIN \"orders\" ON orders.user_id = users.id "]}
172
+ # end
173
+
174
+ it "should order the join statements ascending by the fieldnames so that we don't get double joins where the only difference is that the order of the fields is different" do
175
+ company = Company.create
176
+ user = company.users.create(:company_id => company.id)
177
+ company.users.company_id_eq(company.id).should == [user]
178
+ end
179
+
180
+ it "should sanitize the scope on a foreign model instead of passing the raw options back to the original" do
181
+ Company.scope(:users_count_10, :conditions => {:users_count => 10})
182
+ User.company_users_count_10.should eq_scope(
183
+ User.joins(:company).where("\"companies\".\"users_count\" = 10")
184
+ )
185
+ end
186
+
187
+ #polymorphic
188
+ # it "should delegate to polymorphic relationships" do
189
+ # Audit.auditable_user_type_name_like("ben").should eq_scope(
190
+ # Audit.joins(:auditable, :as=>:user)
191
+ #
192
+ # # }
193
+ # # :conditions => ["users.name LIKE ?", "%ben%"],
194
+ # # :joins => "INNER JOIN \"users\" ON \"users\".id = \"audits\".auditable_id AND \"audits\".auditable_type = 'User'"
195
+ # # }
196
+ # end
197
+
198
+ # it "should delegate to polymorphic relationships (with a lazy split on _type_)" do
199
+ # Audit.auditable_user_type_some_type_id_like("ben").should == {
200
+ # :conditions => ["users.some_type_id LIKE ?", "%ben%"],
201
+ # :joins => "INNER JOIN \"users\" ON \"users\".id = \"audits\".auditable_id AND \"audits\".auditable_type = 'User'"
202
+ # }
203
+ # end
204
+ #
205
+ # it "should deep delegate to polymorphic relationships" do
206
+ # Audit.auditable_user_type_company_name_like("company").should == {
207
+ # :conditions => ["companies.name LIKE ?", "%company%"],
208
+ # :joins => ["INNER JOIN \"users\" ON \"users\".id = \"audits\".auditable_id AND \"audits\".auditable_type = 'User'", " INNER JOIN \"companies\" ON \"companies\".id = \"users\".company_id "]
209
+ # }
210
+ # end
211
+ #
212
+ # it "should allow any on a has_many relationship" do
213
+ # company1 = Company.create
214
+ # user1 = company1.users.create
215
+ # company2 = Company.create
216
+ # user2 = company2.users.create
217
+ # user3 = company2.users.create
218
+ #
219
+ # Company.users_id_equals_any([user2.id, user3.id]).all(:select => "DISTINCT companies.*").should == [company2]
220
+ # end
221
+ end
@@ -0,0 +1,29 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../../spec_helper")
2
+
3
+ describe Searchlogic::NamedScopes::Ordering do
4
+ it "should allow ascending" do
5
+ Company.ascend_by_users_username.should eq_scope(
6
+ Company.joins(:users).order("users.username ASC")
7
+ )
8
+ end
9
+
10
+ # it "should allow descending" do
11
+ # Company.descend_by_users_username.proxy_options.should == User.descend_by_username.proxy_options.merge(:joins => :users)
12
+ # end
13
+ #
14
+ # it "should allow deep ascending" do
15
+ # Company.ascend_by_users_orders_total.proxy_options.should == Order.ascend_by_total.proxy_options.merge(:joins => {:users => :orders})
16
+ # end
17
+ #
18
+ # it "should allow deep descending" do
19
+ # Company.descend_by_users_orders_total.proxy_options.should == Order.descend_by_total.proxy_options.merge(:joins => {:users => :orders})
20
+ # end
21
+ #
22
+ # it "should ascend with a belongs to" do
23
+ # User.ascend_by_company_name.proxy_options.should == Company.ascend_by_name.proxy_options.merge(:joins => :company)
24
+ # end
25
+ #
26
+ # it "should work through #order" do
27
+ # Company.order('ascend_by_users_username').proxy_options.should == Company.ascend_by_users_username.proxy_options
28
+ # end
29
+ end
@@ -0,0 +1,321 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../../spec_helper")
2
+
3
+ describe Searchlogic::NamedScopes::Conditions do
4
+ it "should be dynamically created and then cached" do
5
+ User.should_not respond_to(:age_less_than)
6
+ User.age_less_than(5)
7
+ User.should respond_to(:age_less_than)
8
+ end
9
+
10
+ it "should not allow conditions on non columns" do
11
+ lambda { User.whatever_equals(2) }.should raise_error(NoMethodError)
12
+ end
13
+
14
+ context "comparison conditions" do
15
+ it "should have equals" do
16
+ (5..7).each { |age| User.create(:age => age) }
17
+ User.age_equals(6).all.should == User.find_all_by_age(6)
18
+ User.age_equals(5..6).all.should == User.find_all_by_age(5..6)
19
+ User.age_equals([5, 7]).all.should == User.find_all_by_age([5, 7])
20
+ end
21
+
22
+ it "should have does not equal" do
23
+ (5..7).each { |age| User.create(:age => age) }
24
+ User.age_does_not_equal(6).all.should == User.find_all_by_age([5,7])
25
+ end
26
+
27
+ it "should have less than" do
28
+ (5..7).each { |age| User.create(:age => age) }
29
+ User.age_less_than(6).all.should == User.find_all_by_age(5)
30
+ end
31
+
32
+ it "should have less than or equal to" do
33
+ (5..7).each { |age| User.create(:age => age) }
34
+ User.age_less_than_or_equal_to(6).all.should == User.find_all_by_age([5, 6])
35
+ end
36
+
37
+ it "should have greater than" do
38
+ (5..7).each { |age| User.create(:age => age) }
39
+ User.age_greater_than(6).all.should == User.find_all_by_age(7)
40
+ end
41
+
42
+ it "should have greater than or equal to" do
43
+ (5..7).each { |age| User.create(:age => age) }
44
+ User.age_greater_than_or_equal_to(6).all.should == User.find_all_by_age([6, 7])
45
+ end
46
+ end
47
+
48
+ context "wildcard conditions" do
49
+ it "should have like" do
50
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
51
+ User.username_like("john").all.should == User.find_all_by_username("bjohnson")
52
+ end
53
+
54
+ it "should have not like" do
55
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
56
+ User.username_not_like("john").all.should == User.find_all_by_username("thunt")
57
+ end
58
+
59
+ it "should have begins with" do
60
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
61
+ User.username_begins_with("bj").all.should == User.find_all_by_username("bjohnson")
62
+ end
63
+
64
+ it "should have not begin with" do
65
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
66
+ User.username_not_begin_with("bj").all.should == User.find_all_by_username("thunt")
67
+ end
68
+
69
+ it "should have ends with" do
70
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
71
+ User.username_ends_with("son").all.should == User.find_all_by_username("bjohnson")
72
+ end
73
+
74
+ it "should have not end with" do
75
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
76
+ User.username_not_end_with("son").all.should == User.find_all_by_username("thunt")
77
+ end
78
+ end
79
+
80
+ context "boolean conditions" do
81
+ it "should have scopes for boolean columns" do
82
+ female = User.create(:male => false)
83
+ male = User.create(:male => true)
84
+ User.male.all.should == [male]
85
+ User.not_male.all.should == [female]
86
+ end
87
+
88
+ it "should have null" do
89
+ ["bjohnson", nil].each { |username| User.create(:username => username) }
90
+ User.username_null.all.should == User.find_all_by_username(nil)
91
+ end
92
+
93
+ it "should have not null" do
94
+ ["bjohnson", nil].each { |username| User.create(:username => username) }
95
+ User.username_not_null.all.should == User.find_all_by_username("bjohnson")
96
+ end
97
+
98
+ it "should have empty" do
99
+ ["bjohnson", ""].each { |username| User.create(:username => username) }
100
+ User.username_empty.all.should == User.find_all_by_username("")
101
+ end
102
+
103
+ it "should have blank" do
104
+ ["bjohnson", "", nil].each { |username| User.create(:username => username) }
105
+ User.username_blank.all.should == [User.find_by_username(""), User.find_by_username(nil)]
106
+ end
107
+
108
+ it "should have not blank" do
109
+ ["bjohnson", "", nil].each { |username| User.create(:username => username) }
110
+ User.username_not_blank.all.should == User.find_all_by_username("bjohnson")
111
+ end
112
+ end
113
+
114
+ context "any and all conditions" do
115
+ it "should do nothing if no arguments are passed" do
116
+ # proxy_options no longer supported in ActiveRecord
117
+ #User.username_equals_any.proxy_options.should == {}
118
+ User.username_equals_any.to_sql.squeeze.should == "SELECT \"users\".* FROM \"users\""
119
+ end
120
+
121
+ it "should treat an array and multiple arguments the same" do
122
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
123
+ User.username_like_any("bjohnson", "thunt").should == User.username_like_any(["bjohnson", "thunt"])
124
+ end
125
+
126
+ it "should have equals any" do
127
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
128
+ User.username_equals_any("bjohnson", "thunt").all.should == User.find_all_by_username(["bjohnson", "thunt"])
129
+ end
130
+
131
+ it "should have equals all" do
132
+ %w(bjohnson thunt dainor).each { |username| User.create(:username => username) }
133
+ User.username_equals_all("bjohnson", "thunt").all.should == []
134
+ end
135
+
136
+ it "should have does not equal any" do
137
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
138
+ User.username_does_not_equal_any("bjohnson", "thunt").all.should == User.find_all_by_username(["bjohnson", "thunt", "dgainor"])
139
+ end
140
+
141
+ it "should have does not equal all" do
142
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
143
+ User.username_does_not_equal_all("bjohnson", "thunt").all.should == User.find_all_by_username("dgainor")
144
+ end
145
+
146
+ it "should have less than any" do
147
+ (5..7).each { |age| User.create(:age => age) }
148
+ User.age_less_than_any(7,6).all.should == User.find_all_by_age([5, 6])
149
+ end
150
+
151
+ it "should have less than all" do
152
+ (5..7).each { |age| User.create(:age => age) }
153
+ User.age_less_than_all(7,6).all.should == User.find_all_by_age(5)
154
+ end
155
+
156
+ it "should have less than or equal to any" do
157
+ (5..7).each { |age| User.create(:age => age) }
158
+ User.age_less_than_or_equal_to_any(7,6).all.should == User.find_all_by_age([5, 6, 7])
159
+ end
160
+
161
+ it "should have less than or equal to all" do
162
+ (5..7).each { |age| User.create(:age => age) }
163
+ User.age_less_than_or_equal_to_all(7,6).all.should == User.find_all_by_age([5, 6])
164
+ end
165
+
166
+ it "should have less than any" do
167
+ (5..7).each { |age| User.create(:age => age) }
168
+ User.age_greater_than_any(5,6).all.should == User.find_all_by_age([6, 7])
169
+ end
170
+
171
+ it "should have greater than all" do
172
+ (5..7).each { |age| User.create(:age => age) }
173
+ User.age_greater_than_all(5,6).all.should == User.find_all_by_age(7)
174
+ end
175
+
176
+ it "should have greater than or equal to any" do
177
+ (5..7).each { |age| User.create(:age => age) }
178
+ User.age_greater_than_or_equal_to_any(5,6).all.should == User.find_all_by_age([5, 6, 7])
179
+ end
180
+
181
+ it "should have greater than or equal to all" do
182
+ (5..7).each { |age| User.create(:age => age) }
183
+ User.age_greater_than_or_equal_to_all(5,6).all.should == User.find_all_by_age([6, 7])
184
+ end
185
+
186
+ it "should have like all" do
187
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
188
+ User.username_like_all("bjohnson", "thunt").all.should == []
189
+ User.username_like_all("n", "o").all.should == User.find_all_by_username(["bjohnson", "dgainor"])
190
+ end
191
+
192
+ it "should have like any" do
193
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
194
+ User.username_like_any("bjohnson", "thunt").all.should == User.find_all_by_username(["bjohnson", "thunt"])
195
+ end
196
+
197
+ it "should have begins with all" do
198
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
199
+ User.username_begins_with_all("bjohnson", "thunt").all.should == []
200
+ end
201
+
202
+ it "should have begins with any" do
203
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
204
+ User.username_begins_with_any("bj", "th").all.should == User.find_all_by_username(["bjohnson", "thunt"])
205
+ end
206
+
207
+ it "should have ends with all" do
208
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
209
+ User.username_ends_with_all("n", "r").all.should == []
210
+ end
211
+
212
+ it "should have ends with any" do
213
+ %w(bjohnson thunt dgainor).each { |username| User.create(:username => username) }
214
+ User.username_ends_with_any("n", "r").all.should == User.find_all_by_username(["bjohnson", "dgainor"])
215
+ end
216
+ end
217
+
218
+ context "alias conditions" do
219
+ it "should have is" do
220
+ User.age_is(5).to_sql.squeeze.should == User.age_equals(5).to_sql.squeeze
221
+ end
222
+
223
+ it "should have eq" do
224
+ User.age_eq(5).to_sql.squeeze.should == User.age_equals(5).to_sql.squeeze
225
+ end
226
+
227
+ it "should have not_equal_to" do
228
+ User.age_not_equal_to(5).to_sql.squeeze.should == User.age_does_not_equal(5).to_sql.squeeze
229
+ end
230
+
231
+ it "should have is_not" do
232
+ User.age_is_not(5).to_sql.squeeze.should == User.age_does_not_equal(5).to_sql.squeeze
233
+ end
234
+
235
+ it "should have not" do
236
+ User.age_not(5).to_sql.squeeze.should == User.age_does_not_equal(5).to_sql.squeeze
237
+ end
238
+
239
+ it "should have ne" do
240
+ User.age_ne(5).to_sql.squeeze.should == User.age_does_not_equal(5).to_sql.squeeze
241
+ end
242
+
243
+ it "should have lt" do
244
+ User.age_lt(5).to_sql.squeeze.should == User.age_less_than(5).to_sql.squeeze
245
+ end
246
+
247
+ it "should have lte" do
248
+ User.age_lte(5).to_sql.squeeze.should == User.age_less_than_or_equal_to(5).to_sql.squeeze
249
+ end
250
+
251
+ it "should have gt" do
252
+ User.age_gt(5).to_sql.squeeze.should == User.age_greater_than(5).to_sql.squeeze
253
+ end
254
+
255
+ it "should have gte" do
256
+ User.age_gte(5).to_sql.squeeze.should == User.age_greater_than_or_equal_to(5).to_sql.squeeze
257
+ end
258
+
259
+ it "should have contains" do
260
+ User.username_contains(5).to_sql.squeeze.should == User.username_like(5).to_sql.squeeze
261
+ end
262
+
263
+ it "should have contains" do
264
+ User.username_includes(5).to_sql.squeeze.should == User.username_like(5).to_sql.squeeze
265
+ end
266
+
267
+ it "should have bw" do
268
+ User.username_bw(5).to_sql.squeeze.should == User.username_begins_with(5).to_sql.squeeze
269
+ end
270
+
271
+ it "should have ew" do
272
+ User.username_ew(5).to_sql.squeeze.should == User.username_ends_with(5).to_sql.squeeze
273
+ end
274
+
275
+ it "should have nil" do
276
+ User.username_nil.to_sql.squeeze.should == User.username_nil.to_sql.squeeze
277
+ end
278
+ end
279
+
280
+ context "group conditions" do
281
+ it "should have in" do
282
+ (5..7).each { |age| User.create(:age => age) }
283
+ User.age_in([5,6]).all.should == User.find(:all, :conditions => ["users.age IN (?)", [5, 6]])
284
+ end
285
+
286
+ it "should have not_in" do
287
+ (5..7).each { |age| User.create(:age => age) }
288
+ User.age_not_in([5,6]).all.should == User.find(:all, :conditions => ["users.age NOT IN (?)", [5, 6]])
289
+ end
290
+ end
291
+
292
+ # context "searchlogic lambda" do
293
+ # it "should be a string" do
294
+ # User.username_like("test")
295
+ # User.named_scope_options(:username_like).searchlogic_options[:type].should == :string
296
+ # end
297
+ #
298
+ # it "should be an integer" do
299
+ # User.id_gt(10)
300
+ # User.named_scope_options(:id_gt).searchlogic_options[:type].should == :integer
301
+ # end
302
+ #
303
+ # it "should be a float" do
304
+ # Order.total_gt(10)
305
+ # Order.named_scope_options(:total_gt).searchlogic_options[:type].should == :float
306
+ # end
307
+ # end
308
+
309
+ it "should have priorty to columns over conflicting association conditions" do
310
+ Company.users_count_gt(10)
311
+ User.create
312
+ User.company_id_null.count.should == 1
313
+ User.company_id_not_null.count.should == 0
314
+ end
315
+
316
+ it "should fix bug for issue 26" do
317
+ count1 = User.id_ne(10).username_not_like("root").count
318
+ count2 = User.id_ne(10).username_not_like("root").count
319
+ count1.should == count2
320
+ end
321
+ end
@@ -0,0 +1,66 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../../spec_helper")
2
+
3
+ describe Searchlogic::NamedScopes::OrConditions do
4
+ it "should define a scope by the exact same name as requested by the code" do
5
+ User.name_or_username_like('Test')
6
+ User.respond_to?(:name_or_username_like).should be_true
7
+ end
8
+
9
+ it "should match username or name" do
10
+ User.username_or_name_like("ben").proxy_options.should == {:conditions => "(users.username LIKE '%ben%') OR (users.name LIKE '%ben%')"}
11
+ end
12
+
13
+ it "should use the specified condition" do
14
+ User.username_begins_with_or_name_like("ben").proxy_options.should == {:conditions => "(users.username LIKE 'ben%') OR (users.name LIKE '%ben%')"}
15
+ end
16
+
17
+ it "should use the last specified condition" do
18
+ User.username_or_name_like_or_id_or_age_lt(10).proxy_options.should == {:conditions => "(users.username LIKE '%10%') OR (users.name LIKE '%10%') OR (users.id < 10) OR (users.age < 10)"}
19
+ end
20
+
21
+ it "should raise an error on unknown conditions" do
22
+ lambda { User.usernme_begins_with_or_name_like("ben") }.should raise_error(Searchlogic::NamedScopes::OrConditions::UnknownConditionError)
23
+ end
24
+
25
+ it "should work well with _or_equal_to" do
26
+ User.id_less_than_or_equal_to_or_age_gt(10).proxy_options.should == {:conditions => "(users.id <= 10) OR (users.age > 10)"}
27
+ end
28
+
29
+ it "should work well with _or_equal_to_any" do
30
+ User.id_less_than_or_equal_to_all_or_age_gt(10).proxy_options.should == {:conditions => "(users.id <= 10) OR (users.age > 10)"}
31
+ end
32
+
33
+ it "should work well with _or_equal_to_all" do
34
+ User.id_less_than_or_equal_to_any_or_age_gt(10).proxy_options.should == {:conditions => "(users.id <= 10) OR (users.age > 10)"}
35
+ end
36
+
37
+ it "should play nice with other scopes" do
38
+ User.username_begins_with("ben").id_gt(10).age_not_nil.username_or_name_ends_with("ben").scope(:find).should ==
39
+ {:conditions => "((users.username LIKE '%ben') OR (users.name LIKE '%ben')) AND ((users.age IS NOT NULL) AND ((users.id > 10) AND (users.username LIKE 'ben%')))"}
40
+ end
41
+
42
+ it "should play nice with scopes on associations" do
43
+ lambda { User.name_or_company_name_like("ben") }.should_not raise_error(Searchlogic::NamedScopes::OrConditions::NoConditionSpecifiedError)
44
+ User.name_or_company_name_like("ben").proxy_options.should == {:joins => :company, :conditions => "(users.name LIKE '%ben%') OR (companies.name LIKE '%ben%')"}
45
+ User.company_name_or_name_like("ben").proxy_options.should == {:joins => :company, :conditions => "(companies.name LIKE '%ben%') OR (users.name LIKE '%ben%')"}
46
+ User.company_name_or_company_description_like("ben").proxy_options.should == {:joins =>[:company], :conditions => "(companies.name LIKE '%ben%') OR (companies.description LIKE '%ben%')"}
47
+ end
48
+
49
+ it "should not get confused by the 'or' in find_or_create_by_* methods" do
50
+ User.create(:name => "Fred")
51
+ User.find_or_create_by_name("Fred").should be_a_kind_of User
52
+ end
53
+
54
+ it "should not get confused by the 'or' in compound find_or_create_by_* methods" do
55
+ User.create(:name => "Fred", :username => "fredb")
56
+ User.find_or_create_by_name_and_username("Fred", "fredb").should be_a_kind_of User
57
+ end
58
+
59
+ it "should work with User.search(conditions) method" do
60
+ User.search(:username_or_name_like => 'ben').proxy_options.should == {:conditions => "(users.username LIKE '%ben%') OR (users.name LIKE '%ben%')"}
61
+ end
62
+
63
+ it "should convert types properly when used with User.search(conditions) method" do
64
+ User.search(:id_or_age_lte => '10').proxy_options.should == {:conditions => "(users.id <= 10) OR (users.age <= 10)"}
65
+ end
66
+ end
@@ -0,0 +1,34 @@
1
+ require File.expand_path(File.dirname(__FILE__) + "/../../spec_helper")
2
+
3
+ describe Searchlogic::NamedScopes::Ordering do
4
+ it "should be dynamically created and then cached" do
5
+ User.should_not respond_to(:ascend_by_username)
6
+ User.ascend_by_username
7
+ User.should respond_to(:ascend_by_username)
8
+ end
9
+
10
+ it "should have ascending" do
11
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
12
+ User.ascend_by_username.all.should == User.all(:order => "username ASC")
13
+ end
14
+
15
+ it "should have descending" do
16
+ %w(bjohnson thunt).each { |username| User.create(:username => username) }
17
+ User.descend_by_username.all.should == User.all(:order => "username DESC")
18
+ end
19
+
20
+ it "should have order" do
21
+ User.order("ascend_by_username").to_sql.squeeze.should == User.ascend_by_username.to_sql.squeeze
22
+ end
23
+
24
+ it "should have order by custom scope" do
25
+ User.column_names.should_not include("custom")
26
+ %w(bjohnson thunt fisons).each { |username| User.create(:username => username) }
27
+ User.scope(:ascend_by_custom, :order => "username ASC, name DESC")
28
+ User.order("ascend_by_custom").to_sql.squeeze.should == User.ascend_by_custom.to_sql.squeeze
29
+ end
30
+
31
+ it "should have priorty to columns over conflicting association columns" do
32
+ Company.ascend_by_users_count
33
+ end
34
+ end