Rails 3 加入 table 和模型命名约定

Rails 3 joins table and model naming conventions

我是 运行 Ruby 2.1.9 和 Rails 3.2.17。

首先,在 Rails 中,我总是假设模型应该几乎总是单一的。我见过像 product_categories_product 这样的模型名称。这很好,在 habtm 情况下,您希望模型与我看到的关系一起工作 instructions_products。这在 Rails 中可能有点道理,但我宁愿将模型命名为 instruction_product。这与名为 instructions_products 的联接 table 关联。

事实上,我非常沮丧,我开始研究 rails 是如何命名事物的,结果发生了什么?很明显,它是一个不错的模型名称,并且对应于正确的 table 名称。但是怎样比较合适呢?

ActiveModel::Naming.singular(InstructionsProducts)

returns instructions_products

已编辑:问题的核心是为什么 InstructionsProducts 是 rails 中的有效模型名称以及为什么我上面的示例解析为单数 'instructions_products'。考虑到 rails 惯例是保持模型名称为单数,这似乎很奇怪。

你的问题我不是很清楚。

根据 Rails 惯例,型号名称为单数并以驼峰式书写,例如 InstructionProduct。每个模型在数据库中匹配 table 相同的单词,小写,以'_'分隔,复数形式。 instruction_products 对于提供的示例。

使用has_many看下面的例子:

class User < ActiveRecord::Base
  has_many :contacts
end

class Contact < ActiveRecord::Base
  belong_to :name
end

user = User.find(1)
user.contacts # returns an array of all the associated objects

执行user.contacts时,联系人不是table姓名。它是集合方法,是 has_many 方法中传递的符号的占位符(请遵循 has_many link 并阅读有关 has_many 的文档)。不过可以使用另一个名称:

class User < ActiveRecord::Base
  has_many :personal_contacts, class_name: 'Contact' #, foreign_key: :contact_id
end

user = User.find(1)
user.personal_contacts

class_name 和 foreign_key 是必需的,因为没有遵循 rails 约定。当使用 has_many :personal_contacts 时,rails 期望 personal_contacts 将 return 一个 PersonalContact.

的数组

在 Ruby 中,您必须以大写单词开头 class 名称,因此无法创建名为 instruction_product 的 class。如果您想提供一个不遵循 Rails 约定的名称,我不建议这样做,您需要通知 rails 关于新的 table 名称:

Class AdminUser
  self.table_name = "users"
end

更新 1:

如您所知,惯例规定模型应声明为单数(class InstructionProduct 而不是 class InstructionsProducts。但这只是一个惯例。当 class 继承自 ActiveRecord::Base,并生成一个sql查询,ActiveRecord将class名称小写,用_分隔单词,转换为复数名称并用作table名称(主要是rails 使用 InstructionsProducts.model_name.plural 其中 returns instructions_products).

您假设单数实际上将名称翻译为单数,即使它是以复数形式书写的,但事实并非如此。它假定您使用的是约定,并且主要是 returns class 名称加下划线。

查看 rails 源代码(ActiveModel::Name), ActiveSupport::Inflector.underscore seems to be used (I just did a very superficial investigation, I have to admit). You can see how underscore 在文档中工作。