如何为表格制作通用通用视图?

How to make universal generic view for tables?

我想为 table 创建一个视图辅助方法,我可以在其中传递任何 object 和 header object,它会轻松映射 headers 和数据库中的数据并创建一个 table。 我想让它通用,这样我就可以在项目的任何地方使用它。 我尝试使用 content_tag 但不够成功。 我看到很多关于堆栈溢出的答案,但没有一个能满足我的兴趣。

感谢任何帮助。 这是我尝试做的,专门针对附件模型。

 def display_doc_table(columns, collection = {})

   thead = content_tag :thead do
     content_tag :tr do
      columns.collect {|column|  concat content_tag(:th,column[:display_name])}.join().html_safe
     end
   end

   tbody = content_tag :tbody do
    collection.collect { |elem|
      if elem.is_visible_to_all or (can? :manage, Attachment) 
        content_tag :tr do
          columns.collect { |column|
              concat content_tag(:td, link_to(elem.attributes[column[:name]], elem.document.url, data: { :colorbox => true, :colorbox_height => '700px', :colorbox_width => '700px', :colorbox_iframe => true }) , class: "remove_underline")
              concat content_tag(:td, link_to("Edit ",edit_attachment_path(elem)))
              concat content_tag(:td,"|")
              concat content_tag(:td, link_to(" Delete",attachment_path(elem), data: {method: :delete, confirm: "Are you sure?"}))        
      }.to_s.html_safe
    end
  end
    }.join().html_safe
   end

   content_tag :table, thead.concat(tbody)

end

但是我想要像我将传递@header这样的东西,它将包含散列和@docs或@user,即模型的object。 它将检查模型中是否有动作 url 如果是,它将把动作附加到 @header 并将继续创建一个名为 Action 的列,该列将定义动作 url就像编辑和删除一样,它只会根据@header.

显示table数据

像这样:

def table_for(@header, @user)
 if object has action url in it then
   append the action to header
create a table data as per header along with column Action or
just create a table data as per header.  
end

谢谢!

对于功能齐全的方法,可以使用 gem(如 datagrid),它们可以处理您所描述的内容以及排序、过滤等附加功能。除非您有充分的理由重新发明轮子,我建议研究这些替代方案(Google "rails data tables" 或类似的东西)。

对于基本方法,您可以利用 ActiveRecord 的反射能力:

def table_for(relation, columns = relation.columns.map(&:name))      
  headers = columns.map(&:titleize).map {|h| "<th>#{h}</th>"}
  header_row = "<tr>#{headers.join}</tr>"

  rows = relation.all.map do |row|
    cells = columns.map {|attr| row.send(attr)}.map {|v| "<td>#{v}</td>"}
    "<tr>#{cells.join}</tr>"
  end

  "<table>#{[ header_row, rows ].flatten.join('\n')}</table>"
end

# view.html.erb

<%= h table_for(User) %>

但如您所知,这是非常基本的,在任何生产环境中都不是很有用。