Rails:“渲染模板”实际上意味着啥

Posted

技术标签:

【中文标题】Rails:“渲染模板”实际上意味着啥【英文标题】:Rails: What does it actually mean to "render a template"Rails:“渲染模板”实际上意味着什么 【发布时间】:2012-01-26 15:17:40 【问题描述】:

由于作者在我正在阅读的书中谈论它的方式,我对“渲染”“模板”的想法有些困惑。

我最初对“渲染模板”的理解是,它意味着 Rails 提供在屏幕上查看/呈现给查看者的内容(以呈现部分内容的方式)但我正在阅读的书似乎使用“渲染模板”的概念也意味着其他东西。让我在上下文中解释一下

这本书(rails 3 in action)使用传统的layouts/application.html.erb 文件设置页面布局,然后“让步”到不同的视图页面,例如views/tickets/show.html.erb 向屏幕添加更多内容。这很简单..

在这个视图views/tickets/show.html.erb 中,有一个局部渲染(这也是一个简单的概念)。

<div id='tags'><%= render @ticket.tags %></div>

现在在这个部分中,使用 ajax 调用“tags_controller.rb”中的“remove”方法,该方法旨在允许授权用户从我们的模拟项目中的“ticket”中删除“tag”管理应用。

<% if can?(:tag, @ticket.project) || current_user.admin? %>
    <%= link_to "x", remove_ticket_tag_path(@ticket, tag),
      :remote => true,
      :method => :delete,
      :html =>  :id => "delete-#tag.name.parameterize"  %>
  <% end %>

现在这里是标签控制器中的“删除”操作(它将标签与数据库中的票证解除关联)...

def remove
    @ticket = Ticket.find(params[:ticket_id])
    if can?(:tag, @ticket.project) || current_user.admin?
      @tag = Tag.find(params[:id])
      @ticket.tags -= [@tag]
      @ticket.save
    end
  end
end

在这个删除动作的最后,作者最初包含了render :nothing =&gt; true,但后来他修改了这个动作,因为正如他所说,“你会得到它来渲染一个模板。” 这就是我感到困惑的地方

他拿到这个action去渲染的模板是“remove.js.erb”,里面只有一行jquery,目的是把页面中的“标签”(即用户给的标签)去掉在屏幕上看到)现在它已与数据库中的票证解除关联。

$('#tag-<%= @tag.name.parameterize %>').remove();

当我阅读“渲染模板”时,我希望应用程序将内容插入页面,但控制器中的“删除”操作渲染的模板只调用了一个从页面中删除一个元素的 jquery 函数。

如果“模板”被“渲染”,我希望删除另一个模板(以便为新模板腾出空间),或者我希望内容以部分被渲染。您能否澄清在此问题中使用 jquery 的情况下“渲染”“模板”时实际发生了什么?它实际上是在用户面前放置一个新页面吗(我希望呈现某种物理页面)

【问题讨论】:

【参考方案1】:

你快到了!渲染模板确实总是关于生成内容,但是对于内容的更广泛的描述。它可能是一段 html,例如获取新项目的 ajax 调用可能会生成一些描述新项目的 html,但不一定非要如此。

模板可能会生成 javascript,就像在您的第二个示例中那样。就我个人而言,我试图避免这种情况,而是将 JSON 传递回客户端,让客户端 js 执行所需的工作。

您可能执行的另一种渲染类型是生成一些 JSON。 API 通常会这样做,但您也可以在普通页面上这样做。例如,与其渲染一些 javascript 来删除标签 x,不如渲染 json

 to_delete: "tag-123"

然后让您的 jQuery 成功回调使用该有效负载来知道要从 DOM 中删除哪个元素,方法是将其包含在您的 application.js 文件中

$('a.delete_tag').live('ajax:success', function(data)
  var selector = '#' + data.to_delete;
  $(selector).remove()

(假设您的删除链接具有“delete_tag”类) 像这样渲染 JSON 根本不是模板,因为您通常会通过

render :json => :to_delete => "tag-#@tag.name.parameterize"

虽然我想你可以为此使用 erb 模板(但我无法想象为什么)。

【讨论】:

这很有趣。你能澄清一下吗。我没有使用模板,而是尝试渲染 :js => "$('#tag-').remove();" .这行得通,但是它需要刷新页面才能删除标签,但是如果我将此 jquery 放在模板中,则不需要刷新页面即可删除标签。当您编写“让您的 jQuery 成功回调使用该有效负载来知道要从 DOM 中删除哪个元素”时,这是否允许我使用 render :js 而不必刷新页面?你能解释/展示如何吗?提前谢谢你。 我怀疑如果你渲染 js,它期望正常的 ruby​​ 样式插值 (#) 而不是 erb 标签【参考方案2】:

我的理解是 js.erb 是通过执行其中的 javascript 函数来“渲染”的。经常会执行以下操作:

jQuery(document).ready(function() 
    jQuery('#element').html('<%= escape_javascript(render pages/content) %>');
);

【讨论】:

谢谢,所以在这个函数中,页面/内容被放在了 html 元素中? 是的,其实html.erb正常渲染的内容可以这样渲染【参考方案3】:

http://guides.rubyonrails.org/layouts_and_rendering.html 有一个非常简洁的渲染概述,它可能会有所帮助,因为它还介绍了 ActionController::Base#render 方法的细节以及使用 render :nothing 时在幕后发生的事情(例如)。渲染但也可以用于文件或内联代码——不仅仅是传统意义上的“模板”。

【讨论】:

我查看了那个页面,特别是 2.2.10,它提供了有关直接从控制器操作渲染 js 的说明,例如 render => "alert('Hello Rails');"因此,只是为了尝试一下,我将 jquery 从模板 remove.js.erb 向上移动到控制器中,如 2.2.10 中所述,但是当我单击元素时,我需要刷新页面才能进行删除.如果我在 remove.js.erb 中有 jquery,它实际上会删除元素而不需要刷新页面。相似但不同。

以上是关于Rails:“渲染模板”实际上意味着啥的主要内容,如果未能解决你的问题,请参考以下文章

Flask: 渲染模板

AngularJS地址栏变化为啥不跳转到页面

模板渲染

Django模板渲染

Python Flask Jinja - 扩展模板时扩展/渲染模板

车把部分与渲染与模板