Thi*_*niz 1 ruby activerecord ruby-on-rails hstore
考虑这个类:
class UsersMigration < ActiveRecord::Migration[5.2]
def change
create_table(:users) do |t|
t.hstore :settings
end
end
end
class User < ActiveRecord::Base
store_accessor :settings, :privileges, :colors
end
Run Code Online (Sandbox Code Playgroud)
执行此查询时:
User.where(privileges: 'Admin')
Run Code Online (Sandbox Code Playgroud)
它会导致此错误:
ActiveRecord::StatementInvalid (PG::UndefinedColumn: ERROR: column users.privileges does not exist)
并且是正确的,因为该列实际上是设置
为了进行查询,我们必须这样做:
User.where("settings->'privileges' = 'Admin'")
Run Code Online (Sandbox Code Playgroud)
如果模型已经显式序列化到 hstore 列,为什么第一个查询不会产生以下 SQL:
SELECT "user".* FROM "users" WHERE (settings->'privileges' = 'Admin')
Run Code Online (Sandbox Code Playgroud)
ActiveRecord 并不是为了真正关心 hstore、json 或数组列的内容而构建的。AR 是围绕包含表和列的关系模型构建的。表中的列对应于模型中的属性。
Hstore、json 和数组类型是相对较新的数据库功能,但并不一定不是多语言的。每个数据库的实现都不同。在 ActiveRecord 中,对这些列的支持实际上是由数据库驱动程序而不是框架本身提供的。
store_accessor只需创建一个 getter/setter 并为模型中的属性设置脏跟踪。它不会“明确告诉”AR hstore 列中存在特定键 - 请记住 AR 不关心 hstore 列的内容。
事实上,我想说,如果您以这种方式使用它,那么这是一个非常明显的迹象,表明您已经成为JSON/hstore 反模式的受害者。