searchgasm 1.3.4 → 1.3.5

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.
data/CHANGELOG.rdoc CHANGED
@@ -1,4 +1,8 @@
1
- == 1.3.4 released 2008-10-03
1
+ == 1.3.5 released 2008-10-08
2
+
3
+ * Since joins are now strings, AR doesn't know how to merge them properly. So searchgasm now checks which joins to skip over to avoid conflicts.
4
+
5
+ == 1.3.4 released 2008-10-07
2
6
 
3
7
  * Fixed method names creation for conditions with modifiers
4
8
  * Create local column conditions, incase there are method conflicts. Such as "id".
@@ -108,6 +108,7 @@ module Searchgasm
108
108
  return options unless Searchgasm::Search::Base.needed?(self, options)
109
109
  search = Searchgasm::Search::Base.create_virtual_class(self).new # call explicitly to avoid merging the scopes into the search
110
110
  search.acting_as_filter = true
111
+ search.scope = scope(:find)
111
112
  conditions = options.delete(:conditions) || options.delete("conditions") || {}
112
113
  if conditions
113
114
  case conditions
@@ -120,7 +121,7 @@ module Searchgasm
120
121
  search.options = options
121
122
  search.sanitize(searching)
122
123
  end
123
-
124
+
124
125
  def searchgasm_search(options = {})
125
126
  scope = {}
126
127
  current_scope = scope(:find) && scope(:find).deep_dup
@@ -78,10 +78,10 @@ module Searchgasm
78
78
  # * <tt>:html</tt> -- html arrtributes for the <a> tag.
79
79
  #
80
80
  # === Advanced Options
81
- # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base leve in params such as params[:page], params[:per_page], etc, then set this to nil.
81
+ # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base level in params such as params[:page], params[:per_page], etc, then set this to nil.
82
82
  # * <tt>:search_obj</tt> -- default: @#{params_scope}, this is your search object, everything revolves around this. It will try to infer the name from your params_scope. If your params_scope is :search it will try to get @search, etc. If it can not be inferred by this, you need to pass the object itself.
83
83
  # * <tt>:params</tt> -- default: nil, Additional params to add to the url, must be a hash
84
- # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get include. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
84
+ # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get included. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
85
85
  # * <tt>:search_params</tt> -- default: nil, Additional search params to add to the url, must be a hash. Adds the options into the :params_scope.
86
86
  # * <tt>:exclude_search_params</tt> -- default: nil, Same as :exclude_params but for the :search_params.
87
87
  def order_by_link(order_by, options = {})
@@ -97,7 +97,7 @@ module Searchgasm
97
97
  html
98
98
  end
99
99
 
100
- # Creates a link for ascending or descending data, pretty self e
100
+ # Creates a link for ascending or descending data.
101
101
  #
102
102
  # === Example uses
103
103
  #
@@ -110,10 +110,10 @@ module Searchgasm
110
110
  # * <tt>:html</tt> -- html arrtributes for the <a> tag.
111
111
  #
112
112
  # === Advanced Options
113
- # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base leve in params such as params[:page], params[:per_page], etc, then set this to nil.
113
+ # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base level in params such as params[:page], params[:per_page], etc, then set this to nil.
114
114
  # * <tt>:search_obj</tt> -- default: @#{params_scope}, this is your search object, everything revolves around this. It will try to infer the name from your params_scope. If your params_scope is :search it will try to get @search, etc. If it can not be inferred by this, you need to pass the object itself.
115
115
  # * <tt>:params</tt> -- default: nil, Additional params to add to the url, must be a hash
116
- # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get include. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
116
+ # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get included. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
117
117
  # * <tt>:search_params</tt> -- default: nil, Additional search params to add to the url, must be a hash. Adds the options into the :params_scope.
118
118
  # * <tt>:exclude_search_params</tt> -- default: nil, Same as :exclude_params but for the :search_params.
119
119
  def order_as_link(order_as, options = {})
@@ -151,10 +151,10 @@ module Searchgasm
151
151
  # * <tt>:html</tt> -- html arrtributes for the <a> tag.
152
152
  #
153
153
  # === Advanced Options
154
- # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base leve in params such as params[:page], params[:per_page], etc, then set this to nil.
154
+ # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base level in params such as params[:page], params[:per_page], etc, then set this to nil.
155
155
  # * <tt>:search_obj</tt> -- default: @#{params_scope}, this is your search object, everything revolves around this. It will try to infer the name from your params_scope. If your params_scope is :search it will try to get @search, etc. If it can not be inferred by this, you need to pass the object itself.
156
156
  # * <tt>:params</tt> -- default: nil, Additional params to add to the url, must be a hash
157
- # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get include. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
157
+ # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get included. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
158
158
  # * <tt>:search_params</tt> -- default: nil, Additional search params to add to the url, must be a hash. Adds the options into the :params_scope.
159
159
  # * <tt>:exclude_search_params</tt> -- default: nil, Same as :exclude_params but for the :search_params.
160
160
  def priority_order_by_link(priority_order_by, priority_order_as, options = {})
