Module: Mongoid::Criteria::Queryable::Selectable
Relationships & Source Files | |
Super Chains via Extension / Inclusion / Inheritance | |
Class Chain:
self,
Macroable
|
|
Defined in: | lib/mongoid/criteria/queryable/selectable.rb |
Overview
An queryable selectable is selectable, in that it has the ability to select document from the database. The selectable module brings all functionality to the selectable that has to do with building MongoDB selectors.
Constant Summary
-
LINE_STRING =
Constant for a LineString $geometry.
"LineString"
-
POINT =
Constant for a Point $geometry.
"Point"
-
POLYGON =
Constant for a Polygon $geometry.
"Polygon"
Class Method Summary
-
.forwardables ⇒ Array<Symbol>
Get the methods on the selectable that can be forwarded to from a model.
Macroable
- Extended
Instance Attribute Summary
- #negating rw
- #negating If the next expression is negated.(If the next expression is negated.) rw
-
#negating? ⇒ true | false
rw
Is the current selectable negating the next selection?
- #selector rw
- #selector The query selector.(The query selector.) rw
Instance Method Summary
-
#all(*criteria) ⇒ Selectable
(also: #all_in)
Add the $all criterion.
-
#all_in(*criteria)
Alias for #all.
-
#all_of(*criteria)
Alias for #and.
-
#and(*criteria) ⇒ Selectable
(also: #all_of)
Add the $and criterion.
-
#any_in(condition)
Alias for #in.
-
#any_of(*criteria) ⇒ Selectable
Adds a disjunction of the arguments as an additional constraint to the criteria already existing in the receiver.
-
#between(criterion) ⇒ Selectable
Add the range selection.
-
#elem_match(criterion) ⇒ Selectable
Select with an $elemMatch.
-
#eq(criterion) ⇒ Selectable
Add the $eq criterion to the selector.
-
#excludes(criterion)
Alias for #ne.
-
#exists(criterion) ⇒ Selectable
Add the $exists selection.
-
#geo_spatial(criterion) ⇒ Selectable
Add a $geoIntersects or $geoWithin selection.
-
#gt(criterion) ⇒ Selectable
Add the $gt criterion to the selector.
-
#gte(criterion) ⇒ Selectable
Add the $gte criterion to the selector.
-
#in(condition) ⇒ Selectable
(also: #any_in)
Adds the $in selection to the selectable.
-
#lt(criterion) ⇒ Selectable
Add the $lt criterion to the selector.
-
#lte(criterion) ⇒ Selectable
Add the $lte criterion to the selector.
-
#max_distance(criterion) ⇒ Selectable
Add a $maxDistance selection to the selectable.
-
#mod(criterion) ⇒ Selectable
Adds $mod selection to the selectable.
-
#ne(criterion) ⇒ Selectable
(also: #excludes)
Adds $ne selection to the selectable.
-
#near(criterion) ⇒ Selectable
Adds a $near criterion to a geo selection.
-
#near_sphere(criterion) ⇒ Selectable
Adds a $nearSphere criterion to a geo selection.
-
#nin(condition) ⇒ Selectable
(also: #not_in)
Adds the $nin selection to the selectable.
-
#none_of(*criteria) ⇒ Selectable
Negate the arguments, constraining the query to only those documents that do NOT match the arguments.
-
#nor(*criteria) ⇒ Selectable
Adds $nor selection to the selectable.
-
#not(*criteria) ⇒ Selectable
Negate the arguments, or the next selection if no arguments are given.
-
#not_in(condition)
Alias for #nin.
-
#or(*criteria) ⇒ Selectable
Creates a disjunction using $or from the existing criteria in the receiver and the provided arguments.
-
#text_search(terms, opts = nil) ⇒ Selectable
Construct a text search selector.
-
#where(*criteria) ⇒ Selectable
This is the general entry point for most MongoDB queries.
-
#with_size(criterion) ⇒ Selectable
Add a $size selection for array fields.
-
#with_type(criterion) ⇒ Selectable
Adds a $type selection to the selectable.
-
#expr_query(criterion) ⇒ Selectable
private
Internal use only
Internal use only
Adds the specified expression to the query.
-
#js_query(criterion) ⇒ Selectable
private
Internal use only
Internal use only
Create a javascript selection.
-
#selection(criterion = nil) ⇒ Selectable
private
Internal use only
Internal use only
Take the provided criterion and store it as a selection in the query selector.
-
#typed_override(criterion, operator)
private
Internal use only
Internal use only
Force the values of the criterion to be evolved.
Class Method Details
.forwardables ⇒ Array<Symbol>
Get the methods on the selectable that can be forwarded to from a model.
Instance Attribute Details
#negating (rw)
[ GitHub ]# File 'lib/mongoid/criteria/queryable/selectable.rb', line 25
attr_accessor :negating, :selector
#negating If the next expression is negated.(If the next expression is negated.) (rw)
[ GitHub ]
#negating? ⇒ true
| false
(rw)
Is the current selectable negating the next selection?
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 535
def negating? !!negating end
#selector (rw)
[ GitHub ]# File 'lib/mongoid/criteria/queryable/selectable.rb', line 25
attr_accessor :negating, :selector
#selector The query selector.(The query selector.) (rw)
[ GitHub ]Instance Method Details
#all(*criteria) ⇒ Selectable
Also known as: #all_in
Add the $all criterion.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 38
def all(*criteria) if criteria.empty? return clone.tap do |query| query.reset_strategies! end end criteria.inject(clone) do |query, condition| if condition.nil? raise Errors::CriteriaArgumentRequired, :all end condition = (condition) if strategy send(strategy, condition, "$all") else condition.inject(query) do |_query, (field, value)| v = {'$all' => value} if negating? v = {'$not' => v} end _query.add_field_expression(field.to_s, v) end end end.reset_strategies! end
#all_in(*criteria)
Alias for #all.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 65
alias :all_in :all
#all_of(*criteria)
Alias for #and.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 111
alias :all_of :and
#and(*criteria) ⇒ Selectable
Also known as: #all_of
Add the $and criterion.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 78
def and(*criteria) _mongoid_flatten_arrays(criteria).inject(self.clone) do |c, new_s| if new_s.is_a?(Selectable) new_s = new_s.selector end normalized = (new_s) normalized.each do |k, v| k = k.to_s if c.selector[k] # There is already a condition on k. # If v is an operator, and all existing conditions are # also operators, and v isn't present in existing conditions, # we can add to existing conditions. # Otherwise use $and. if v.is_a?(Hash) && v.length == 1 && (new_k = v.keys.first).start_with?('$') && (existing_kv = c.selector[k]).is_a?(Hash) && !existing_kv.key?(new_k) && existing_kv.keys.all? { |sub_k| sub_k.start_with?('$') } then merged_v = c.selector[k].merge(v) c.selector.store(k, merged_v) else c = c.send(:__multi__, [k => v], '$and') end else c.selector.store(k, v) end end c end end
#any_in(condition)
Alias for #in.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 339
alias :any_in :in
#any_of(*criteria) ⇒ Selectable
Adds a disjunction of the arguments as an additional constraint to the criteria already existing in the receiver.
Use #or to make the receiver one of the disjunction operands.
Each argument can be a ::Hash
, a ::Mongoid::Criteria
object, an array of ::Hash
or ::Mongoid::Criteria
objects, or a nested array. Nested arrays will be flattened and can be of any depth. Passing arrays is deprecated.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 674
def any_of(*criteria) criteria = _mongoid_flatten_arrays(criteria) case criteria.length when 0 clone when 1 # When we have a single criteria, any_of behaves like and. # Note: criteria can be a Query object, which #where method does # not support. self.and(*criteria) else # When we have multiple criteria, combine them all with $or # and add the result to self. exprs = criteria.map do |criterion| if criterion.is_a?(Selectable) (criterion.selector) else Hash[criterion.map do |k, v| if k.is_a?(Symbol) [k.to_s, v] else [k, v] end end] end end self.and('$or' => exprs) end end
#between(criterion) ⇒ Selectable
Add the range selection.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 124
def between(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :between end selection(criterion) do |selector, field, value| selector.store( field, { "$gte" => value.min, "$lte" => value.max } ) end end
#elem_match(criterion) ⇒ Selectable
Select with an $elemMatch.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 154
def elem_match(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :elem_match end and_with_operator(criterion, "$elemMatch") end
#eq(criterion) ⇒ Selectable
Add the $eq criterion to the selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 257
def eq(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :eq end and_with_operator(criterion, "$eq") end
#excludes(criterion)
Alias for #ne.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 437
alias :excludes :ne
#exists(criterion) ⇒ Selectable
Add the $exists selection.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 177
def exists(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :exists end typed_override(criterion, "$exists") do |value| Mongoid::Boolean.evolve(value) end end
#expr_query(criterion) ⇒ Selectable
(private)
Adds the specified expression to the query.
Criterion must be a hash in one of the following forms:
-
value
-
=> value
-
value
-
=> operator_value_expression
Field name and operator may be given as either strings or symbols.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 852
def expr_query(criterion) if criterion.nil? raise ArgumentError, 'Criterion cannot be nil here' end unless Hash === criterion raise Errors::InvalidQuery, "Expression must be a Hash: #{Errors::InvalidQuery.truncate_expr(criterion)}" end normalized = (criterion) clone.tap do |query| normalized.each do |field, value| field_s = field.to_s if field_s.start_with?('$') # Query expression-level operator, like $and or $where query.add_operator_expression(field_s, value) else query.add_field_expression(field, value) end end query.reset_strategies! end end
#geo_spatial(criterion) ⇒ Selectable
The only valid geometry shapes for a $geoIntersects are: :intersects_line
, :intersects_point
, and :intersects_polygon
.
The only valid options for a $geoWithin query are the geometry shape :within_polygon
and the operator :within_box
.
The :within_box
operator for the $geoWithin query expects the lower left (south west) coordinate pair as the first argument and the upper right (north east) as the second argument. Important: When latitude and longitude are passed, longitude is expected as the first element of the coordinate pair. Source: www.mongodb.com/docs/manual/reference/operator/query/box/
Add a $geoIntersects or $geoWithin selection. ::Symbol
operators must be used as shown in the examples to expand the criteria.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 224
def geo_spatial(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :geo_spatial end __merge__(criterion) end
#gt(criterion) ⇒ Selectable
Add the $gt criterion to the selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 277
def gt(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :gt end and_with_operator(criterion, "$gt") end
#gte(criterion) ⇒ Selectable
Add the $gte criterion to the selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 297
def gte(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :gte end and_with_operator(criterion, "$gte") end
#in(condition) ⇒ Selectable
Also known as: #any_in
Adds the $in selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 320
def in(condition) if condition.nil? raise Errors::CriteriaArgumentRequired, :in end condition = (condition) if strategy send(strategy, condition, "$in") else condition.inject(clone) do |query, (field, value)| v = {'$in' => value} if negating? v = {'$not' => v} end query.add_field_expression(field.to_s, v) end.reset_strategies! end end
#js_query(criterion) ⇒ Selectable
(private)
Create a javascript selection.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 904
def js_query(criterion) clone.tap do |query| if negating? query.add_operator_expression('$and', [{'$nor' => [{'$where' => criterion}]}]) else query.add_operator_expression('$where', criterion) end query.reset_strategies! end end
#lt(criterion) ⇒ Selectable
Add the $lt criterion to the selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 353
def lt(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :lt end and_with_operator(criterion, "$lt") end
#lte(criterion) ⇒ Selectable
Add the $lte criterion to the selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 373
def lte(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :lte end and_with_operator(criterion, "$lte") end
#max_distance(criterion) ⇒ Selectable
Add a $maxDistance selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 390
def max_distance(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :max_distance end # $maxDistance must be given together with $near __add__(criterion, "$maxDistance") end
#mod(criterion) ⇒ Selectable
Adds $mod selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 410
def mod(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :mod end and_with_operator(criterion, "$mod") end
#ne(criterion) ⇒ Selectable
Also known as: #excludes
Adds $ne selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 430
def ne(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :ne end and_with_operator(criterion, "$ne") end
#near(criterion) ⇒ Selectable
Adds a $near criterion to a geo selection.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 451
def near(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :near end and_with_operator(criterion, "$near") end
#near_sphere(criterion) ⇒ Selectable
Adds a $nearSphere criterion to a geo selection.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 471
def near_sphere(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :near_sphere end and_with_operator(criterion, "$nearSphere") end
#nin(condition) ⇒ Selectable
Also known as: #not_in
Adds the $nin selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 494
def nin(condition) if condition.nil? raise Errors::CriteriaArgumentRequired, :nin end condition = (condition) if strategy send(strategy, condition, "$nin") else condition.inject(clone) do |query, (field, value)| v = {'$nin' => value} if negating? v = {'$not' => v} end query.add_field_expression(field.to_s, v) end.reset_strategies! end end
#none_of(*criteria) ⇒ Selectable
Negate the arguments, constraining the query to only those documents that do NOT match the arguments.
#nor(*criteria) ⇒ Selectable
Adds $nor selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 525
def nor(*criteria) _mongoid_add_top_level_operation('$nor', criteria) end
#not(*criteria) ⇒ Selectable
Negate the arguments, or the next selection if no arguments are given.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 554
def not(*criteria) if criteria.empty? dup.tap { |query| query.negating = true } else criteria.compact.inject(self.clone) do |c, new_s| if new_s.is_a?(Selectable) new_s = new_s.selector end (new_s).each do |k, v| k = k.to_s if c.selector[k] || k.start_with?('$') c = c.send(:__multi__, [{'$nor' => [{k => v}]}], '$and') else if v.is_a?(Hash) c = c.send(:__multi__, [{'$nor' => [{k => v}]}], '$and') else if v.is_a?(Regexp) negated_operator = '$not' else negated_operator = '$ne' end c = c.send(:__override__, {k => v}, negated_operator) end end end c end end end
#not_in(condition)
Alias for #nin.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 513
alias :not_in :nin
#or(*criteria) ⇒ Selectable
Creates a disjunction using $or from the existing criteria in the receiver and the provided arguments.
This behavior (receiver becoming one of the disjunction operands) matches ActiveRecord’s or
behavior.
Use #any_of to add a disjunction of the arguments as an additional constraint to the criteria already existing in the receiver.
Each argument can be a ::Hash
, a ::Mongoid::Criteria
object, an array of ::Hash
or ::Mongoid::Criteria
objects, or a nested array. Nested arrays will be flattened and can be of any depth. Passing arrays is deprecated.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 644
def or(*criteria) _mongoid_add_top_level_operation('$or', criteria) end
#selection(criterion = nil) ⇒ Selectable
(private)
Take the provided criterion and store it as a selection in the query selector.
#text_search(terms, opts = nil) ⇒ Selectable
Per www.mongodb.com/docs/manual/reference/operator/query/text/ it is not currently possible to supply multiple text search conditions in a query. ::Mongoid
will build such a query but the server will return an error when trying to execute it.
Construct a text search selector.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 776
def text_search(terms, opts = nil) if terms.nil? raise Errors::CriteriaArgumentRequired, :terms end clone.tap do |query| criterion = {'$text' => { '$search' => terms }} criterion['$text'].merge!(opts) if opts if query.selector['$text'] # Per https://www.mongodb.com/docs/manual/reference/operator/query/text/ # multiple $text expressions are not currently supported by # MongoDB server, but build the query correctly instead of # overwriting previous text search condition with the currently # given one. Mongoid.logger.warn('Multiple $text expressions per query are not currently supported by the server') query.selector = {'$and' => [query.selector]}.merge(criterion) else query.selector = query.selector.merge(criterion) end end end
#typed_override(criterion, operator) (private)
Force the values of the criterion to be evolved.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 885
def typed_override(criterion, operator) if criterion criterion.transform_values! do |value| yield(value) end end __override__(criterion, operator) end
#where(*criteria) ⇒ Selectable
This is the general entry point for most MongoDB queries. This either creates a standard field: value selection, and expanded selection with the use of hash methods, or a $where selection if a string is provided.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 812
def where(*criteria) criteria.inject(clone) do |query, criterion| if criterion.nil? raise Errors::CriteriaArgumentRequired, :where end # We need to save the criterion in an instance variable so # Modifiable methods know how to create a polymorphic object. # Note that this method in principle accepts multiple criteria, # but only the first one will be stored in @criterion. This # works out to be fine because first_or_create etc. methods # only ever specify one criterion to #where. @criterion = criterion if criterion.is_a?(String) js_query(criterion) else expr_query(criterion) end end.reset_strategies! end
#with_size(criterion) ⇒ Selectable
This method is named #with_size not to conflict with any existing #size method on enumerables or symbols.
Add a $size selection for array fields.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 718
def with_size(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :with_size end typed_override(criterion, "$size") do |value| ::Integer.evolve(value) end end
#with_type(criterion) ⇒ Selectable
vurl.me/PGOU contains a list of all types.
Adds a $type selection to the selectable.
# File 'lib/mongoid/criteria/queryable/selectable.rb', line 744
def with_type(criterion) if criterion.nil? raise Errors::CriteriaArgumentRequired, :with_type end typed_override(criterion, "$type") do |value| ::Integer.evolve(value) end end