You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Rails中yield与content_for异常:yield :filters仅在默认yield后生效?

这确实是Rails的正常行为,我来帮你理清楚原因和解决办法

首先,问题核心在于**content_for的执行时机**:当你把content_for :filters写在局部视图的渲染块里时,这段代码只有在默认的yield被执行的时候才会运行。也就是说:

  • 当你先调用yield :filters再调用默认yield时,content_for :filters还没被执行,Rails还没存储这个区块的内容,自然输出为空;
  • 而当你先调用默认yield时,块里的content_for :filters会被执行,内容被存储起来,之后的yield :filters就能正确输出内容了。

哪怕你换成<%= content_for :filters %>也没用,因为本质上yield :xxx和content_for :xxx(不带块)都是读取已存储的内容,前提是content_for :xxx的块已经被执行过。


解决办法有两种,看你更偏好哪种:

方法1:把content_for :filters移到渲染块外面

直接在调用局部视图之前先执行content_for :filters,这样无论局部视图里的yield顺序如何,内容都已经被存储好了:

<% content_for :filters do %>
  <h2> Content for Filters </h2>
<% end %>
<%= render 'layouts/sub_header' do %>
  <h2> Content For Yield </h2>
<% end %>

方法2:在局部视图里先捕获默认yield的内容

通过capture方法先执行默认yield的内容(这样里面的content_for会被触发),再按你想要的顺序输出:

# layouts/_subheader.html.erb
<div class="subheader">
  <%# 先捕获默认yield的内容,触发里面的content_for %>
  <% default_content = capture { yield } %>
  <%= yield :filters %>
  <%= default_content %>
</div>

这样即使content_for :filters写在默认yield的块里,也能确保它先被执行,之后yield :filters就能拿到内容了。


内容的提问来源于stack exchange,提问作者Nijeesh Joshy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.08 14:22:57