@@ -185,10 +185,10 @@ module Searchgasm
185
185
  # * <tt>:html</tt> -- html arrtributes for the <a> tag.
186
186
  #
187
187
  # === Advanced Options
188
- # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base leve in params such as params[:page], params[:per_page], etc, then set this to nil.
188
+ # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base level in params such as params[:page], params[:per_page], etc, then set this to nil.
189
189
  # * <tt>:search_obj</tt> -- default: @#{params_scope}, this is your search object, everything revolves around this. It will try to infer the name from your params_scope. If your params_scope is :search it will try to get @search, etc. If it can not be inferred by this, you need to pass the object itself.
190
190
  # * <tt>:params</tt> -- default: nil, Additional params to add to the url, must be a hash
191
- # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get include. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
191
+ # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get included. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
192
192
  # * <tt>:search_params</tt> -- default: nil, Additional search params to add to the url, must be a hash. Adds the options into the :params_scope.
193
193
  # * <tt>:exclude_search_params</tt> -- default: nil, Same as :exclude_params but for the :search_params.
194
194
  def per_page_link(per_page, options = {})
@@ -217,10 +217,10 @@ module Searchgasm
217
217
  # * <tt>:html</tt> -- html arrtributes for the <a> tag.
218
218
  #
219
219
  # === Advanced Options
220
- # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base leve in params such as params[:page], params[:per_page], etc, then set this to nil.
220
+ # * <tt>:params_scope</tt> -- default: :search, this is the scope in which your search params will be preserved (params[:search]). If you don't want a scope and want your options to be at base level in params such as params[:page], params[:per_page], etc, then set this to nil.
221
221
  # * <tt>:search_obj</tt> -- default: @#{params_scope}, this is your search object, everything revolves around this. It will try to infer the name from your params_scope. If your params_scope is :search it will try to get @search, etc. If it can not be inferred by this, you need to pass the object itself.
222
222
  # * <tt>:params</tt> -- default: nil, Additional params to add to the url, must be a hash
223
- # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get include. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
223
+ # * <tt>:exclude_params</tt> -- default: nil, params you want to exclude. This is nifty because it does a "deep delete". So you can pass {:param1 => {:param2 => :param3}} and it will make sure param3 does not get included. param1 and param2 will not be touched. This also accepts an array or just a symbol or string.
224
224
  # * <tt>:search_params</tt> -- default: nil, Additional search params to add to the url, must be a hash. Adds the options into the :params_scope.
225
225
  # * <tt>:exclude_search_params</tt> -- default: nil, Same as :exclude_params but for the :search_params.
226
226
  def page_link(page, options = {})
@@ -43,7 +43,7 @@ module Searchgasm #:nodoc:
43
43
  end
44
44
 
45
45
  # Flag to determine if searchgasm is acting as a filter for the ActiveRecord search methods.
46
- # The purpose of this is to determine if Config.per_page should be implemented.
46
+ # By filter it means that searchgasm is being used on the default ActiveRecord search methods, like all, count, find(:all), first, etc.
47
47
  def acting_as_filter=(value)
48
48
  @acting_as_filter = value
49
49
  end
@@ -79,7 +79,8 @@ module Searchgasm #:nodoc:
79
79
  "#<#{klass}Search #{current_find_options.inspect}>"
80
80
  end
81
81
 
82
- # Searchgasm requires that all joins be left outer joins for conditions and ordering to work properly
82
+ # The method is unique in the fact that if searchgasm is acting_as_filter? then auto joins are not included. Searchgasm should not change the default ActiveRecord behavior.
83
+ # If you are running a search via new_search or build_search then auto joins are included.
83
84
  def joins
84
85
  joins_sql = ""
85
86
  all_joins = auto_joins
@@ -92,14 +93,33 @@ module Searchgasm #:nodoc:
92
93
  end
93
94
 
94
95
  return if joins_sql.blank? && all_joins.blank?
96
+ return joins_sql if all_joins.blank?
95
97
 
96
- unless all_joins.blank?
97
- join_dependency = ::ActiveRecord::Associations::ClassMethods::JoinDependency.new(klass, all_joins, nil)
98
- joins_sql += " " unless joins_sql.blank?
99
- joins_sql += join_dependency.join_associations.collect { |assoc| assoc.association_join }.join
98
+ # convert scopes joins to sql, so we can determine which joins to skip
99
+ scope_joins_sql = nil
100
+ if scope && !scope[:joins].blank?
101
+ case scope[:joins]
102
+ when String
103
+ scope_joins_sql = scope[:joins]
104
+ else
105
+ join_dependency = ::ActiveRecord::Associations::ClassMethods::JoinDependency.new(klass, scope[:joins], nil)
106
+ scope_joins_sql = join_dependency.join_associations.collect { |assoc| assoc.association_join }.join
107
+ end
108
+ end
109
+
110
+ join_dependency = ::ActiveRecord::Associations::ClassMethods::JoinDependency.new(klass, all_joins, nil)
111
+ safe_joins = []
112
+ join_dependency.join_associations.each do |assoc|
113
+ join_sql = assoc.association_join
114
+
115
+ #debugger if scope && scope[:joins].include?("LEFT OUTER JOIN \"users\"")
116
+ safe_joins << join_sql if scope_joins_sql.blank? || !scope_joins_sql.include?(join_sql.gsub(/(LEFT OUTER JOIN|INNER JOIN)/i, "").strip)
100
117
  end
