Rails仪表板设计:每个div一个控制器动作

时间:2009-05-26 01:05:54

标签: ruby-on-rails ruby model-view-controller dashboard

我正在实施仪表板作为相对Rails新手(更多的是基础设施人员)。仪表板将包含多个页面,每个页面将包含多个图表/表格等。对于模块化,我希望它能够尽可能简单地添加新图表或更改数据视图。

假设一个页面有5个不同的图表。我可以让控制器执行5次单独的数据查找,将所有相关数据保存在实例变量中,并渲染5个部分,每个部分触摸数据的子集。但似乎更模块化的是有一个“索引”控制器动作,其渲染具有一堆div,并且对于每个div,还有另一个控制器动作执行数据查找并且具有相关视图部分负责管理该数据的视图在div内。

因此,如果我要显示包含两个图表的网站信息中心页面,website/index将使用website/graph1website/graph2查找每个图表的数据,然后_graph1.html.erb_graph2.html.erb将使用控制器数据填写div "graph1""graph2"等。

这是正确的设计,如果是这样,最简单的方法是什么?我使用remote_function:action => "graph1"进行近似来填写div,但我并不是百分之百满意。我怀疑我错过了Rails会为我做的更容易的事情。

4 个答案:

答案 0 :(得分:10)

版本1:

我在制作中实际使用的简单方法:iframe。

大多数情况下,您实际上并不关心页面是否一次性呈现并直接来自服务器,实际上它最好是交错加载。

如果您只是将iframe src添加到控制器的show动作中,那么您将拥有一个非常简单的解决方案,不需要直接的跨控制器交互。

临:

  • 死得轻松
  • 适用于现有的节目动作等
  • 甚至可能更快,取决于并行与顺序请求和内存负载等的节省

缺点:

  • 您无法轻松将页面与任何内容一起保存
  • iframe将突破主机页面的javascript命名空间,所以如果他们需要,你可能需要给他们自己的简约布局;他们也无法影响iframe外的周边页面
  • 可能会更慢,具体取决于ping时间等
  • 潜在的n + 1效率错误,如果您在页面上有许多此类模块

版本2:

使用JS调用同样的东西用div替换div:àla:

<div id="placeholder">
<%= update_page {|page| page['placeholder'].replace with some partial call here } %>

与上述相同,除了:

临:

  • 不会将其锁定为iframe,因此共享JS上下文等
  • 允许更好地处理失败案例

缺点:

  • 需要JS和占位符div;更复杂一点

版本3:

召唤一大堆部分人。一旦你谈论了各个模块都有大量设置逻辑的仪表板之类的东西,这样做会很复杂。

有各种方法可以通过将这些东西变成'mixins'之类来解决这个问题,但是IMO它们有点像kludgy。

ETA:通过mixins来实现它的方法是创建一个本质上是库文件来实现模块控制器的设置功能,包括使用调用'em'的地方,并调用它们。

然而,这有缺点:

  • 您必须知道哪些顶级控制器操作会导致包含这些模块的页面(如果这些模块真的是可能出现的小部件,例如依赖于用户偏好,那么您可能不容易这些操作)
  • 它并不真正充当完全成熟的控制器
  • 它仍然混合了许多逻辑,你的控股事物需要知道它所持有的东西
  • 你不能轻易将它分隔成自己的控制器,因为它需要在库类型的文件/ mixin中

可以从另一个控制器调用一个控制器中的方法。然而,这是屁股上的一个主要痛苦,也是一个主要的问题。你应该考虑这样做的唯一一次是:a)他们在自己的权利中都是独立必要的控制者,b)它必须完全在后端运作。

我必须这样做一次 - 主要是因为重构它的原因甚至更加痛苦 - 而且我保证除非你必须这样做,否则你不想去那里。

摘要

最好的方法IMHO是第一个,如果你有足够复杂的东西,他们需要重要的设置 - 一个简单的iframe显示模块,传递一个参数告诉它使用超极简主义布局(只是CSS + JS标题),因为它是没有显示为自己的页面。

这允许你保持事物完全独立,功能或多或少,就好像它们是完全正常的控制器(布局设置除外),保留正常路线等。

如果您不需要重要的设置,那么只需使用partials,并将他们需要的任何内容作为局部变量传递。如果你遇到像n + 1效率错误这样的问题,这将开始变得脆弱,但是......

答案 1 :(得分:7)

为什么不试试Apotomo,这是Rails的有状态小部件:

A tutorial how to build a simple dashboard

答案 2 :(得分:1)

您可以使用

来实现这一目标

render_output = render:action =&gt; “graph2”

但我个人可能会将代码包装在共享帮助程序中,或者在lib目录下编写自己的“lib”,以便将代码重用于共享模板。请记住,除非您更改route.rb文件,否则任何定义的公共方法都可以通过

访问

/控制器/动作/:ID

还要记得关闭该功能的布局:layout =&gt; nil(或在控制器布局“graph”的顶部指定,:except =&gt; [“graph2”]

干杯

基督教

答案 3 :(得分:0)

我不知道有任何特殊的Rails技巧可以实现这一点,而不会像你概述的那样使用AJAX。

获得所需模块化的最简单方法是将控制器代码的这些部分放入单独的方法(例如set_up_graph1_dataset_up_graph2_data等),您只需从{{1动作来设置视图的变量。

如果您希望将这些方法用于多个控制器,则可以将这些方法放入index

作为旁注,在早期,Rails 曾经曾经有一个名为'components'的功能,它可以让你完全按照你的要求去做,而不必使用AJAX。从您的角度来看,您可以直接呈现另一个控制器操作。但是,出于性能和设计理念的原因,此功能已被删除。