scoped_search 2.3.7 → 2.4.0
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/.travis.yml +28 -0
- data/Gemfile +11 -10
- data/Gemfile.activerecord2 +16 -0
- data/Gemfile.activerecord3 +16 -0
- data/README.rdoc +5 -3
- data/lib/scoped_search.rb +1 -1
- data/lib/scoped_search/auto_complete_builder.rb +6 -3
- data/lib/scoped_search/definition.rb +61 -52
- data/lib/scoped_search/query_builder.rb +30 -10
- data/scoped_search.gemspec +5 -7
- data/spec/database.jruby.yml +15 -0
- data/spec/database.ruby.yml +15 -0
- data/spec/integration/api_spec.rb +1 -1
- data/spec/integration/auto_complete_spec.rb +34 -17
- data/spec/integration/key_value_querying_spec.rb +25 -24
- data/spec/integration/ordinal_querying_spec.rb +1 -1
- data/spec/integration/profile_querying_spec.rb +1 -1
- data/spec/integration/relation_querying_spec.rb +1 -1
- data/spec/integration/set_query_spec.rb +1 -1
- data/spec/integration/string_querying_spec.rb +10 -3
- data/spec/lib/database.rb +16 -6
- data/spec/lib/mocks.rb +1 -0
- data/spec/unit/ast_spec.rb +1 -1
- data/spec/unit/auto_complete_builder_spec.rb +1 -1
- data/spec/unit/definition_spec.rb +16 -1
- data/spec/unit/parser_spec.rb +1 -1
- data/spec/unit/query_builder_spec.rb +1 -1
- data/spec/unit/tokenizer_spec.rb +1 -1
- data/tasks/github-gem.rake +5 -3
- metadata +65 -92
data/.travis.yml
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
language: ruby
|
2
|
+
script: bundle exec rake
|
3
|
+
before_script:
|
4
|
+
- psql -c 'create database scoped_search_test;' -U postgres
|
5
|
+
- mysql -e 'create database scoped_search_test;'
|
6
|
+
rvm:
|
7
|
+
- 1.8.7
|
8
|
+
- 1.9.2
|
9
|
+
- 1.9.3
|
10
|
+
- ruby-head
|
11
|
+
- ree
|
12
|
+
- jruby-18mode
|
13
|
+
- jruby-19mode
|
14
|
+
- jruby-head
|
15
|
+
gemfile:
|
16
|
+
- Gemfile.activerecord2
|
17
|
+
- Gemfile.activerecord3
|
18
|
+
matrix:
|
19
|
+
allow_failures:
|
20
|
+
- rvm: ruby-head
|
21
|
+
- rvm: jruby-head
|
22
|
+
exclude:
|
23
|
+
- rvm: jruby-18mode
|
24
|
+
gemfile: Gemfile.activerecord2
|
25
|
+
- rvm: jruby-19mode
|
26
|
+
gemfile: Gemfile.activerecord2
|
27
|
+
- rvm: jruby-head
|
28
|
+
gemfile: Gemfile.activerecord2
|
data/Gemfile
CHANGED
@@ -1,15 +1,16 @@
|
|
1
1
|
source :rubygems
|
2
2
|
gemspec
|
3
3
|
|
4
|
-
|
5
|
-
# Uncomment the following gems to test scoped search on other RDBMSs.
|
6
|
-
# You can specify the databasde connection details in spec/database.yml
|
4
|
+
gem 'activerecord'
|
7
5
|
|
8
|
-
|
9
|
-
|
10
|
-
|
6
|
+
platforms :jruby do
|
7
|
+
gem 'activerecord-jdbcsqlite3-adapter'
|
8
|
+
gem 'activerecord-jdbcmysql-adapter'
|
9
|
+
gem 'activerecord-jdbcpostgresql-adapter'
|
10
|
+
end
|
11
11
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
12
|
+
platforms :ruby do
|
13
|
+
gem 'sqlite3'
|
14
|
+
gem 'mysql2'
|
15
|
+
gem 'pg'
|
16
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
source :rubygems
|
2
|
+
gemspec
|
3
|
+
|
4
|
+
gem 'activerecord', '~> 2'
|
5
|
+
|
6
|
+
platforms :jruby do
|
7
|
+
gem 'activerecord-jdbcsqlite3-adapter'
|
8
|
+
gem 'activerecord-jdbcmysql-adapter'
|
9
|
+
gem 'activerecord-jdbcpostgresql-adapter'
|
10
|
+
end
|
11
|
+
|
12
|
+
platforms :ruby do
|
13
|
+
gem 'sqlite3'
|
14
|
+
gem 'mysql2', '~> 0.2.6'
|
15
|
+
gem 'pg'
|
16
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
source :rubygems
|
2
|
+
gemspec
|
3
|
+
|
4
|
+
gem 'activerecord', '~> 3'
|
5
|
+
|
6
|
+
platforms :jruby do
|
7
|
+
gem 'activerecord-jdbcsqlite3-adapter'
|
8
|
+
gem 'activerecord-jdbcmysql-adapter'
|
9
|
+
gem 'activerecord-jdbcpostgresql-adapter'
|
10
|
+
end
|
11
|
+
|
12
|
+
platforms :ruby do
|
13
|
+
gem 'sqlite3'
|
14
|
+
gem 'mysql2', '~> 0.3.11'
|
15
|
+
gem 'pg'
|
16
|
+
end
|
data/README.rdoc
CHANGED
@@ -124,6 +124,8 @@ For more info, see the the project wiki: http://github.com/wvanbergen/scoped_sea
|
|
124
124
|
|
125
125
|
== License
|
126
126
|
|
127
|
-
This plugin is released under the MIT license
|
128
|
-
|
129
|
-
|
127
|
+
This plugin is released under the MIT license (see LICENSE).
|
128
|
+
|
129
|
+
This plugin was originally developed for Floorplanner.com by Willem van Bergen
|
130
|
+
(https://github.com/wvanbergen) with help from Wes Hays (https://github.com/weshays).
|
131
|
+
The current maintainer is Amos Benari (https://github.com/abenari).
|
data/lib/scoped_search.rb
CHANGED
@@ -14,7 +14,7 @@ module ScopedSearch
|
|
14
14
|
|
15
15
|
# The current scoped_search version. Do not change thisvalue by hand,
|
16
16
|
# because it will be updated automatically by the gem release script.
|
17
|
-
VERSION = "2.
|
17
|
+
VERSION = "2.4.0"
|
18
18
|
|
19
19
|
# The ClassMethods module will be included into the ActiveRecord::Base class
|
20
20
|
# to add the <tt>ActiveRecord::Base.scoped_search</tt> method and the
|
@@ -168,9 +168,12 @@ module ScopedSearch
|
|
168
168
|
return ["#{name}."] if !val || !val.is_a?(String) || !(val.include?('.'))
|
169
169
|
val = val.sub(/.*\./,'')
|
170
170
|
|
171
|
-
|
172
|
-
|
173
|
-
|
171
|
+
connection = definition.klass.connection
|
172
|
+
quoted_table = field.key_klass.connection.quote_table_name(field.key_klass.table_name)
|
173
|
+
quoted_field = field.key_klass.connection.quote_column_name(field.key_field)
|
174
|
+
field_name = "#{quoted_table}.#{quoted_field}"
|
175
|
+
select_clause = "DISTINCT #{field_name}"
|
176
|
+
opts = value_conditions(field_name, val).merge(:select => select_clause, :limit => 20)
|
174
177
|
|
175
178
|
field.key_klass.all(opts).map(&field.key_field).compact.map{ |f| "#{name}.#{f} "}
|
176
179
|
end
|
@@ -15,12 +15,49 @@ module ScopedSearch
|
|
15
15
|
# class, so you should not create instances of this class yourself.
|
16
16
|
class Field
|
17
17
|
|
18
|
-
attr_reader :definition, :field, :only_explicit, :relation, :key_relation,
|
18
|
+
attr_reader :definition, :field, :only_explicit, :relation, :key_relation, :full_text_search,
|
19
19
|
:key_field, :complete_value, :offset, :word_size, :ext_method, :operators
|
20
20
|
|
21
|
+
# Initializes a Field instance given the definition passed to the
|
22
|
+
# scoped_search call on the ActiveRecord-based model class.
|
23
|
+
def initialize(definition, options = {})
|
24
|
+
@definition = definition
|
25
|
+
@definition.profile = options[:profile] if options[:profile]
|
26
|
+
@definition.default_order ||= default_order(options)
|
27
|
+
|
28
|
+
case options
|
29
|
+
when Symbol, String
|
30
|
+
@field = field.to_sym
|
31
|
+
when Hash
|
32
|
+
@field = options.delete(:on)
|
33
|
+
|
34
|
+
# Set attributes from options hash
|
35
|
+
@complete_value = options[:complete_value]
|
36
|
+
@relation = options[:in]
|
37
|
+
@key_relation = options[:in_key]
|
38
|
+
@key_field = options[:on_key]
|
39
|
+
@offset = options[:offset]
|
40
|
+
@word_size = options[:word_size] || 1
|
41
|
+
@ext_method = options[:ext_method]
|
42
|
+
@operators = options[:operators]
|
43
|
+
@only_explicit = !!options[:only_explicit]
|
44
|
+
@full_text_search = options[:full_text_search]
|
45
|
+
@default_operator = options[:default_operator] if options.has_key?(:default_operator)
|
46
|
+
end
|
47
|
+
|
48
|
+
# Store this field is the field array
|
49
|
+
definition.fields[@field] ||= self unless options[:rename]
|
50
|
+
definition.fields[options[:rename].to_sym] ||= self if options[:rename]
|
51
|
+
definition.unique_fields << self
|
52
|
+
|
53
|
+
# Store definition for alias / aliases as well
|
54
|
+
definition.fields[options[:alias].to_sym] ||= self if options[:alias]
|
55
|
+
options[:aliases].each { |al| definition.fields[al.to_sym] ||= self } if options[:aliases]
|
56
|
+
end
|
57
|
+
|
21
58
|
# The ActiveRecord-based class that belongs to this field.
|
22
59
|
def klass
|
23
|
-
if relation
|
60
|
+
@klass ||= if relation
|
24
61
|
related = definition.klass.reflections[relation]
|
25
62
|
raise ScopedSearch::QueryNotSupported, "relation '#{relation}' not one of #{definition.klass.reflections.keys.join(', ')} " if related.nil?
|
26
63
|
related.klass
|
@@ -28,9 +65,10 @@ module ScopedSearch
|
|
28
65
|
definition.klass
|
29
66
|
end
|
30
67
|
end
|
68
|
+
|
31
69
|
# The ActiveRecord-based class that belongs the key field in a key-value pair.
|
32
70
|
def key_klass
|
33
|
-
|
71
|
+
@key_klass ||= if key_relation
|
34
72
|
definition.klass.reflections[key_relation].klass
|
35
73
|
elsif relation
|
36
74
|
definition.klass.reflections[relation].klass
|
@@ -41,12 +79,18 @@ module ScopedSearch
|
|
41
79
|
|
42
80
|
# Returns the ActiveRecord column definition that corresponds to this field.
|
43
81
|
def column
|
44
|
-
|
82
|
+
@column ||= begin
|
83
|
+
if klass.columns_hash.has_key?(field.to_s)
|
84
|
+
klass.columns_hash[field.to_s]
|
85
|
+
else
|
86
|
+
raise ActiveRecord::UnknownAttributeError, "#{klass.inspect} doesn't have column #{field.inspect}."
|
87
|
+
end
|
88
|
+
end
|
45
89
|
end
|
46
90
|
|
47
91
|
# Returns the column type of this field.
|
48
92
|
def type
|
49
|
-
column.type
|
93
|
+
@type ||= column.type
|
50
94
|
end
|
51
95
|
|
52
96
|
# Returns true if this field is a datetime-like column
|
@@ -95,41 +139,6 @@ module ScopedSearch
|
|
95
139
|
order = (options[:default_order].to_s.downcase.include?('desc')) ? "DESC" : "ASC"
|
96
140
|
return "#{field_name} #{order}"
|
97
141
|
end
|
98
|
-
# Initializes a Field instance given the definition passed to the
|
99
|
-
# scoped_search call on the ActiveRecord-based model class.
|
100
|
-
def initialize(definition, options = {})
|
101
|
-
@definition = definition
|
102
|
-
@definition.profile = options[:profile] if options[:profile]
|
103
|
-
@definition.default_order ||= default_order(options)
|
104
|
-
|
105
|
-
case options
|
106
|
-
when Symbol, String
|
107
|
-
@field = field.to_sym
|
108
|
-
when Hash
|
109
|
-
@field = options.delete(:on)
|
110
|
-
|
111
|
-
# Set attributes from options hash
|
112
|
-
@complete_value = options[:complete_value]
|
113
|
-
@relation = options[:in]
|
114
|
-
@key_relation = options[:in_key]
|
115
|
-
@key_field = options[:on_key]
|
116
|
-
@offset = options[:offset]
|
117
|
-
@word_size = options[:word_size] || 1
|
118
|
-
@ext_method = options[:ext_method]
|
119
|
-
@operators = options[:operators]
|
120
|
-
@only_explicit = !!options[:only_explicit]
|
121
|
-
@default_operator = options[:default_operator] if options.has_key?(:default_operator)
|
122
|
-
end
|
123
|
-
|
124
|
-
# Store this field is the field array
|
125
|
-
definition.fields[@field] ||= self unless options[:rename]
|
126
|
-
definition.fields[options[:rename].to_sym] ||= self if options[:rename]
|
127
|
-
definition.unique_fields << self
|
128
|
-
|
129
|
-
# Store definition for alias / aliases as well
|
130
|
-
definition.fields[options[:alias].to_sym] ||= self if options[:alias]
|
131
|
-
options[:aliases].each { |al| definition.fields[al.to_sym] ||= self } if options[:aliases]
|
132
|
-
end
|
133
142
|
end
|
134
143
|
|
135
144
|
attr_reader :klass
|
@@ -185,13 +194,15 @@ module ScopedSearch
|
|
185
194
|
end
|
186
195
|
|
187
196
|
NUMERICAL_REGXP = /^\-?\d+(\.\d+)?$/
|
197
|
+
INTEGER_REGXP = /^\-?\d+$/
|
188
198
|
|
189
199
|
# Returns a list of appropriate fields to search in given a search keyword and operator.
|
190
200
|
def default_fields_for(value, operator = nil)
|
191
201
|
|
192
202
|
column_types = []
|
193
203
|
column_types += [:string, :text] if [nil, :like, :unlike, :ne, :eq].include?(operator)
|
194
|
-
column_types += [:
|
204
|
+
column_types += [:double, :float, :decimal] if value =~ NUMERICAL_REGXP
|
205
|
+
column_types += [:integer] if value =~ INTEGER_REGXP
|
195
206
|
column_types += [:datetime, :date, :timestamp] if (parse_temporal(value))
|
196
207
|
|
197
208
|
default_fields.select { |field| column_types.include?(field.type) && !field.set? }
|
@@ -236,8 +247,7 @@ module ScopedSearch
|
|
236
247
|
search_scope = search_scope.where(find_options[:conditions]) if find_options[:conditions]
|
237
248
|
search_scope = search_scope.includes(find_options[:include]) if find_options[:include]
|
238
249
|
search_scope = search_scope.joins(find_options[:joins]) if find_options[:joins]
|
239
|
-
search_scope = search_scope.
|
240
|
-
search_scope = search_scope.group(find_options[:group]) if find_options[:group]
|
250
|
+
search_scope = search_scope.reorder(find_options[:order]) if find_options[:order]
|
241
251
|
search_scope
|
242
252
|
})
|
243
253
|
else
|
@@ -247,15 +257,14 @@ module ScopedSearch
|
|
247
257
|
raise "Currently, only ActiveRecord 2.1 or higher is supported!"
|
248
258
|
end
|
249
259
|
end
|
250
|
-
end
|
251
|
-
end
|
252
260
|
|
253
|
-
# Registers the complete_for method within the class that is used for searching.
|
254
|
-
|
255
|
-
@klass.class_eval do
|
256
|
-
|
257
|
-
|
258
|
-
|
261
|
+
# Registers the complete_for method within the class that is used for searching.
|
262
|
+
def register_complete_for! # :nodoc
|
263
|
+
@klass.class_eval do
|
264
|
+
def self.complete_for(query, options = {})
|
265
|
+
ScopedSearch::AutoCompleteBuilder.auto_complete(@scoped_search , query, options)
|
266
|
+
end
|
267
|
+
end
|
259
268
|
end
|
260
269
|
end
|
261
|
-
|
270
|
+
end
|
@@ -81,7 +81,6 @@ module ScopedSearch
|
|
81
81
|
find_attributes[:include] = includes.uniq unless includes.empty?
|
82
82
|
find_attributes[:joins] = joins.uniq unless joins.empty?
|
83
83
|
find_attributes[:order] = order unless order.nil?
|
84
|
-
find_attributes[:group] = options[:group] unless options[:group].nil?
|
85
84
|
|
86
85
|
# p find_attributes # Uncomment for debugging
|
87
86
|
return find_attributes
|
@@ -89,13 +88,13 @@ module ScopedSearch
|
|
89
88
|
|
90
89
|
def order_by(order, &block)
|
91
90
|
order ||= definition.default_order
|
92
|
-
if order
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
91
|
+
return nil if order.blank?
|
92
|
+
field = definition.field_by_name(order.to_s.split(' ')[0])
|
93
|
+
raise ScopedSearch::QueryNotSupported, "the field '#{order.to_s.split(' ')[0]}' in the order statement is not valid field for search" unless field
|
94
|
+
sql = field.to_sql(&block)
|
95
|
+
direction = (order.to_s.downcase.include?('desc')) ? " DESC" : " ASC"
|
96
|
+
order = sql + direction
|
97
|
+
|
99
98
|
return order
|
100
99
|
end
|
101
100
|
|
@@ -461,10 +460,25 @@ module ScopedSearch
|
|
461
460
|
# <tt>ILIKE operator</tt> instead of <tt>LIKE</tt>.
|
462
461
|
class PostgreSQLAdapter < ScopedSearch::QueryBuilder
|
463
462
|
|
464
|
-
# Switches out the default
|
465
|
-
#
|
463
|
+
# Switches out the default query generation of the <tt>sql_test</tt>
|
464
|
+
# method if full text searching is enabled and a text search is being
|
465
|
+
# performed.
|
466
|
+
def sql_test(field, operator, value, lhs, &block)
|
467
|
+
if [:like, :unlike].include?(operator) and field.full_text_search
|
468
|
+
yield(:parameter, value)
|
469
|
+
negation = (operator == :unlike) ? "NOT " : ""
|
470
|
+
locale = (field.full_text_search == true) ? 'english' : field.full_text_search
|
471
|
+
return "#{negation}to_tsvector('#{locale}', #{field.to_sql(operator, &block)}) #{self.sql_operator(operator, field)} to_tsquery('#{locale}', ?)"
|
472
|
+
else
|
473
|
+
super
|
474
|
+
end
|
475
|
+
end
|
476
|
+
|
477
|
+
# Switches out the default LIKE operator in the default <tt>sql_operator</tt>
|
478
|
+
# method for ILIKE or @@ if full text searching is enabled.
|
466
479
|
def sql_operator(operator, field)
|
467
480
|
raise ScopedSearch::QueryNotSupported, "the operator '#{operator}' is not supported for field type '#{field.type}'" if [:like, :unlike].include?(operator) and !field.textual?
|
481
|
+
return '@@' if [:like, :unlike].include?(operator) and field.full_text_search
|
468
482
|
case operator
|
469
483
|
when :like then 'ILIKE'
|
470
484
|
when :unlike then 'NOT ILIKE'
|
@@ -476,6 +490,12 @@ module ScopedSearch
|
|
476
490
|
def to_not_sql(rhs, definition, &block)
|
477
491
|
"NOT COALESCE(#{rhs.to_sql(self, definition, &block)}, false)"
|
478
492
|
end
|
493
|
+
|
494
|
+
def order_by(order, &block)
|
495
|
+
sql = super(order, &block)
|
496
|
+
sql += sql.include?('DESC') ? ' NULLS LAST ' : ' NULLS FIRST ' if sql
|
497
|
+
sql
|
498
|
+
end
|
479
499
|
end
|
480
500
|
|
481
501
|
# The Oracle adapter also requires some tweaks to make the case insensitive LIKE work.
|
data/scoped_search.gemspec
CHANGED
@@ -3,8 +3,8 @@ Gem::Specification.new do |s|
|
|
3
3
|
|
4
4
|
# Do not change the version and date fields by hand. This will be done
|
5
5
|
# automatically by the gem release script.
|
6
|
-
s.version = "2.
|
7
|
-
s.date = "2012-
|
6
|
+
s.version = "2.4.0"
|
7
|
+
s.date = "2012-09-11"
|
8
8
|
|
9
9
|
s.summary = "Easily search you ActiveRecord models with a simple query language using a named scope."
|
10
10
|
s.description = <<-EOS
|
@@ -20,21 +20,19 @@ Gem::Specification.new do |s|
|
|
20
20
|
it may not be the best choice if it is going to be used on very large datasets or by a large user base.
|
21
21
|
EOS
|
22
22
|
|
23
|
-
s.authors = ['Willem van Bergen', 'Wes Hays']
|
24
|
-
s.email = ['willem@railsdoctors.com', 'weshays@gbdev.com']
|
23
|
+
s.authors = ['Amos Benari', 'Willem van Bergen', 'Wes Hays']
|
24
|
+
s.email = ['abenari@redhat.com', 'willem@railsdoctors.com', 'weshays@gbdev.com']
|
25
25
|
s.homepage = 'http://github.com/wvanbergen/scoped_search/wiki'
|
26
26
|
|
27
27
|
s.add_runtime_dependency('activerecord', '>= 2.1.0')
|
28
28
|
s.add_development_dependency('rspec', '~> 2.0')
|
29
29
|
s.add_development_dependency('rake')
|
30
|
-
|
31
|
-
s.add_development_dependency('sqlite3-ruby')
|
32
30
|
|
33
31
|
s.rdoc_options << '--title' << s.name << '--main' << 'README.rdoc' << '--line-numbers' << '--inline-source'
|
34
32
|
s.extra_rdoc_files = ['README.rdoc']
|
35
33
|
|
36
34
|
# Do not change the files and test_files fields by hand. This will be done
|
37
35
|
# automatically by the gem release script.
|
38
|
-
s.files = %w(.gitignore .infinity_test Gemfile LICENSE README.rdoc Rakefile init.rb lib/scoped_search.rb lib/scoped_search/auto_complete_builder.rb lib/scoped_search/definition.rb lib/scoped_search/query_builder.rb lib/scoped_search/query_language.rb lib/scoped_search/query_language/ast.rb lib/scoped_search/query_language/parser.rb lib/scoped_search/query_language/tokenizer.rb lib/scoped_search/rails_helper.rb scoped_search.gemspec spec/database.yml spec/integration/api_spec.rb spec/integration/auto_complete_spec.rb spec/integration/key_value_querying_spec.rb spec/integration/ordinal_querying_spec.rb spec/integration/profile_querying_spec.rb spec/integration/relation_querying_spec.rb spec/integration/set_query_spec.rb spec/integration/string_querying_spec.rb spec/lib/database.rb spec/lib/matchers.rb spec/lib/mocks.rb spec/spec_helper.rb spec/unit/ast_spec.rb spec/unit/auto_complete_builder_spec.rb spec/unit/definition_spec.rb spec/unit/parser_spec.rb spec/unit/query_builder_spec.rb spec/unit/tokenizer_spec.rb tasks/github-gem.rake)
|
36
|
+
s.files = %w(.gitignore .infinity_test .travis.yml Gemfile Gemfile.activerecord2 Gemfile.activerecord3 LICENSE README.rdoc Rakefile init.rb lib/scoped_search.rb lib/scoped_search/auto_complete_builder.rb lib/scoped_search/definition.rb lib/scoped_search/query_builder.rb lib/scoped_search/query_language.rb lib/scoped_search/query_language/ast.rb lib/scoped_search/query_language/parser.rb lib/scoped_search/query_language/tokenizer.rb lib/scoped_search/rails_helper.rb scoped_search.gemspec spec/database.jruby.yml spec/database.ruby.yml spec/integration/api_spec.rb spec/integration/auto_complete_spec.rb spec/integration/key_value_querying_spec.rb spec/integration/ordinal_querying_spec.rb spec/integration/profile_querying_spec.rb spec/integration/relation_querying_spec.rb spec/integration/set_query_spec.rb spec/integration/string_querying_spec.rb spec/lib/database.rb spec/lib/matchers.rb spec/lib/mocks.rb spec/spec_helper.rb spec/unit/ast_spec.rb spec/unit/auto_complete_builder_spec.rb spec/unit/definition_spec.rb spec/unit/parser_spec.rb spec/unit/query_builder_spec.rb spec/unit/tokenizer_spec.rb tasks/github-gem.rake)
|
39
37
|
s.test_files = %w(spec/integration/api_spec.rb spec/integration/auto_complete_spec.rb spec/integration/key_value_querying_spec.rb spec/integration/ordinal_querying_spec.rb spec/integration/profile_querying_spec.rb spec/integration/relation_querying_spec.rb spec/integration/set_query_spec.rb spec/integration/string_querying_spec.rb spec/unit/ast_spec.rb spec/unit/auto_complete_builder_spec.rb spec/unit/definition_spec.rb spec/unit/parser_spec.rb spec/unit/query_builder_spec.rb spec/unit/tokenizer_spec.rb)
|
40
38
|
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
sqlite:
|
2
|
+
adapter: "jdbcsqlite3"
|
3
|
+
database: ":memory:"
|
4
|
+
|
5
|
+
mysql:
|
6
|
+
adapter: "jdbcmysql"
|
7
|
+
host: "localhost"
|
8
|
+
username: "root"
|
9
|
+
database: "scoped_search_test"
|
10
|
+
|
11
|
+
postgresql:
|
12
|
+
adapter: "jdbcpostgresql"
|
13
|
+
host: "localhost"
|
14
|
+
username: "postgres"
|
15
|
+
database: "scoped_search_test"
|
@@ -0,0 +1,15 @@
|
|
1
|
+
sqlite:
|
2
|
+
adapter: "sqlite3"
|
3
|
+
database: ":memory:"
|
4
|
+
|
5
|
+
mysql:
|
6
|
+
adapter: "mysql2"
|
7
|
+
host: "localhost"
|
8
|
+
username: "root"
|
9
|
+
database: "scoped_search_test"
|
10
|
+
|
11
|
+
postgresql:
|
12
|
+
adapter: "postgresql"
|
13
|
+
host: "localhost"
|
14
|
+
username: "postgres"
|
15
|
+
database: "scoped_search_test"
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require "
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
# These specs will run on all databases that are defined in the spec/database.yml file.
|
4
4
|
# Comment out any databases that you do not have available for testing purposes if needed.
|
@@ -9,31 +9,48 @@ ScopedSearch::RSpec::Database.test_databases.each do |db|
|
|
9
9
|
before(:all) do
|
10
10
|
ScopedSearch::RSpec::Database.establish_named_connection(db)
|
11
11
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
12
|
+
ActiveRecord::Migration.create_table(:bars, :force => true) do |t|
|
13
|
+
t.integer :foo_id
|
14
|
+
t.string :related
|
15
|
+
end
|
16
16
|
|
17
|
-
::
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
17
|
+
ActiveRecord::Migration.create_table(:foos, :force => true) do |t|
|
18
|
+
t.string :string
|
19
|
+
t.string :another
|
20
|
+
t.string :explicit
|
21
|
+
t.integer :int
|
22
|
+
t.date :date
|
23
|
+
t.integer :unindexed
|
24
|
+
end
|
25
|
+
|
26
|
+
class ::Bar < ActiveRecord::Base
|
27
|
+
belongs_to :foo
|
28
|
+
end
|
29
|
+
|
30
|
+
class ::Foo < ActiveRecord::Base
|
31
|
+
has_many :bars
|
24
32
|
|
33
|
+
scoped_search :on => [:string, :int, :date]
|
34
|
+
scoped_search :on => :another, :default_operator => :eq, :alias => :alias
|
35
|
+
scoped_search :on => :explicit, :only_explicit => true, :complete_value => true
|
36
|
+
scoped_search :on => :related, :in => :bars, :rename => 'bars.related'.to_sym
|
25
37
|
end
|
26
38
|
|
27
|
-
@foo_1 = Foo.create!(:string => 'foo', :another => 'temp 1', :explicit => 'baz', :int => 9 , :date => 'February 8,
|
28
|
-
Foo.create!(:string => 'bar', :another => 'temp 2', :explicit => 'baz', :int => 9 , :date => 'February 10,
|
39
|
+
@foo_1 = Foo.create!(:string => 'foo', :another => 'temp 1', :explicit => 'baz', :int => 9 , :date => 'February 8, 2011' , :unindexed => 10)
|
40
|
+
Foo.create!(:string => 'bar', :another => 'temp 2', :explicit => 'baz', :int => 9 , :date => 'February 10, 2011', :unindexed => 10)
|
29
41
|
Foo.create!(:string => 'baz', :another => nil, :explicit => nil , :int => nil, :date => nil , :unindexed => nil)
|
30
42
|
|
31
43
|
Bar.create!(:related => 'lala', :foo => @foo_1)
|
32
|
-
Bar.create!(:related => 'another lala', :foo => @foo_1)
|
44
|
+
Bar.create!(:related => 'another lala', :foo => @foo_1)
|
33
45
|
end
|
34
46
|
|
35
47
|
after(:all) do
|
36
|
-
|
48
|
+
ActiveRecord::Migration.drop_table(:foos)
|
49
|
+
ActiveRecord::Migration.drop_table(:bars)
|
50
|
+
|
51
|
+
Object.send :remove_const, :Foo
|
52
|
+
Object.send :remove_const, :Bar
|
53
|
+
|
37
54
|
ScopedSearch::RSpec::Database.close_connection
|
38
55
|
end
|
39
56
|
|
@@ -136,7 +153,7 @@ ScopedSearch::RSpec::Database.test_databases.each do |db|
|
|
136
153
|
end
|
137
154
|
end
|
138
155
|
|
139
|
-
|
156
|
+
context 'exceptional search strings' do
|
140
157
|
|
141
158
|
it "query that starts with 'or'" do
|
142
159
|
Foo.complete_for('or ').should have(9).items
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require "
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
# These specs will run on all databases that are defined in the spec/database.yml file.
|
4
4
|
# Comment out any databases that you do not have available for testing purposes if needed.
|
@@ -20,72 +20,73 @@ require "#{File.dirname(__FILE__)}/../spec_helper"
|
|
20
20
|
ActiveRecord::Migration.create_table(:keys) { |t| t.string :name }
|
21
21
|
class ::Key < ActiveRecord::Base; has_many :facts; end
|
22
22
|
|
23
|
-
ActiveRecord::Migration.create_table(:facts) { |t| t.string :value; t.integer :key_id; t.integer :
|
24
|
-
class ::Fact < ActiveRecord::Base; belongs_to :key; belongs_to :
|
23
|
+
ActiveRecord::Migration.create_table(:facts) { |t| t.string :value; t.integer :key_id; t.integer :key_value_id }
|
24
|
+
class ::Fact < ActiveRecord::Base; belongs_to :key; belongs_to :key_value; end
|
25
25
|
|
26
26
|
# The class that will run the queries
|
27
|
-
::
|
28
|
-
|
29
|
-
|
30
|
-
|
27
|
+
ActiveRecord::Migration.create_table(:key_values) { |t| t.string :name }
|
28
|
+
class ::KeyValue < ActiveRecord::Base
|
29
|
+
has_many :facts
|
30
|
+
has_many :keys, :through => :facts
|
31
|
+
|
32
|
+
scoped_search :in => :facts, :on => :value, :rename => :facts, :in_key => :keys, :on_key => :name, :complete_value => true
|
31
33
|
end
|
32
34
|
|
33
35
|
@key1 = Key.create!(:name => 'color')
|
34
36
|
@key2 = Key.create!(:name => 'size')
|
35
37
|
|
38
|
+
@kv1 = KeyValue.create!(:name => 'bar')
|
39
|
+
@kv2 = KeyValue.create!(:name => 'barbary')
|
36
40
|
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
Fact.create!(:value => 'green', :key => @key1, :bar => @bar1)
|
41
|
-
Fact.create!(:value => 'gold' , :key => @key1, :bar => @bar2)
|
42
|
-
Fact.create!(:value => '5' , :key => @key2, :bar => @bar1)
|
41
|
+
Fact.create!(:value => 'green', :key => @key1, :key_value => @kv1)
|
42
|
+
Fact.create!(:value => 'gold' , :key => @key1, :key_value => @kv2)
|
43
|
+
Fact.create!(:value => '5' , :key => @key2, :key_value => @kv1)
|
43
44
|
|
44
45
|
end
|
45
46
|
|
46
47
|
after(:all) do
|
47
|
-
ScopedSearch::RSpec::Database.drop_model(
|
48
|
+
ScopedSearch::RSpec::Database.drop_model(KeyValue)
|
48
49
|
ScopedSearch::RSpec::Database.drop_model(Fact)
|
49
50
|
ScopedSearch::RSpec::Database.drop_model(Key)
|
50
51
|
Object.send :remove_const, :Fact
|
51
52
|
Object.send :remove_const, :Key
|
52
|
-
Object.send :remove_const, :
|
53
|
+
Object.send :remove_const, :KeyValue
|
53
54
|
end
|
54
55
|
|
55
56
|
it "should find all bars with a fact name color and fact value green" do
|
56
|
-
|
57
|
+
KeyValue.search_for('facts.color = green').should have(1).items
|
57
58
|
end
|
58
59
|
|
59
60
|
it "should find all bars with a fact name color and fact value gold" do
|
60
|
-
|
61
|
+
KeyValue.search_for('facts.color = gold').first.name.should eql('barbary')
|
61
62
|
end
|
62
63
|
|
63
64
|
it "should find all bars with a fact name size and fact value 5" do
|
64
|
-
|
65
|
+
KeyValue.search_for('facts.size = 5').should have(1).items
|
65
66
|
end
|
66
67
|
|
67
68
|
it "should find all bars with a fact color green and fact size 5" do
|
68
|
-
|
69
|
+
KeyValue.search_for('facts.color = green and facts.size = 5').should have(1).items
|
69
70
|
end
|
70
71
|
|
71
72
|
it "should find all bars with a fact color gold or green" do
|
72
|
-
|
73
|
+
KeyValue.search_for('facts.color = gold or facts.color = green').should have(2).items
|
73
74
|
end
|
74
75
|
|
75
76
|
it "should find all bars that has size value" do
|
76
|
-
|
77
|
+
KeyValue.search_for('has facts.size').should have(1).items
|
77
78
|
end
|
78
79
|
|
79
80
|
it "should find all bars that has color value" do
|
80
|
-
|
81
|
+
KeyValue.search_for('has facts.color').should have(2).items
|
81
82
|
end
|
82
83
|
|
83
84
|
it "should complete facts names" do
|
84
|
-
|
85
|
+
KeyValue.complete_for('facts.').should have(2).items
|
85
86
|
end
|
86
87
|
|
87
88
|
it "should complete values for fact name = color" do
|
88
|
-
|
89
|
+
KeyValue.complete_for('facts.color = ').should have(2).items
|
89
90
|
end
|
90
91
|
|
91
92
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require "
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
# These specs will run on all databases that are defined in the spec/database.yml file.
|
4
4
|
# Comment out any databases that you do not have available for testing purposes if needed.
|
@@ -192,6 +192,7 @@ ScopedSearch::RSpec::Database.test_databases.each do |db|
|
|
192
192
|
@class.search_for('null? explicit').should have(1).items
|
193
193
|
end
|
194
194
|
end
|
195
|
+
|
195
196
|
context 'using order' do
|
196
197
|
it "sort by string ASC" do
|
197
198
|
@class.search_for('',:order => 'string ASC').first.string.should eql('bar')
|
@@ -205,8 +206,14 @@ ScopedSearch::RSpec::Database.test_databases.each do |db|
|
|
205
206
|
@class.search_for('').first.string.should eql('bar')
|
206
207
|
end
|
207
208
|
|
208
|
-
|
209
|
-
|
209
|
+
it "resetting order when selecting distinct values" do
|
210
|
+
distinct_search = if ActiveRecord::VERSION::MAJOR == 2
|
211
|
+
@class.search_for('', :order => '').all(:select => 'DISTINCT(explicit)')
|
212
|
+
else
|
213
|
+
@class.search_for('', :order => '').select(:explicit).uniq
|
214
|
+
end
|
215
|
+
|
216
|
+
Set.new(distinct_search.map(&:explicit)).should == Set['baz', nil]
|
210
217
|
end
|
211
218
|
end
|
212
219
|
end
|
data/spec/lib/database.rb
CHANGED
@@ -12,12 +12,22 @@ module ScopedSearch::RSpec::Database
|
|
12
12
|
end
|
13
13
|
|
14
14
|
def self.test_databases_configuration
|
15
|
-
file =
|
16
|
-
|
15
|
+
file = if RUBY_PLATFORM == 'java'
|
16
|
+
File.expand_path("../database.jruby.yml", File.dirname(__FILE__))
|
17
|
+
else
|
18
|
+
File.expand_path("../database.ruby.yml", File.dirname(__FILE__))
|
19
|
+
end
|
20
|
+
|
21
|
+
@database_connections ||= YAML.load(File.read(file))
|
17
22
|
end
|
18
23
|
|
19
24
|
def self.test_databases
|
20
|
-
test_databases_configuration.keys.sort
|
25
|
+
database_names = test_databases_configuration.keys.sort
|
26
|
+
if ENV['EXCLUDE_DATABASE'].present?
|
27
|
+
exclude_databases = ENV['EXCLUDE_DATABASE'].split(',')
|
28
|
+
database_names -= exclude_databases
|
29
|
+
end
|
30
|
+
return database_names
|
21
31
|
end
|
22
32
|
|
23
33
|
def self.establish_named_connection(name)
|
@@ -34,7 +44,7 @@ module ScopedSearch::RSpec::Database
|
|
34
44
|
end
|
35
45
|
|
36
46
|
def self.create_model(fields)
|
37
|
-
table_name = "model_#{rand}".gsub(
|
47
|
+
table_name = "model_#{rand}".gsub(/\W/, '')
|
38
48
|
ActiveRecord::Migration.create_table(table_name) do |t|
|
39
49
|
fields.each do |name, field_type|
|
40
50
|
options = (field_type == :decimal) ? { :scale => 2, :precision => 10 } : {}
|
@@ -42,8 +52,8 @@ module ScopedSearch::RSpec::Database
|
|
42
52
|
end
|
43
53
|
end
|
44
54
|
|
45
|
-
klass = Class.new(ActiveRecord::Base)
|
46
|
-
klass.
|
55
|
+
klass = ScopedSearch::RSpec::Database.const_set(table_name.classify, Class.new(ActiveRecord::Base))
|
56
|
+
klass.table_name = table_name
|
47
57
|
yield(klass) if block_given?
|
48
58
|
return klass
|
49
59
|
end
|
data/spec/lib/mocks.rb
CHANGED
@@ -10,6 +10,7 @@ module ScopedSearch::RSpec::Mocks
|
|
10
10
|
ar_mock.stub!(:scope).with(:search_for, anything)
|
11
11
|
ar_mock.stub!(:connection).and_return(mock_database_connection)
|
12
12
|
ar_mock.stub!(:ancestors).and_return([ActiveRecord::Base])
|
13
|
+
ar_mock.stub!(:columns_hash).and_return({'existing' => mock('column')})
|
13
14
|
return ar_mock
|
14
15
|
end
|
15
16
|
|
data/spec/unit/ast_spec.rb
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
require "
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe ScopedSearch::Definition do
|
4
4
|
|
@@ -8,6 +8,21 @@ describe ScopedSearch::Definition do
|
|
8
8
|
@definition.stub!(:setup_adapter)
|
9
9
|
end
|
10
10
|
|
11
|
+
describe ScopedSearch::Definition::Field do
|
12
|
+
describe '#column' do
|
13
|
+
it "should raise an exception when using an unknown field" do
|
14
|
+
lambda {
|
15
|
+
@definition.define(:on => 'nonexisting').column
|
16
|
+
}.should raise_error(ActiveRecord::UnknownAttributeError)
|
17
|
+
end
|
18
|
+
|
19
|
+
it "should not raise an exception when using an unknown field" do
|
20
|
+
lambda {
|
21
|
+
@definition.define(:on => 'existing').column
|
22
|
+
}.should_not raise_error(ActiveRecord::UnknownAttributeError)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
11
26
|
|
12
27
|
describe '#initialize' do
|
13
28
|
|
data/spec/unit/parser_spec.rb
CHANGED
data/spec/unit/tokenizer_spec.rb
CHANGED
data/tasks/github-gem.rake
CHANGED
@@ -13,8 +13,8 @@ module GithubGem
|
|
13
13
|
|
14
14
|
# Detects the main include file of this project using heuristics
|
15
15
|
def self.detect_main_include
|
16
|
-
if
|
17
|
-
"lib/#{
|
16
|
+
if File.exist?(File.expand_path("../lib/#{File.basename(detect_gemspec_file, '.gemspec').gsub(/-/, '/')}.rb", detect_gemspec_file))
|
17
|
+
"lib/#{File.basename(detect_gemspec_file, '.gemspec').gsub(/-/, '/')}.rb"
|
18
18
|
elsif FileList['lib/*.rb'].length == 1
|
19
19
|
FileList['lib/*.rb'].first
|
20
20
|
else
|
@@ -24,6 +24,8 @@ module GithubGem
|
|
24
24
|
|
25
25
|
class RakeTasks
|
26
26
|
|
27
|
+
include Rake::DSL if Rake.const_defined?('DSL')
|
28
|
+
|
27
29
|
attr_reader :gemspec, :modified_files
|
28
30
|
attr_accessor :gemspec_file, :task_namespace, :main_include, :root_dir, :spec_pattern, :test_pattern, :remote, :remote_branch, :local_branch
|
29
31
|
|
@@ -342,7 +344,7 @@ module GithubGem
|
|
342
344
|
require 'net/https'
|
343
345
|
require 'uri'
|
344
346
|
|
345
|
-
uri = URI.parse('https://github.com/wvanbergen/github-gem/
|
347
|
+
uri = URI.parse('https://raw.github.com/wvanbergen/github-gem/master/tasks/github-gem.rake')
|
346
348
|
http = Net::HTTP.new(uri.host, uri.port)
|
347
349
|
http.use_ssl = true
|
348
350
|
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
metadata
CHANGED
@@ -1,97 +1,77 @@
|
|
1
|
-
--- !ruby/object:Gem::Specification
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
2
|
name: scoped_search
|
3
|
-
version: !ruby/object:Gem::Version
|
4
|
-
|
5
|
-
prerelease:
|
6
|
-
segments:
|
7
|
-
- 2
|
8
|
-
- 3
|
9
|
-
- 7
|
10
|
-
version: 2.3.7
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 2.4.0
|
5
|
+
prerelease:
|
11
6
|
platform: ruby
|
12
|
-
authors:
|
7
|
+
authors:
|
8
|
+
- Amos Benari
|
13
9
|
- Willem van Bergen
|
14
10
|
- Wes Hays
|
15
11
|
autorequire:
|
16
12
|
bindir: bin
|
17
13
|
cert_chain: []
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
requirement: &id001 !ruby/object:Gem::Requirement
|
14
|
+
date: 2012-09-11 00:00:00.000000000 Z
|
15
|
+
dependencies:
|
16
|
+
- !ruby/object:Gem::Dependency
|
17
|
+
name: activerecord
|
18
|
+
requirement: &70188989608520 !ruby/object:Gem::Requirement
|
24
19
|
none: false
|
25
|
-
requirements:
|
26
|
-
- -
|
27
|
-
- !ruby/object:Gem::Version
|
28
|
-
hash: 11
|
29
|
-
segments:
|
30
|
-
- 2
|
31
|
-
- 1
|
32
|
-
- 0
|
20
|
+
requirements:
|
21
|
+
- - ! '>='
|
22
|
+
- !ruby/object:Gem::Version
|
33
23
|
version: 2.1.0
|
34
24
|
type: :runtime
|
35
|
-
name: activerecord
|
36
25
|
prerelease: false
|
37
|
-
version_requirements: *
|
38
|
-
- !ruby/object:Gem::Dependency
|
39
|
-
|
26
|
+
version_requirements: *70188989608520
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: rspec
|
29
|
+
requirement: &70188989607800 !ruby/object:Gem::Requirement
|
40
30
|
none: false
|
41
|
-
requirements:
|
31
|
+
requirements:
|
42
32
|
- - ~>
|
43
|
-
- !ruby/object:Gem::Version
|
44
|
-
|
45
|
-
segments:
|
46
|
-
- 2
|
47
|
-
- 0
|
48
|
-
version: "2.0"
|
33
|
+
- !ruby/object:Gem::Version
|
34
|
+
version: '2.0'
|
49
35
|
type: :development
|
50
|
-
name: rspec
|
51
36
|
prerelease: false
|
52
|
-
version_requirements: *
|
53
|
-
- !ruby/object:Gem::Dependency
|
54
|
-
requirement: &id003 !ruby/object:Gem::Requirement
|
55
|
-
none: false
|
56
|
-
requirements:
|
57
|
-
- - ">="
|
58
|
-
- !ruby/object:Gem::Version
|
59
|
-
hash: 3
|
60
|
-
segments:
|
61
|
-
- 0
|
62
|
-
version: "0"
|
63
|
-
type: :development
|
37
|
+
version_requirements: *70188989607800
|
38
|
+
- !ruby/object:Gem::Dependency
|
64
39
|
name: rake
|
65
|
-
|
66
|
-
version_requirements: *id003
|
67
|
-
- !ruby/object:Gem::Dependency
|
68
|
-
requirement: &id004 !ruby/object:Gem::Requirement
|
40
|
+
requirement: &70188989607000 !ruby/object:Gem::Requirement
|
69
41
|
none: false
|
70
|
-
requirements:
|
71
|
-
- -
|
72
|
-
- !ruby/object:Gem::Version
|
73
|
-
|
74
|
-
segments:
|
75
|
-
- 0
|
76
|
-
version: "0"
|
42
|
+
requirements:
|
43
|
+
- - ! '>='
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
version: '0'
|
77
46
|
type: :development
|
78
|
-
name: sqlite3-ruby
|
79
47
|
prerelease: false
|
80
|
-
version_requirements: *
|
81
|
-
description: " Scoped search makes it easy to search your ActiveRecord-based
|
82
|
-
|
48
|
+
version_requirements: *70188989607000
|
49
|
+
description: ! " Scoped search makes it easy to search your ActiveRecord-based
|
50
|
+
models.\n \n It will create a named scope :search_for that can be called with
|
51
|
+
a query string. It will build an SQL query using\n the provided query string
|
52
|
+
and a definition that specifies on what fields to search. Because the functionality
|
53
|
+
is\n built on named_scope, the result of the search_for call can be used like
|
54
|
+
any other named_scope, so it can be\n chained with another scope or combined
|
55
|
+
with will_paginate.\n \n Because it uses standard SQL, it does not require
|
56
|
+
any setup, indexers or daemons. This makes scoped_search\n suitable to quickly
|
57
|
+
add basic search functionality to your application with little hassle. On the other
|
58
|
+
hand,\n it may not be the best choice if it is going to be used on very large
|
59
|
+
datasets or by a large user base.\n"
|
60
|
+
email:
|
61
|
+
- abenari@redhat.com
|
83
62
|
- willem@railsdoctors.com
|
84
63
|
- weshays@gbdev.com
|
85
64
|
executables: []
|
86
|
-
|
87
65
|
extensions: []
|
88
|
-
|
89
|
-
extra_rdoc_files:
|
66
|
+
extra_rdoc_files:
|
90
67
|
- README.rdoc
|
91
|
-
files:
|
68
|
+
files:
|
92
69
|
- .gitignore
|
93
70
|
- .infinity_test
|
71
|
+
- .travis.yml
|
94
72
|
- Gemfile
|
73
|
+
- Gemfile.activerecord2
|
74
|
+
- Gemfile.activerecord3
|
95
75
|
- LICENSE
|
96
76
|
- README.rdoc
|
97
77
|
- Rakefile
|
@@ -106,7 +86,8 @@ files:
|
|
106
86
|
- lib/scoped_search/query_language/tokenizer.rb
|
107
87
|
- lib/scoped_search/rails_helper.rb
|
108
88
|
- scoped_search.gemspec
|
109
|
-
- spec/database.yml
|
89
|
+
- spec/database.jruby.yml
|
90
|
+
- spec/database.ruby.yml
|
110
91
|
- spec/integration/api_spec.rb
|
111
92
|
- spec/integration/auto_complete_spec.rb
|
112
93
|
- spec/integration/key_value_querying_spec.rb
|
@@ -126,46 +107,38 @@ files:
|
|
126
107
|
- spec/unit/query_builder_spec.rb
|
127
108
|
- spec/unit/tokenizer_spec.rb
|
128
109
|
- tasks/github-gem.rake
|
129
|
-
has_rdoc: true
|
130
110
|
homepage: http://github.com/wvanbergen/scoped_search/wiki
|
131
111
|
licenses: []
|
132
|
-
|
133
112
|
post_install_message:
|
134
|
-
rdoc_options:
|
113
|
+
rdoc_options:
|
135
114
|
- --title
|
136
115
|
- scoped_search
|
137
116
|
- --main
|
138
117
|
- README.rdoc
|
139
118
|
- --line-numbers
|
140
119
|
- --inline-source
|
141
|
-
require_paths:
|
120
|
+
require_paths:
|
142
121
|
- lib
|
143
|
-
required_ruby_version: !ruby/object:Gem::Requirement
|
122
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
144
123
|
none: false
|
145
|
-
requirements:
|
146
|
-
- -
|
147
|
-
- !ruby/object:Gem::Version
|
148
|
-
|
149
|
-
|
150
|
-
- 0
|
151
|
-
version: "0"
|
152
|
-
required_rubygems_version: !ruby/object:Gem::Requirement
|
124
|
+
requirements:
|
125
|
+
- - ! '>='
|
126
|
+
- !ruby/object:Gem::Version
|
127
|
+
version: '0'
|
128
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
153
129
|
none: false
|
154
|
-
requirements:
|
155
|
-
- -
|
156
|
-
- !ruby/object:Gem::Version
|
157
|
-
|
158
|
-
segments:
|
159
|
-
- 0
|
160
|
-
version: "0"
|
130
|
+
requirements:
|
131
|
+
- - ! '>='
|
132
|
+
- !ruby/object:Gem::Version
|
133
|
+
version: '0'
|
161
134
|
requirements: []
|
162
|
-
|
163
135
|
rubyforge_project:
|
164
|
-
rubygems_version: 1.
|
136
|
+
rubygems_version: 1.8.16
|
165
137
|
signing_key:
|
166
138
|
specification_version: 3
|
167
|
-
summary: Easily search you ActiveRecord models with a simple query language using
|
168
|
-
|
139
|
+
summary: Easily search you ActiveRecord models with a simple query language using
|
140
|
+
a named scope.
|
141
|
+
test_files:
|
169
142
|
- spec/integration/api_spec.rb
|
170
143
|
- spec/integration/auto_complete_spec.rb
|
171
144
|
- spec/integration/key_value_querying_spec.rb
|