101
118
 
102
- joins_sql
119
+
120
+
121
+ joins_sql += " " unless joins_sql.blank?
122
+ joins_sql += safe_joins.join
103
123
  end
104
124
 
105
125
  def limit=(value)
@@ -123,7 +143,7 @@ module Searchgasm #:nodoc:
123
143
  end
124
144
 
125
145
  # Sanitizes everything down into options ActiveRecord::Base.find can understand
126
- def sanitize(searching = true)
146
+ def sanitize(searching = true)
127
147
  find_options = {}
128
148
 
129
149
  (searching ? AR_FIND_OPTIONS : AR_CALCULATIONS_OPTIONS).each do |find_option|
@@ -20,7 +20,7 @@ module Searchgasm
20
20
  def #{method}(*args)
21
21
  find_options = {}
22
22
  options = args.extract_options! # can't pass options, your options are in the search
23
- klass.send(:with_scope, :find => scope) do
23
+ klass.send(:with_scope, :find => acting_as_filter? ? {} : scope) do
24
24
  options = sanitize(#{SEARCH_METHODS.include?(method)})
25
25
  if #{CALCULATION_METHODS.include?(method)}
26
26
  options[:distinct] = true
@@ -67,7 +67,7 @@ module Searchgasm
67
67
 
68
68
  MAJOR = 1
69
69
  MINOR = 3
70
- TINY = 4
70
+ TINY = 5
71
71
 
72
72
  # The current version as a Version instance
73
73
  CURRENT = new(MAJOR, MINOR, TINY)
data/searchgasm.gemspec CHANGED
@@ -1,18 +1,18 @@
1
1
 
2
- # Gem::Specification for Searchgasm-1.3.4
2
+ # Gem::Specification for Searchgasm-1.3.5
3
3
  # Originally generated by Echoe
4
4
 
5
5
  --- !ruby/object:Gem::Specification
6
6
  name: searchgasm
7
7
  version: !ruby/object:Gem::Version
8
- version: 1.3.4
8
+ version: 1.3.5
9
9
  platform: ruby
10
10
  authors:
11
11
  - Ben Johnson of Binary Logic
12
12
  autorequire:
13
13
  bindir: bin
14
14
 
15
- date: 2008-10-07 00:00:00 -04:00
15
+ date: 2008-10-08 00:00:00 -04:00
16
16
  default_executable:
17
17
  dependencies:
18
18
  - !ruby/object:Gem::Dependency
@@ -51,6 +51,8 @@ class TestActiveRecordBase < Test::Unit::TestCase
51
51
 
52
52
  assert_equal Account.find(1, 3), Account.all(:conditions => {:name_contains => "Binary"}, :page => 2)
53
53
  assert_equal [], Account.all(:conditions => {:name_contains => "Binary"}, :page => 2, :per_page => 20)
54
+
55
+ assert_equal [Account.find(1)], Account.scope1.all(:conditions => {:users => {:first_name_starts_with => "Ben"}})
54
56
  end
55
57
 
56
58
  def test_searchgasm_counting
@@ -10,7 +10,7 @@ class TestConditionsBase < Test::Unit::TestCase
10
10
  end
11
11
 
12
12
  def test_association_names
13
- assert_equal ["account", "parent", "orders", "user_groups", "children"], Searchgasm::Cache::UserConditions.association_names
13
+ assert_equal ["children", "orders", "account", "parent", "user_groups"], Searchgasm::Cache::UserConditions.association_names
14
14
  assert_equal ["admin", "orders", "users"], Searchgasm::Cache::AccountConditions.association_names
15
15
  end
16
16
 
data/test/test_helper.rb CHANGED
@@ -13,6 +13,8 @@ class Account < ActiveRecord::Base
13
13
  has_one :admin, :class_name => "User", :conditions => {:first_name => "Ben"}
14
14
  has_many :users, :dependent => :destroy
15
15
  has_many :orders, :through => :users
16
+
17
+ named_scope :scope1, :conditions => {:users => {:first_name_contains => "Ben"}}
16
18
  end
17
19
 
18
20
  class UserGroup < ActiveRecord::Base
@@ -185,6 +185,8 @@ class TestSearchBase < Test::Unit::TestCase
185
185
  search = Account.new_search
186
186
  search.select = "id, name"
187
187
  assert_equal Account.all, search.all
188
+
189
+ assert_equal [Account.find(1)], Account.scope1.new_search(:conditions => {:users => {:first_name_starts_with => "Ben"}}).all
188
190
  end
189
191
 
190
192
  def test_calculations
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: searchgasm
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.4
4
+ version: 1.3.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ben Johnson of Binary Logic
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2008-10-07 00:00:00 -04:00
12
+ date: 2008-10-08 00:00:00 -04:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency