基于用户表单的动态Active Record Store访问器?

Active Record Store允许您序列化单个单元格内的参数。

class User < ActiveRecord::Base store :options, accessors: [ :option1, :option2, :another_random_option ] end 

现在,所有访问器都在users表的“options”列中序列化。

 u = User.new u.option2 = 'some option' u.option2 # => 'some option' 

这对我的应用程序很有用,因为我必须每天创建许多表单,其中90%的表单是相同的(用户名,爱好,兴趣等),然后10%是无模式(random_option_here,another_random_option_in_another_form) 。 我也从不需要按无架构选项排序。

我做的是我为90%的表单字段创建了1个表,它们始终是相同的,然后我有另一个表,其中包含最后10%的字段(我有另一个表的原因是因为这是belongs_to关系,因此用户可以在此表中有许多行)。

   ...   

现在唯一的问题是每次我在自定义表单中创建一个新字段时,我必须将该参数添加到Active Record Store访问器,否则我会得到一个方法缺失错误。 如果我可以进入并为无模式字段创建尽可能多的View表单并且永远不更新模型中的访问器,那将是很好的。

所以我的问题是:是否有动态添加所有用户提交的自定义字段到访问者数组,这样如果用户提交字段“some_random_option1221”,“another_option_here”然后我不必进入访问者数组并添加那个领域?

谢谢!

使用rails 4和postgresql以下内容适用于我。 通过一些小的调整看起来也可以使用rails 3存储方法。

在给定模型实例拥有的商店哈希中的每个字段键上动态调用store_accessor。 如果您的用户模型具有名为hstore类型的选项的列,那么您可以访问选项哈希。 (在rails 3中,您可以像在问题中的代码中那样调用store方法,以使选项方法有效。)

每当用户界面添加新字段时,创建一个方法来执行此操作。 然后还调用此方法after_initialize,以便从db加载用户将在加载时设置字段名称访问器。 您可能还想调用此方法after_save。

 class User < ActiveRecord::Base after_initialize :add_field_accessors after_save :add_field_accessors def add_store_accessor field_name singleton_class.class_eval {store_accessor :options, field_name} end def add_field_accessors num_fields = options.try(:keys).try(:count) || 0 options.keys.each {|field_name| add_store_accessor field_name} if num_fields > 0 end end 

然后,每个用户实例可以具有不同的store_accessor方法,具体取决于每个用户在该用户的db行的options列中具有的字段。

在您的控制器中,根据您添加/删除/编辑选项的首选用户界面,您可以使用帮助程序方法在用户上构建选项,并从new,create,update等调用它。

 def build_options @user.options = options_hash @user.add_field_accessors end 

在rails 3中,您将调用attr_accessor而不是调用store_accessor。

请注意,您将无法调用User.new(:option_1 =>’some_option_value’),因为User类对象没有访问器方法(因为每个用户实例可能具有不同的属性。)

请查看以下链接: https : //www.ruby-forum.com/topic/113069

如何为动态实例变量设置attr_accessor?