lib/scoped_search/definition.rb in scoped_search-4.1.5 vs lib/scoped_search/definition.rb in scoped_search-4.1.6
- old
+ new
@@ -15,11 +15,11 @@
# class, so you should not create instances of this class yourself.
class Field
attr_reader :definition, :field, :only_explicit, :relation, :key_relation, :full_text_search,
:key_field, :complete_value, :complete_enabled, :offset, :word_size, :ext_method, :operators,
- :validator
+ :validator, :value_translation, :special_values
# Initializes a Field instance given the definition passed to the
# scoped_search call on the ActiveRecord-based model class.
#
# Field name may be given in positional 'field' argument or 'on' named
@@ -40,18 +40,22 @@
only_explicit: nil,
operators: nil,
profile: nil,
relation: nil,
rename: nil,
+ special_values: [],
validator: nil,
+ value_translation: nil,
word_size: 1,
**kwargs)
# Prefer 'on' kw arg if given, defaults to the 'field' positional to allow either syntax
raise ArgumentError, "Missing field or 'on' keyword argument" if on.nil?
@field = on.to_sym
+ raise ArgumentError, "'special_values' must be an Array" unless special_values.kind_of?(Array)
+
# Reserved Ruby keywords so access via kwargs instead, but deprecate them for future versions
if kwargs.key?(:in)
relation = kwargs.delete(:in)
ActiveSupport::Deprecation.warn("'in' argument deprecated, prefer 'relation' since scoped_search 4.0.0", caller(6))
end
@@ -75,12 +79,14 @@
@key_relation = in_key
@offset = offset
@only_explicit = !!only_explicit
@operators = operators
@relation = relation
+ @special_values = special_values
@validator = validator
@word_size = word_size
+ @value_translation = value_translation
# Store this field in the field array
definition.define_field(rename || @field, self)
# Store definition for aliases as well
@@ -152,10 +158,14 @@
# Returns true if this is a textual column.
def textual?
[:string, :text].include?(type)
end
+ def uuid?
+ type == :uuid
+ end
+
# Returns true if this is a set.
def set?
complete_value.is_a?(Hash)
end
@@ -236,26 +246,28 @@
def operator_by_field_name(name)
field = field_by_name(name)
return [] if field.nil?
return field.operators if field.operators
return ['=', '!=', '>', '<', '<=', '>=', '~', '!~', '^', '!^'] if field.virtual?
- return ['=', '!='] if field.set?
+ return ['=', '!='] if field.set? || field.uuid?
return ['=', '>', '<', '<=', '>=', '!=', '^', '!^'] if field.numerical?
return ['=', '!=', '~', '!~', '^', '!^'] if field.textual?
return ['=', '>', '<'] if field.temporal?
raise ScopedSearch::QueryNotSupported, "Unsupported type '#{field.type.inspect}')' for field '#{name}'. This can be a result of a search definition problem."
end
NUMERICAL_REGXP = /^\-?\d+(\.\d+)?$/
INTEGER_REGXP = /^\-?\d+$/
+ UUID_REGXP = /^[0-9a-f]{8}(-[0-9a-f]{4}){3}-[0-9a-f]{12}$/
# Returns a list of appropriate fields to search in given a search keyword and operator.
def default_fields_for(value, operator = nil)
column_types = [:virtual]
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 += [:uuid] if value =~ UUID_REGXP
column_types += [:datetime, :date, :timestamp] if (parse_temporal(value))
default_fields.select { |field| !field.set? && column_types.include?(field.type) }
end