module Mongoid::Matchable

This module contains all the behavior for ruby implementations of MongoDB selectors.

@since 4.0.0

Constants

MATCHERS

Hash lookup for the matcher for a specific operation.

@since 1.0.0

Private Class Methods

extract_attribute(document, key) click to toggle source

Extract the attribute from the key, being smarter about dot notation.

@api private

@example Extract the attribute.

strategy.extract_attribute(doc, "info.field")

@param [ Document ] document The document. @param [ String ] key The key.

@return [ Object ] The value of the attribute.

@since 2.2.1

# File lib/mongoid/matchable.rb, line 143
def extract_attribute(document, key)
  if (key_string = key.to_s) =~ /.+\..+/
    key_string.split('.').inject(document.as_document) do |_attribs, _key|
      if _attribs.is_a?(::Array)
        _attribs.map { |doc| doc.try(:[], _key) }
      else
        _attribs.try(:[], _key)
      end
    end
  else
    if document.is_a?(Hash)
      document[key_string]
    else
      document.attributes[key_string]
    end
  end
end
matcher(document, key, value) click to toggle source

Get the matcher for the supplied key and value. Will determine the class name from the key.

@api private

@example Get the matcher.

document.matcher(:title, { "$in" => [ "test" ] })

@param [ Document ] document The document to check. @param [ Symbol, String ] key The field name. @param [ Object, Hash ] The value or selector.

@return [ Matcher ] The matcher.

@since 2.0.0.rc.7

# File lib/mongoid/matchable.rb, line 111
def matcher(document, key, value)
  if value.is_a?(Hash)
    matcher = MATCHERS[value.keys.first]
    if matcher
      matcher.new(extract_attribute(document, key))
    else
      Default.new(extract_attribute(document, key))
    end
  else
    case key.to_s
      when "$or" then Or.new(value, document)
      when "$and" then And.new(value, document)
      else Default.new(extract_attribute(document, key))
    end
  end
end

Public Instance Methods

matches?(selector) click to toggle source

Determines if this document has the attributes to match the supplied MongoDB selector. Used for matching on embedded associations.

@example Does the document match?

document.matches?(:title => { "$in" => [ "test" ] })

@param [ Hash ] selector The MongoDB selector.

@return [ true, false ] True if matches, false if not.

@since 1.0.0

# File lib/mongoid/matchable.rb, line 55
def matches?(selector)
  selector.each_pair do |key, value|
    if value.is_a?(Hash)
      value.each do |item|
        if item[0].to_s == "$not".freeze
          item = item[1]
          return false if matcher(self, key, item).matches?(item)
        else
          return false unless matcher(self, key, Hash[*item]).matches?(Hash[*item])
        end
      end
    else
      return false unless matcher(self, key, value).matches?(value)
    end
  end
  true
end

Private Instance Methods

matcher(document, key, value) click to toggle source

Get the matcher for the supplied key and value. Will determine the class name from the key.

@api private

@example Get the matcher.

document.matcher(:title, { "$in" => [ "test" ] })

@param [ Document ] document The document to check. @param [ Symbol, String ] key The field name. @param [ Object, Hash ] The value or selector.

@return [ Matcher ] The matcher.

@since 2.0.0.rc.7

# File lib/mongoid/matchable.rb, line 90
def matcher(document, key, value)
  Matchable.matcher(document, key, value)
end