cocoon: form error messages not returning with `remote: true` when creating pictures?

Hi Nathan. I am getting similar to this issue https://github.com/nathanvda/cocoon/issues/150 where I use remotipart gem to get past the authenticity token issue when using remote: true in a form. When I use remote: true everything renders out correctly from server to the page except error messages are not being sent. The only reason I believe its a cocoon issue is the problem only occurs when I add pictures. If I do not add any pictures and submit a invalid form the error messages display.My server reads these two results

POST req without pics

Started POST “/users/2/galleries” for ::1 at 2017-12-11 16:52:42 +1100 Processing by GalleriesController#create as JS Parameters: {“utf8”=>“✓”, “gallery”=>{“name”=>“Hello”, “cover”=>“”}, “commit”=>“Create Gallery”, “user_id”=>“2”} User Load (0.0ms) SELECT “users”.* FROM “users” WHERE “users”.“id” = ? LIMIT ? [[“id”, 2], [“LIMIT”, 1]] (0.0ms) begin transaction User Load (0.5ms) SELECT “users”.* FROM “users” WHERE “users”.“id” = ? LIMIT ? [[“id”, 2], [“LIMIT”, 1]] (0.0ms) rollback transaction Rendering galleries/new.js.erb Rendering galleries/new.html.erb Rendered shared/_error_messages.html.erb (0.5ms) Rendered galleries/_picture_fields.html.erb (1.0ms) Rendered galleries/_form.html.erb (303.9ms) Rendered galleries/new.html.erb (455.6ms) Rendered galleries/new.js.erb (605.8ms) Completed 200 OK in 796ms (Views: 791.3ms | ActiveRecord: 0.5ms)

POST req with pics

Started POST “/users/2/galleries” for ::1 at 2017-12-11 16:52:11 +1100 Processing by GalleriesController#create as JS Parameters: {“utf8”=>“✓”, “gallery”=>{“name”=>“Hello”, “cover”=>“”, “pictures_attributes”=>{“1512971529011”=>{“picture_cache”=>“”, “_destroy”=>“false”, “picture”=>#<ActionDispatch::Http::UploadedFile:0xd1409f0 @tempfile=#Tempfile:C:/Users/Lee/AppData/Local/Temp/RackMultipart20171211-11944-1ox30j6.jpg, @original_filename=“All-Out-EDM-mix-picture-3.jpg”, @content_type=“image/jpeg”, @headers=“Content-Disposition: form-data; name="gallery[pictures_attributes][1512971529011][picture]"; filename="All-Out-EDM-mix-picture-3.jpg"\r\nContent-Type: image/jpeg\r\n”>}}}, “commit”=>“Create Gallery”, “remotipart_submitted”=>“true”, “authenticity_token”=>“6H0jpCI/uTwUTeKMdWK3ttYL2loFFjSZh8DXoDdxhPrPUL8YNVLQL05/V9iMVidAmoeN+An+8D1+39q77IQQIQ==”, “X-Requested-With”=>“IFrame”, “X-Http-Accept”=>“text/javascript, application/javascript, application/ecmascript, application/x-ecmascript, /; q=0.01”, “user_id”=>“2”} User Load (0.0ms) SELECT “users”.* FROM “users” WHERE “users”.“id” = ? LIMIT ? [[“id”, 2], [“LIMIT”, 1]] (0.0ms) begin transaction User Load (0.0ms) SELECT “users”.* FROM “users” WHERE “users”.“id” = ? LIMIT ? [[“id”, 2], [“LIMIT”, 1]] (0.5ms) rollback transaction Rendering galleries/new.js.erb Rendering galleries/new.html.erb Rendered shared/_error_messages.html.erb (0.5ms) Rendered galleries/_picture_fields.html.erb (2.0ms) Rendered galleries/_picture_fields.html.erb (1.0ms) Rendered galleries/_form.html.erb (490.6ms) Rendered galleries/new.html.erb (663.8ms) Rendered galleries/new.js.erb (828.0ms) Completed 200 OK in 1521ms (Views: 1026.6ms | ActiveRecord: 0.5ms)

The form looks like this

<%= form_for([@user, @gallery], remote: true) do |f| %>
<%= render 'shared/error_messages', object: f.object %>
  <div class="field">
    <%= f.label :name %>
    <%= f.text_field :name %>
  </div>
  <div class="field">
    <%= f.label :cover %>
    <%= f.text_field :cover %>
  </div>
  <table class="user-picture-form">
    <tbody>
      <%= f.fields_for :pictures do |pic| %>
      <%= render 'picture_fields', f: pic %>
      <% end %>
   </tbody>
 </table>
 <div class="links">
   <%= link_to_add_association 'add picture', f, :pictures %>
   <%= f.submit %>
 </div>
<% end %>

and

<tr class="nested-fields">
  <td>
    <%= f.file_field :picture, accept: 'image/jpg,image/jpeg,image/gif,image/png' %>
    <%= f.hidden_field :picture_cache, :value => f.object.picture_cache %>
  </td>
  <td class="thumb">
    <% if f.object.picture.url.present? %>
    <%= image_tag f.object.picture.url %>
    <% end %>
    </td>
    <td> 
      <%= link_to_remove_association "remove", f %>
    </td>
</tr>

Also I am confused because removing remote: true from the form and submitting as html and also adding pictures the form returns the errors correctly so things work when the response is HTML. I even removed remotipart gem and changed ActionView::Helpers::FormTagHelper.embed_authenticity_token_in_remote_forms = true to true but then rails would not recognise js format. Wondering if you can shed some light on this.

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Comments: 21 (7 by maintainers)

Most upvoted comments

I posted on SO here and remotipart ticket here but as a work around I just put return in the custom renderer and everything works fine.

Eg link nathan linked to and code

....
def render_with_remotipart *args
  render_without_remotipart *args
  if remotipart_submitted?
    return # added by lee as this (remotipart) renderer wasnt inserting code into div with cocoon enabled.
    textarea_body = response.content_type == 'text/html' ? html_escape(response.body) : response.body
    response.body = %{<script type=\"text/javascript\">try{window.parent.document;}catch(err){document.domain=document.domain;}</script> <textarea data-type=\"#{response.content_type}\" data-status=\"#{response.response_code}\" data-statusText=\"#{response.message}\">#{textarea_body}</textarea>}
    response.content_type = ::Rails.version >= '5' ? Mime[:html] : Mime::HTML
  end
  response_body
end
...

The issue is weird but I am not that smart when it comes to javascript and the browser, only good at troubleshooting events on nodes and thats about it. Thanks guys. There is another gem to which may be good as a fallback to remotipart here ufujs-rails but not sure on how well maintained…

Could you verify that what is in the POST request response is valid, e.g. copy the contents of the response and run it in the browser console, then you will most likely get an error (that would explain the behaviour)(or for instance replacing a selector that is no longer on the page, also a classic).

I have no experience with this because I tend to use dropzone.js for uploading images (which only works after the “owner” element is created --so I never create the owner and attachments in one nested form).