Rails STI 和“类型”字段

问题描述

我参考了一些资料来弄清楚如何在 Ruby On Rails 中实现单表继承。我使用的具体示例仅涉及两种类型的用户RegularUserAdmin,它们继承自 User 模型,该模型具有一些类似 username 的字段。 User 模型中的字段之一是用户的类型,它只是一个字符串字段。我的问题是:当我简单地在名为“type”的字符串字段中指定它时,Rails 如何连接要使用的子类上的点,该字段可能只是一个与子类无关的字符串字段?如果 type 字段符合我的想法,是否意味着它是一个专门为 RoR 中的 STI 保留的关键字? 任何指针将不胜感激。 这是我的用户迁移文件(没什么特别的):

class createusers < ActiveRecord::Migration[6.1]
  def change
    create_table :users do |t|
      t.string :username
      t.string :email
      t.string :type

      t.timestamps
    end
  end
end

解决方法

Rails 有根据类型名infer the corresponding class 的方法

所以如果在你的数据库中你有一个记录

User,id: 5,type: 'user_admin'

然后你User.find(5)

Rails 将查看类型值 'user_admin' 并通过基本上执行 ActiveSupport::Dependencies.constantize("user_admin") 为您常量化正确的实例 这是一个花哨的名字,表示给我对应于这个字符串的 ruby​​ 类。

在 Rails 中,除了促进 STI 之外,您不应该使用“type”作为列名,因此它确实是一种保留字,如果您的数据库包含不是 AR 类名的任何内容,您将导致代码崩溃在那里。如果您想为列使用名称“类型”,则需要按照说明更改继承列here

,

我认为要回答您的问题是这样的。

当一个表有一个名为 type 的列时,活动记录将启用 STI,无论这是否是您的意图。这就是点如何连接起来的。如果表中的列名为 type,如果不是有意使用 STI,则可能会破坏事情。

执行 type 时不必填写 create 字段的值,活动记录将使用类名填充它。从基类(或任何继承的类)执行 find 将返回 type 列中指定的类的实例。

所有这一切都是通过名为 type 的列的存在而实现的。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...