2017-10-20 100 views
1

看起来像我的表单执行的操作 - 发送正确的值,但不保存在数据库中。 Check_box_tag需要从enum(我用枚举,因为我使用的选择字段相同的数据):Rails check_box_tag - 将数组保存到Postgres中

class UserProfile < ApplicationRecord 
    enum locations: { Kursenai: 0, Papiskes: 1, Versiai: 2 } 

而在的form_for:

<% UserProfile.locations.each do |key, val| %> 
    <%= f.label key %> 
    <%= check_box_tag('user_profile[locations][]', val, false, id: val) %> 
<% end %> 

但不能更新:

“ [“0”,“1”]'不是有效位置

Postgres:

t.integer "locations", array: true 

因此,我认为,因为行类型是integer失败,但这样的:

<%= check_box_tag('user_profile[locations][].to_i', val.to_i, false, id: val) %> 

删除错误,但用户领域:locations仍然nil。我错过了什么?

强PARAMS:

..permit(locations: []) 

附:如果您认为这可以以更好的方式完成 - 请随时展示。

回答

1

为什么?

因为“[‘0’,‘1’]”被认为是字符串,它不是在枚举即提到amoung值你 0,1,2

U可以不能直接作为实现它枚举要求字段类型保存单个值。但在 您的情况下它的数组。

如何存档?

class UserProfile < ApplicationRecord 
    # value should store as array not as string. 
    serialize :locations, Array 

    # define your own enum by creating static var.U can use Array or Hash structure. 
    # Here I am using Hash. 
    # ENUM_LOCATIONS = ["Kursenai", "Papiskes", "Versiai"] 
    ENUM_LOCATIONS = {"Kursenai": 0, "Papiskes": 1, "Versiai": 2} 


    # Now modify you getter little bit to return enumed values 
    def locations 
    res = [] 
    self[:locations].each{|v| ENUM_LOCATIONS.is_a?(Array) ? res << ENUM_LOCATIONS[v.to_i] : res << ENUM_LOCATIONS.key(v.to_i).to_s} 
    res  
    end 

end 

就是这样

1

你为什么使用枚举?我认为最好创建一个新的模型位置并通过HABTM关系与UserProfile连接。它将满足数据库规范化并更易于使用。

编辑:

class UserProfile < ApplicationRecord 
    has_and_belongs_to_many :locations 
end 

class Location < ApplicationRecord 
    has_and_belongs_to_many :user_profiles 
end 

,你需要创建3个位置记录

Location.create(name: 'Kursenai') 
Location.create(name: 'Papiskes') 
Location.create(name: 'Versiai') 

使用任何非标准的查询,联接。你可以建立像这里的一种形式: Rails 4 - checkboxes for has_and_belongs_to_many association

Multiple select issue with a HABTM relationship using Rails 4

+0

然后呢?我仍然会在那里散列enum –

+0

@ J.D。解释我的观点更好一点 – kolas

+0

谢谢,@ kolas,但我看不出有这样的严重理由。枚举是更轻,在这种方法中,我会创建许多静态对象,而在课堂上包括枚举看起来更轻的工作。我现在正在处理简单的字符串数组,并对其进行哈希处理,因为之后我可能会删除或向其添加项目。但我想我一定会用这种方式,如果我的字符串数组将成为对象数组。感谢您的信息。如果我错了,请纠正我 –

0

看起来有一些命名冲突。我的猜测是,因为我在模型locations中声明为散列,并且稍后允许使用与数组同名的强params属性。这只是我的猜测。我改名枚举 - enum locs:和形式 - UserProfile.locs.each和看起来像它正常工作:

class UserProfile < ApplicationRecord 
    enum locs: { Kursenai: 0, Papiskes: 1, Versiai: 2 } 

形式:

<% UserProfile.locs.each do |key, val| %> 
    <%= f.label key %> 
    <%= check_box_tag('user_profile[locations][]', val, false, id: val) %> 
<% end %> 

附:但如您所见,现在我将数据保存为string[] - ["1", "2"],即使我的db行是 - t.integer "locaions", array: true。想知道为什么Postgres允许将字符串数组写入此行? 不得不重启服务器