I could not find a "standard" way of doing just that, so here are some helper methods I use in a class. (Part of soon-to-come BoxCMS)
This Gist uses Mongoid metadata and reflect_on_all_associations, so it might break for newer versions of mongoid at some point.
Using dot notation queries in mongoid, makes it easy to dig for even the deepest "weird" embedded structures you might have.
Example of query:
» Box::Page.where("rows.boxes.box_items.is_template_object" => false).first
Dot notations in mongodb are a powerful tool, but use it wisely unless you are indexing "more than you should".
Basic usage: Call dot_notation_for_element(embedded_element) to get the dot notation all the way up to the parent document, excluding the parent documents name/embedded name.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# | |
# Get dot notification for the current mongoid element | |
# | |
def dot_notation_for_element(element) | |
return "" if element.nil? | |
dot_notation = dot_notation_for_element_nested(element) | |
if dot_notation.nil? | |
return "" | |
else | |
dot_notation[0] = '' | |
end | |
dot_notation | |
end | |
# | |
# Get dot notification for nested elements (nesting updwards) | |
# | |
def dot_notation_for_element_nested(element) | |
# Get non-nil_embedded_relation | |
p = get_embedded_relation(element) | |
# puts p.inspect | |
if p.nil? | |
return nil | |
else | |
"#{dot_notation_for_element_nested(p[0])}.#{p[1].inverse_of}" | |
end | |
end | |
# | |
# Returns array [p, r], where p is the parent element for the embedded element, and | |
# r is the inverse reflection name | |
# | |
def get_embedded_relation(element) | |
element.reflect_on_all_associations(:embedded_in).each do |r| | |
# puts r.inspect | |
p = element.send(r.name.to_s) | |
return [p, r] unless p.nil? | |
end | |
nil | |
end | |