[英]Model Inheritance in Ruby on Rails 3
Please help a newbie to choose the best way to implement inheritance in RoR3. 请帮助新手选择在RoR3中实现继承的最佳方法。 I have:
我有:
-Person (address fields, birthdate, etc.) -Player, inherits from Person (position, shoe_size, etc.) -Goalkeeper, inherits from Player (other specific fields related to this role)
I think that Single Table Inheritance is a bad solution, because there will be a lot of null fields in the table created. 我认为“单表继承”是一个不好的解决方案,因为在创建的表中将有很多空字段。 What is the best way to do this?
做这个的最好方式是什么? Use polymorphic associations (with has_one?)?
使用多态关联(与has_one吗?)? Use belongs_to/has_one (but then how to show in the Player views the fields of Person too?)?
使用belongs_to / has_one(但是又如何在“播放器”视图中显示“人”的字段?)? Don't implement inheritance?
不实现继承吗? Other solutions?
其他解决方案?
While I think STI is probably the approach I would use for this, one other possibility, if you want to avoid a lot of NULL
attributes, is to add a column other_attributes
to your Person model that will store a Hash
of attributes. 尽管我认为STI可能是我要使用的方法,但如果要避免使用许多
NULL
属性,另一种可能的方法是在Person模型中添加一列other_attributes
,该列将存储属性的Hash
值。 To do this, add a text
column to the people
table: 为此,将
text
列添加到people
表:
def self.up
add_column :people, :other_attributes, :text
end
Then make sure the attribute is serialized in the model. 然后,确保该属性在模型中已序列化。 And you may want to write a wrapper to make sure it's initialized as an empty
Hash
when you use it: 而且,您可能想编写一个包装器,以确保在使用它时将其初始化为空的
Hash
:
class Person < ActiveRecord::Base
serialize :other_attributes
...
def other_attributes
write_attribute(:other_attributes, {}) unless read_attribute(:other_attributes)
read_attribute(:other_attributes)
end
end
Then you can use the attribute as follows: 然后,您可以使用以下属性:
p = Person.new(...)
p.other_attributes #=> {}
pl = Player.new(...)
pl.other_attributes["position"] = "forward"
pl.other_attributes #=> {"position" => "forward"}
One caveat with this approach is that you should use strings as keys when retrieving data from other_attributes
, as the keys will always be strings when the Hash
is retrieved from the database. 使用此方法的一个注意事项是,从
other_attributes
检索数据时,应将字符串用作键,因为从数据库中检索Hash
时,键始终是字符串。
I suggest STI. 我建议性传播感染。 An alternative solution is to use a document store like mongodb, or use the activerecord store http://api.rubyonrails.org/classes/ActiveRecord/Store.html .
另一种解决方案是使用诸如mongodb的文档存储,或使用activerecord存储http://api.rubyonrails.org/classes/ActiveRecord/Store.html 。 If you have a postgress database look at his HStore column http://rubygems.org/gems/activerecord-postgres-hstore .
如果您有一个postgress数据库,请查看他的HStore列http://rubygems.org/gems/activerecord-postgres-hstore 。
Another option is PostgreSQL table inheritance. 另一个选择是PostgreSQL表继承。 http://www.postgresql.org/docs/8.1/static/ddl-inherit.html
http://www.postgresql.org/docs/8.1/static/ddl-inherit.html
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.