这简直要把我逼疯了,我觉得我可能错误地使用了嵌入文档。
class User
include MongoMapper::Document
key :name, String
many :businesses
end
class Business
include MongoMapper::EmbeddedDocument
key :name, String
one :address
many :clients
belongs_to :user
end
class Address
include MongoMapper::EmbeddedDocument
key :name, String
belongs_to :business
end
class Client
include MongoMapper::EmbeddedDocument
key :name, String
belongs_to :business
end
我已经创建了一个用户和一个业务,我现在想做的是为业务添加地址,但是我无法做到。
我唯一能想到的就是通过名称或id找到用户,然后循环遍历企业数组,找到符合名称的企业并设置地址…
但老实说,这听起来真的很蹩脚,我认为有一个更优雅的方法。
谢谢
首先,当你嵌入时,你使用embedded_in
而不是belongs_to
。
class Business
include MongoMapper::EmbeddedDocument
key :name, String
one :address
many :clients
embedded_in :user
end
class Address
include MongoMapper::EmbeddedDocument
key :name, String
embedded_in :business
end
class Client
include MongoMapper::EmbeddedDocument
key :name, String
embedded_in :business
end
原因是,在内部,belongs_to
创建了一个复杂的关联代理,为非嵌入式关联做各种数据库交互,而embedded_in
只是创建了_parent_document
方法的别名。belongs_to
仅用于非嵌入关联。
没有办法"很好"地查询嵌入的文档。我认为Mongoid让你假装嵌入的关联就像普通的关联一样是可查询的,但是MongoMapper不喜欢假装。在MongoMapper中,嵌入的文档数组只是一个加了很少糖的Array
。MongoDB可能最终会允许嵌入文档的虚拟集合(这是JIRA的头号问题),我想在这一点上MM的家伙会考虑一些更花哨的东西。
事实上,Ruby的可枚举方法是如此之好,以至于你自己去查找并不是很疯狂。
user = User.find("1234567abc")
user.business.select { |b| b.name == target_name }.each { |b| b.address = new_address }
user.save