控制器中的render_to_string partial格式错误

10
在控制器上运行以下代码时,我收到以下错误。请注意错误中的:formats => [:json],即使在render_to_string中传递了:formats => [:html]
有什么做错了吗? 有什么想法吗? 实际上,下面的代码之前都可以正常工作,不确定哪些更改会影响此错误。 Rails版本:3.2.8
顺便问一下: 在哪里可以找到API文档,显示可以传递给render_to_string的参数以及其工作原理?
错误: ActionView :: MissingTemplate(使用{:locale => [:en],:formats => [:json],:handlers => [:erb,:builder,:coffee]}缺少局部loc / search_details。
  respond_to do |format|
    format.json { 
      @detail_str = render_to_string(:partial => 'loc/search_details', :layout => false, :formats=>[:html], :locals => {:beer_results => @beer_results})
      @list_str = render_to_string(:partial => 'loc/search_list', :layout => false,:formats=>[:html], :locals => {:beer_results => @beer_results})
      render :json => {:results => @results_hash, :result_details => @detail_str, :result_list => @list_str }

      }
  end

我认为:format不是传递给render的有效参数。 - Andrew Hubbs
我不使用 :format,而是用的是 :formats。 - vrepsys
True。但我认为这也不是一个有效的参数。 - Andrew Hubbs
5个回答

4

如果您尝试一下呢?

render_to_string(:partial => 'loc/search_details.html.erb', :layout => false, :locals => {:beer_results => @beer_results})

或者

with_format("html") { render_to_string(:partial => 'loc/search_details', :layout => false, :locals => {:beer_results => @beer_results}) }

并添加该方法
private
def with_format(format, &block)
  old_format = @template_format
  @template_format = format
  result = block.call
  @template_format = old_format
  return result
end

来源:如何在Rails中呈现不同格式的局部视图?


传递处理程序并没有帮助,还有另一个关于:formats html的弃用警告,如果我添加格式,我会回到我拥有的代码,它不起作用。 第二个解决方案看起来像是一个肮脏的hack :) 我稍后会尝试一下。 - vrepsys
这是一个不太正规的解决方案,但另一方面,你想要做的事情也有点不太正规,所以这个解决方案符合需求 ;) - mrbrdo
顺便说一下,模板肯定已经就位了:loc/search_details.html.erb。 哈哈,我希望你在那里打错了一个字母,你知道部分文件名是以下划线开头的,希望如此 :-) 因为我在一个空白的 Rails 应用程序中尝试了你的代码,并且它可以正常工作,当然要使用正确命名的部分。 - mrbrdo
是的,那是个打字错误 :) 现在已经修复了。所以它现在可以正常工作吗?但我还是无法使用它...明天我会试着找出问题所在。谢谢。 - vrepsys
是的,它对我有效,我复制了你的设置:format.json ... "@detail_str = render_to_string(:partial => 'home/index_details', :layout => false, :formats=>[:html], :locals => {:beer_results => 1}) ; render :json => {:result_details => @detail_str }"。文件app/views/home/_index_details.html.erb也可以正常渲染。如果您遇到问题,请创建一个简单的Rails应用程序进行测试,并从那里开始。 - mrbrdo
显示剩余2条评论

4
请参阅这个问题这个问题。由于您正在进行JSON请求,因此您的 render_to_string 希望您的部分为_search_details.json.erb。您可以提供其他JSON部分、重命名该部分或在部分中添加<% self.formats = [:json, :html] %>,或尝试该问题的已接受答案中的解决方法。

3
你错了,render_to_string方法中的:formats => [:html]参数是让它首先查找_search_details.html.erb文件。我已经亲自测试过,在Rails 3.2.9中它是可行的。 - mrbrdo
<% self.formats = [:json, :html] %> -- 这个实际上是有效的 - vrepsys
我需要在render_to_string方法中传递:formats => [:html],并在partial中添加<% self.formats = [:json, :html] %>才能使其正常工作。 - Mitya

2

以防其他人也遇到这个问题,如果你要将内容渲染为字符串,你需要在format.json块的上下文之外进行渲染。以你的例子为例:

respond_to do |format|
  @detail_str = render_to_string(:partial => 'loc/search_details', :locals => {:beer_results => @beer_results})
  @list_str = render_to_string(:partial => 'loc/search_list', :locals => {:beer_results => @beer_results})
  format.json {     
      render :json => {
        :results => @results_hash, 
        :result_details => @detail_str, 
        :result_list => @list_str 
      }

  }
end

以这种方式,您无需指定格式或设置布局为false。

1
尝试通过。
:format => :html

不是

:formats => [:html]

:formats 在 4.2.1 版本中可用,而 :format 则不行。 - lulalala

1

以防万一有人遇到同样的问题,这是对我有效的解决方法。

当我使用render_to_string时出现的错误消息与问题中完全相同,包括format不匹配。然而,这并不是问题的根源。

问题在于我的应用程序进行了i18n,并且语言环境是通过URL给出的。我的routes.rb如下:

Quoties::Application.routes.draw do

  scope "(:locale)", locale: /en|pl/ do
    # all routes go here
  end

end

我的application_controller.rb看起来像这样:

class ApplicationController < ActionController::Base
  protect_from_forgery

  before_filter :set_locale

  def default_url_options(options={})
    locale = I18n.locale
    locale = nil if locale == :en
    { locale: locale  }
  end

  def set_locale
    parsed_locale = params[:locale] || 'en'
    I18n.locale = I18n.available_locales.include?(parsed_locale.to_sym) ? parsed_locale : nil
  end
end

这是我在互联网上找到的一个稍微改进过的解决方案。

在大多数情况下,它运行得非常好。然而,当我在局部视图中使用路径助手时,它却成为“缺少部分”的错误原因。

<%= item_path(item) %>

解决问题的方法是将上述行替换为:
<%= item_path(item, locale: params[:locale]) %>

我不知道为什么在这种情况下default_url_options不起作用,以及为什么Rails会引发如此奇怪的异常。

上面建议的<% self.formats = [:html, :json] %>解决方案只是让错误消息更清晰,至少它改变为在item_path处抛出“没有匹配路由...”。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接