Class: ScopedSearch::Definition

Inherits:
Object
  • Object
show all
Defined in:
lib/scoped_search/definition.rb

Overview

The ScopedSearch definition class defines on what fields should be search in the model in what cases

A definition can be created by calling the scoped_search method on an ActiveRecord-based class, so you should not create an instance of this class yourself.

Defined Under Namespace

Classes: Field

Constant Summary

NUMERICAL_REGXP =
/^\-?\d+(\.\d+)?$/
INTEGER_REGXP =
/^\-?\d+$/

Instance Attribute Summary (collapse)

Instance Method Summary (collapse)

Constructor Details

- (Definition) initialize(klass)

Initializes a ScopedSearch definition instance. This method will also setup a database adapter and create the :search_for named scope if it does not yet exist.



148
149
150
151
152
153
154
155
156
157
# File 'lib/scoped_search/definition.rb', line 148

def initialize(klass)
  @klass                 = klass
  @fields                = {}
  @unique_fields         = []
  @profile_fields        = {:default => {}}
  @profile_unique_fields = {:default => []}

  register_named_scope! unless klass.respond_to?(:search_for)
  register_complete_for! unless klass.respond_to?(:complete_for)
end

Instance Attribute Details

- (Object) default_order

Returns the value of attribute default_order



159
160
161
# File 'lib/scoped_search/definition.rb', line 159

def default_order
  @default_order
end

- (Object) klass (readonly)

Returns the value of attribute klass



143
144
145
# File 'lib/scoped_search/definition.rb', line 143

def klass
  @klass
end

- (Object) profile

Returns the value of attribute profile



159
160
161
# File 'lib/scoped_search/definition.rb', line 159

def profile
  @profile
end

Instance Method Details

- (Object) default_fields

Returns a list of fields that should be searched on by default.

Every field will show up in this method's result, except for fields for which the only_explicit parameter is set to true.



223
224
225
# File 'lib/scoped_search/definition.rb', line 223

def default_fields
  unique_fields.reject { |field| field.only_explicit }
end

- (Object) default_fields_for(value, operator = nil)

Returns a list of appropriate fields to search in given a search keyword and operator.



197
198
199
200
201
202
203
204
205
206
# File 'lib/scoped_search/definition.rb', line 197

def default_fields_for(value, operator = nil)

  column_types  = []
  column_types += [:string, :text]                if [nil, :like, :unlike, :ne, :eq].include?(operator)
  column_types += [:double, :float, :decimal]     if value =~ NUMERICAL_REGXP
  column_types += [:integer]                      if value =~ INTEGER_REGXP
  column_types += [:datetime, :date, :timestamp]  if (parse_temporal(value))

  default_fields.select { |field| column_types.include?(field.type) && !field.set? }
end

- (Object) define(options)

Defines a new search field for this search definition.



228
229
230
# File 'lib/scoped_search/definition.rb', line 228

def define(options)
  Field.new(self, options)
end

- (Object) field_by_name(name)

this method return definitions::field object from string



172
173
174
175
176
177
178
179
# File 'lib/scoped_search/definition.rb', line 172

def field_by_name(name)
  field = fields[name.to_sym] unless name.blank?
  if field.nil?
    dotted = name.to_s.split('.')[0]
    field = fields[dotted.to_sym] unless dotted.blank?
  end
  field
end

- (Object) fields



161
162
163
164
# File 'lib/scoped_search/definition.rb', line 161

def fields
  @profile ||= :default
  @profile_fields[@profile] ||= {}
end

- (Object) operator_by_field_name(name)

this method is used by the syntax auto completer to suggest operators.



182
183
184
185
186
187
188
189
190
191
# File 'lib/scoped_search/definition.rb', line 182

def operator_by_field_name(name)
  field = field_by_name(name)
  return [] if field.nil?
  return field.operators                                      if field.operators
  return ['= ', '!= ']                                        if field.set?
  return ['= ', '> ', '< ', '<= ', '>= ','!= ', '^ ', '!^ ']  if field.numerical?
  return ['= ', '!= ', '~ ', '!~ ', '^ ', '!^ ']              if field.textual?
  return ['= ', '> ', '< ']                                   if field.temporal?
  raise ScopedSearch::QueryNotSupported, "could not verify '#{name}' type, this can be a result of a definition error"
end

- (Object) parse_temporal(value)

Try to parse a string as a datetime. Supported formats are Today, Yesterday, Sunday, '1 day ago', '2 hours ago', '3 months ago','Jan 23, 2004' And many more formats that are documented in Ruby DateTime API Doc.



211
212
213
214
215
216
217
# File 'lib/scoped_search/definition.rb', line 211

def parse_temporal(value)
  return Date.current if value =~ /\btoday\b/i
  return 1.day.ago.to_date if value =~ /\byesterday\b/i
  return (eval(value.strip.gsub(/\s+/,'.').downcase)).to_datetime if value =~ /\A\s*\d+\s+\bhours?|minutes?\b\s+\bago\b\s*\z/i
  return (eval(value.strip.gsub(/\s+/,'.').downcase)).to_date if value =~ /\A\s*\d+\s+\b(days?|weeks?|months?|years?)\b\s+\bago\b\s*\z/i
  DateTime.parse(value, true) rescue nil
end

- (Object) unique_fields



166
167
168
169
# File 'lib/scoped_search/definition.rb', line 166

def unique_fields
  @profile ||= :default
  @profile_unique_fields[@profile] ||= []
end