我有一个基类Place
和使用STI约定的多个子类。我有一个单独的模型Post
,该模型belongs_to
是Place
的子类之一:
class Place < ApplicationRecord
end
class SubPlace < Place
has_many :posts, class_name: "SubPlace", foreign_key: "sub_place_id"
end
class Post < ApplicationRecord
belongs_to :sub_place, class_name: "SubPlace", foreign_key: "sub_place_id"
end
可以使用Rails控制台保存新的Post
记录,但是在尝试为特定Posts
查找SubPlace
时遇到以下错误:
ActiveRecord::StatementInvalid (PG::UndefinedColumn: ERROR: column places.sub_place_id does not exist)
是否可以进行这项工作,或者我的关联必须仅与基类相关?
添加的架构:
create_table "posts", force: :cascade do |t|
t.string "title"
t.bigint "sub_place_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["sub_place_id"], name: "index_posts_on_sub_place_id"
end
create_table "places", force: :cascade do |t|
t.string "name"
t.string "type"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
答案 0 :(得分:1)
ActiveRecord :: StatementInvalid(PG :: UndefinedColumn:ERROR:列 place.sub_place_id不存在)
您在SubPlace
中的关联无效。您应该将其重写为
class SubPlace < Place
has_many :posts
end
答案 1 :(得分:1)
处理关联和STI的更好方法是将关联设置为基类:
class Place < ApplicationRecord
end
class SubPlace < Place
has_many :posts, foreign_key: 'place_id', inverse_of: 'place'
end
class AnotherKindOfPlace < Place
has_many :posts, foreign_key: 'place_id', inverse_of: 'place'
end
class Post < ApplicationRecord
belongs_to :place
end
由于Post
不知道或不在乎有不同种类的地方,因此这使事情变得简单明了。当您访问@post.place
时,ActiveRecord会读取places.type
列,并将实例化正确的子类型。
如果基本Post类也具有关联,则只需将其编写为:
class Place < ApplicationRecord
has_many :posts, foreign_key: 'place_id', inverse_of: 'place'
end