gpt4 book ai didi

ruby-on-rails - Rails 5 - 对象关系阻抗以及如何构造多个继承的类/表

转载 作者:行者123 更新时间:2023-12-04 06:28:15 25 4
gpt4 key购买 nike

编辑
我对原文进行了编辑,以使其更容易理解。

我了解对象关系阻抗问题。我了解 Rails STI 和多态性(Rails 方式,它不是真正的 OO 多态性)。我已经阅读了大量关于此的博客和问题,但仍然找不到这个问题的答案。

class Person < ApplicationRecord (ie what was ActiveRecord::Base)
end

class Employee < Person
end

class Customer < Person
end

...多种其他类型的人

现在让我们说“客户”要求扩展系统,并创建一些新东西。让我们称之为一个项目,我们可以将其分配给员工:

好的,让我们使用第三范式创建多对多:
class Project < ApplicationRecord
has_many :assignments
has_many :employees, through: :assignments
end

class Employee < Person
has_many :assignments
has_many :projects, through: :assignments
end

class Assignment < ApplicationRecord
belongs_to :employee
belongs_to :project
end

这行不通。迁移将失败,因为没有名为 Employee 的表可在其上创建外键约束。 STI 意味着“基类”是 People 表。

两个问题:

1 你是怎么解决这个问题的? (为此,您可能还想加入 here )

2 您如何为项目(应包括员工,但不包括人员或人员的其他子类型)正确创建序列化数据?
ProjectSerializer < ActiveModelSerializers

has_many :employees
has_many :employees, through: :assignments

end

不会工作,所以你必须连载人。

更新

在迁移中,我创建了 Project 和 Assignment 表(Person 已经存在)。

所以现在数据库有这些表:
Project
Person
Assignment

Assignment 有两个外键(引用 Person,因为这是存在的表,而不是 Employee):
person_id   
project_id

每次我尝试创建作业时,都会抛出此错误,这当然是我所期望的:
ActiveModel::UnknownAttributeError (unknown attribute 'employee_id' for Assignment.)

根据 Rails 文档 ( section 4.1.2.5 ) 以及我可以在任何地方找到的针对这种情况的所有其他答案的解决方案是告诉 Rails foreign_key 是什么。像这样:
class Assignment < ApplicationRecord
belongs_to :employee, foreign_key: "person_id"
belongs_to :project
end

但是我发现的每个示例(甚至在文档中)都假设没有继承——所有模型都继承自 ActiveRecord:Base(或 Rails 5 中的 ApplicationRecord)。

即使我明确地告诉 Rails 分配表有一个名为“person_id”的外键,它保存了员工的 id,它仍然找不到它。

最后我尝试了这个(感谢@camonz 的回答)
class Assignment < ApplicationRecord
belongs_to :person, foreign_key: "person_id", foreign_type: "employee"
belongs_to :project
end

同样的错误。

这真的是 Rails 无法处理的模型设置吗?

这是 Rails 日志:
I, [2016-09-22T22:54:55.088466 #12182]  INFO -- : Started POST "/assignments" for ::1 at 2016-09-22 22:54:55 +0200
I, [2016-09-22T22:54:55.095768 #12182] INFO -- : Processing by AssignmentsController#create as JSON
I, [2016-09-22T22:54:55.096007 #12182] INFO -- : Parameters: {"data"=>{"attributes"=>{"status"=>"pending"}, "relationships"=>{"project"=>{"data"=>{"type"=>"projects", "id"=>"601"}}, "employee"=>{"data"=>{"type"=>"employees", "id"=>"143"}}}, "type"=>"assignments"}, "assignment"=>{}}
I, [2016-09-22T22:54:55.098032 #12182] INFO -- : {:status=>"pending", :project_id=>"601", :employee_id=>"143"}
I, [2016-09-22T22:54:55.117411 #12182] INFO -- : Completed 500 Internal Server Error in 21ms (ActiveRecord: 8.8ms)


F, [2016-09-22T22:54:55.119116 #12182] FATAL -- :
F, [2016-09-22T22:54:55.119246 #12182] FATAL -- : ActiveModel::UnknownAttributeError (unknown attribute 'employee_id' for Assignment.):
F, [2016-09-22T22:54:55.119283 #12182] FATAL -- :
F, [2016-09-22T22:54:55.119313 #12182] FATAL -- : app/controllers/assignments_controller.rb:18:in `create'

最佳答案

  • 在迁移时,删除 addressses 上的 FK 约束。 table 。在子类上重新定义 has_many关系并指定 :foreign_key & :foreign_type .
  • 在您的分配序列化程序上,指定 belongs_to :employee , AMS 应该正确处理它。
    也看看:source:source_type has_many 的选项协会。
  • 关于ruby-on-rails - Rails 5 - 对象关系阻抗以及如何构造多个继承的类/表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39524488/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com