【发布时间】:2014-07-26 11:06:14
【问题描述】:
我使用的是 Rails 4.1.1 和 Ruby 2.1.2p95。我使用 Slim 作为我的 HTML 模板语言(类似于 HAML)。我使用 Thin 作为我的 Rack 服务器。
我正在尝试制作一个完全 AJAX 的应用程序(我的要求之一是我不能重新加载页面)。
问题
我有一个如下所示的用户注册页面:
= form_for( User.new, url: user_path, remote: true ) do |f|
= f.label :username
= f.text_field :username, label: true
= f.label :password
= f.password_field :password, label: true
= f.label :password_confirmation
= f.password_field :password_confirmation, label: true
= f.submit
我有一个如下所示的 UsersController 操作(出于本示例的目的):
def create
render html: "PRETEND A USER WAS CREATED"
end
我有一个看起来像这样的响应处理程序(这实际上并不重要 - 可以说成功处理程序不会触发而错误处理程序会触发):
$("#dynamic_body").on( "ajax:success", "[data-remote]", function( event, data, status, xhr ) {
$("#dynamic_body").empty();
$("#dynamic_body").append( data );
});
$("#dynamic_body").on( "ajax:error", "[data-remote]", function( event, xhr, status, error ) {
$("#dynamic_body").empty();
$("#dynamic_body").append( error );
});
Rails 发送回一个响应,其中 Content-Type 标头设置为“text/javascript”。因此,浏览器尝试将响应解析为 JavaScript,这当然会失败,并导致错误事件而不是 AJAX 响应的成功事件。
我不喜欢的解决方案
我可以通过明确使用 Rails 来解决此问题,方法是在 form_for 调用中指定请求 URL 格式:
= form_for( User.new, url: user_path( format: :html ), remote: true ) do |f|
...
或通过在控制器操作中明确指定标头:
def create
render html: "PRETEND A USER WAS CREATED", content_type: :html
end
但我很不高兴我什至不得不这样做。没有人要求 Rails 返回一个 javascript 响应。 Their own documentation says that the controller defaults to "text/html",这在大多数情况下显然是正确的,但在使用他们不引人注目的 JavaScript 工具时则不然。
我很想了解这里发生了什么,以及是否有任何方法可以配置我的应用程序,因此我不需要编写这些额外的解决方法。
提前感谢好人。
【问题讨论】:
-
这似乎是特定于 Chrome 的问题。我对 Firefox 没有这种头痛。在每个浏览器中使用网络分析器,我看到 Chrome 选择将响应视为“文本/javascript”,导致问题,而 Firefox 将其视为“html”,并且工作正常。但是,仍然不知道原因是什么。在过去的几个小时里,我一直在浏览 jquery 和 jquery-ujs 文件,但一无所获。更改 JS 中的请求标头或 Rails 应用程序中的响应标头似乎没有任何效果。此外,问题是间歇性的。
-
没关系。一旦我发表了该评论,我就会重新开始工作,它适用于 Chrome,不适用于 Firefox。
标签: javascript ruby-on-rails ajax content-type unobtrusive-javascript