我对如何使多态性与嵌入和 mongoid 8.x 一起工作感到困惑。
class Entity
include Mongoid::Document
embeds_many :custom_fields, as: :item
end
class EmailField
include Mongoid::Document
field :name, type: String
field :value, type: String
embedded_in :item, polymorphic: true
end
class MultivalueField
include Mongoid::Document
field :name
field :value, type: Array
embedded_in :item, polymorphic: true
end
我不明白为什么这不起作用。我期望模型
Entity
嵌入许多不同类型的字段,但它会爆炸
NameError:
uninitialized constant MetadataService::Models::Entity::CustomField
我做错了什么?
Mongoid 不支持
embeds_many
的多态性。相反,您可以使用 inheritance 来嵌入不同类的文档:
class Entity
include Mongoid::Document
embeds_many :items
end
class Item
include Mongoid::Document
embedded_in :entity
field :name, type: String
end
class EmailItem < Item
field :value, type: String
end
class MultivalueItem < Item
field :value, type: Array
end
我使用“Item”而不是“Field”,因为后者在 Mongoid 中具有特殊含义,被视为保留字。您可以使用
embeds_many :items, class_name: 'Field'
来解决此限制,但我想让示例尽可能简单。
用途:
e = Entity.new
e.items << EmailItem.new(name: 'email', value: '[email protected]')
e.items << MultivalueItem.new(name: 'email', value: [1, 2, 3])
e.as_document
#=> {
# "_id"=>BSON::ObjectId('660e7a7e571de609e1c84723'),
# "items"=>[
# {
# "_id"=>BSON::ObjectId('660e7a7e571de609e1c84724'),
# "name"=>"email",
# "value"=>"[email protected]",
# "_type"=>"EmailItem"
# },
# {
# "_id"=>BSON::ObjectId('660e7a7e571de609e1c84725'),
# "name"=>"email",
# "value"=>[1, 2, 3],
# "_type"=>"MultivalueItem"
# }
# ]
# }