我有待办事项列表应用。在应用程序中,您可以通过单击复选框来标记待办事项。
这是erb
<% @todos.each do |todo|%>
<%= form_for todo, remote: true do |f| %>
<%= f.check_box :completed, :class => "dashboard_done_box", :id => todo.id %>
<% end %>
<% end %>
这里是js
$(document).on('click', ".dashboard_done_box", function(){
$("#edit_todo_" + $(this).attr('id')).submit()
});
routes.rb有一行
resources :todos
当我刷新页面时,它可以工作,但是当我导航到它时,我收到了这个错误。
Started POST "/todos/1" for 127.0.0.1 at 2014-05-07 13:18:45 +0200
ActionController::RoutingError (No route matches [POST] "/todos/1"):
当我停用 turbolinks 时,它也有效。
此代码适用于我的应用程序中的其他页面,它只在一个页面上我遇到此问题。
当它工作时发出PATCH请求
Started PATCH "/todos/1" for 127.0.0.1 at 2014-05-07 13:44:08 +0200
Processing by TodosController#update as JS
为什么它会执行POST请求以及它如何连接到turbolinks?
更新
Yosep Kim建议我应该制作一个后期路线
的routes.rb
post 'todos/:id' => 'todos#update', :as => :todo_update
表格
<%= form_for @todo, remote: true, url: todo_update_path(@todo), method: :post do |f| %>
现在我得到了控制器,但只有这些参数
{"controller"=>"todos", "action"=>"update", "id"=>"3"}
结论:表单提交未进行序列化。为什么呢?
答案 0 :(得分:2)
表单是如何呈现的?
Rails使用PATCH谓词进行更新,因为在rails应用程序中,更新几乎总是部分更新。 PUT动词应该用于完整更新(比如覆盖文件时)在这里阅读更多Riding With Rails
Rails使用隐藏字段来容纳html动词。
您的表单应该像这样呈现
<form accept-charset="UTF-8" action="/todos/5" class="edit_todo" data-remote="true" id="roster_edit_done_todo_5" method="post">
<div style="display:none">
<input name="utf8" type="hidden" value="✓">
<input name="_method" type="hidden" value="patch">
</div>
<!-- What ever fields you need -->
</form>
请注意表格中是否有表格。该表可能会使表单呈现奇怪。
答案 1 :(得分:2)
最新的64位Chrome开发/测试频道版本37,38上有一个错误。
如果您使用它,请参阅https://code.google.com/p/chromium/issues/detail?id=388664
答案 2 :(得分:1)
首先,当单击复选框时,您的代码将创建两个冗余请求。第一个是由表单触发的,第二个是由你的JS代码触发的。表单触发的那个在页面刷新后只能工作一次。一旦你点击它,Turbolink将刷新BODY中的内容而不重新加载DOM,无法将AJAX事件处理程序附加到表单。
您可以使用preventDefault来抑制默认行为。这应该只通过JS代码触发一次动作。
$(document).on('click', ".dashboard_done_box", function(e){
e.preventDefault();
$("#edit_todo_" + $(this).attr('id')).submit()
});