在Rails 3.2应用程序中,我正在尝试添加一个从外部API调用获取其数据的选择字段。此数据作为哈希数组返回:
[{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
如何使用此数据构建类似于以下内容的选择字段:
<select>
<option value="001"> NameA </option>
<option value="002"> NameB </option>
</select>
编辑:
感谢下面的建议,我尝试了以下内容:
A:
<%= select_tag 'model[field]', options_from_collection_for_select(@hash, :id, :name) %>
给出错误:
undefined method `name' for {"name"=>"NameA", "id"=>"001"}:Hash
B:
<%= select_tag 'model[field]', options_from_collection_for_select(@hash) %>
修复错误但生成错误的标记
<option value="{"name"=>"NameA", "id"=>"001"}"> {"name"=>"NameA", "id"=>"001"}</option>
所以我认为我的问题是正确地格式化哈希数组,而且我对操纵哈希数组的知识不足以解决如何做到这一点。
除非我完全关注这个方向,否则我认为这个问题的关键是重新格式化这个问题顶部的数组给出:
{"NameA" =>"001", "NameB" =>"002"}
这甚至可能吗?如果是这样,怎么样?
答案 0 :(得分:38)
如果你有这样的哈希数组:
@people = [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
您可以options_for_select
使用collect
方法使用{{3}}方法:
= select_tag "people", options_for_select(@people.collect {|p| [ p['name'], p['id'] ] })
完成了: - )。
答案 1 :(得分:11)
只在一个命令中执行此操作的更好方法:
<%= select_tag "model[field]", options_for_select(@array_of_hashes.map { |obj| [obj['name'], obj['id']] }) %>
使用您的示例哈希:
irb> @array_of_hashes = [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
=> [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
irb> @array_of_hashes.map { |obj| [obj['name'], obj['id']] }
=> [["NameA", "001"], ["NameB", "002"]]
答案 2 :(得分:2)
对我来说,选择哈希的最简单方法是:
哈希:
REVISION_TYPES={"S"=>"Stock", "T"=>"Traducción"}
表格形式:
select_tag(:revision_type,options_for_select(REVISION_TYPES.invert.to_a))
答案 3 :(得分:1)
您可以将options_for_select
用于此目的。它需要一个二维数组。您可以像这样转换哈希:
data = [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
data_for_select = data.each { |hash| [hash['name'], hash['id']] }
options_for_select(data_for_select)
作为options_from_collection_for_select
的旁注,它与对象结合使用。它遍历对象并发送标签的消息和id的消息。
答案 4 :(得分:0)
好的,我最终找到了一个有效的解决方案,尽管它可能不是最好的。
$ @array_of_hashes = [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
=> [{"name"=>"NameA", "id"=>"001"}, {"name"=>"NameB", "id"=>"002"}]
$ @formatted_array_of_hashes = @array_of_hashes.each.map{ |h| { h["name"] => h["id"] }}
=> [{"NameA" => "001"}, {"NameB" => "002"}]
$ @merged_hash = Hash[*@formatted_array_of_hashes.map(&:to_a).flatten]
=> {"NameA" => "001", "NameB" => "002"}
然后我就可以创建一个选择字段
<%= select_tag 'model[field]', options_for_select(@merged_hash) %>
生成正确的标记
<select>
<option value="001">NameA</option>
<option value="002">NameB</option>
</select>
有点费解,但它的工作。我欢迎任何改进。
答案 5 :(得分:0)
我不确定为什么,但没有一个答案对我有用。也许是因为Rails 5,所以我自己想出来,我很乐意分享。 它现在很漂亮,但运作良好。
这是一个来自外部API(Pipedrive)的哈希数组,我想与用户的表关联:
这是我的形式:
<%= form.collection_select(:id_user_pipedrive, Owner.all_id_name, :id, :name, :include_blank => '') %>
这是我的假模型:
UserPipedrive = Struct.new(:id, :name)
def self.all_id_name
all["data"].map { |d| UserPipedrive.new(d["id"],d["name"]) }
end
希望它有所帮助。