Rails js.erb not rendering partial file but get response file rendered

Viewed 1637

I have the following partial files

_report.html.erb

<h5>REPORT</h5>
<hr/>
<%= link_to "Extract REPORT", "#", :class => 'btn btn-primary', id: 'load_panel' %>
<br/>
<br/>

<div class="row">
  <% rand = Time.now.to_i - Random.new.rand(1..Time.now.to_i) %>
  <div class="col-md-12">
    <input type="hidden" id="randValue" value="<%= rand %>" data-validate="false" data-hidden="true"/>
    <div>
      <b>File Name</b>
      <hr/>
    </div>
    <div id="application-attachments-<%= rand %>" class="col-xs-12">
      <%= render partial: 'report_attachment', locals: {application_attachments: f.object.application_attachments} %>
    </div>
  </div>
</div>


_report_attachment.html.erb

<% application_attachments.each do |attachment| %>
    <div class="fields">
        <%= render "report_attachment_fields", rep_attachment: attachment, instalment: true, type: 'application_assignment' %>
    </div>
<% end %>


_report_attachment_fields.html.erb

<div class="row attachment_display">
  <% if rep_attachment.attachment? && rep_attachment.attachment.model.share_file %>
    <% if @action == "show" && @account_type %>
      <div class="col-md-6 ellipis">
        <%= link_to File.basename(rep_attachment.attachment.path), rep.attachment.url, target: "_blank", id: 'view_file', :data => { application_attachment_id: rep_attachment.id } %>
        <%= rep_attachment.active %>
      </div>
    <% end %>
  <% end %>
</div>

Upon initial load, it loads all 3 files accordingly. But Upon clicking Extract CTOS, it makes a javascript request

application.js

$('body').on('click', '#load_panel', function(event) {
    object_selected = $(this)
    $(this).attr('disabled', 'disabled');

    $.ajax({
      type: 'GET',
      url: '/applications/generate_report?application_id='+$(this).attr('data-application-id')+'&rand_value='+$(this).attr('data-rand-value'),
      dataType: 'json',
      success: function(data) {
        object_selected.removeAttr('disabled');
      }
    })
  })

On calling the GET request, it will call this method

def generate_report
  @rand_value = params[:rand_value]
  @rep_application_attachment = @application.rep_attachment
  respond_to do |format|
    format.js
  end
end

Which should call this js.erb file

generate_report.js.erb

$("#application-attachments-#{@rand_value}").html("<%= escape_javascript(render 'report_attachment', application_attachments: @rep_application_attachment) %>");

The problem now is that i dont get an error and it says generate_report.js.erb has been rendered but it doesnt render anything. What am i missing?

3 Answers

solved it. It had to do with my ajax call.

$.ajax({
      type: 'GET',
      url: '/applications/generate_report?application_id='+$(this).attr('data-application-id')+'&rand_value='+$(this).attr('data-rand-value'),
      dataType: 'json',
      success: function(data) {
        object_selected.removeAttr('disabled');
      }
    })

should be this instead. by not including datatype ='script' and correct format, even though my js.erb got called, it wasn't executed.

$.ajax({
      type: 'GET',
      url: '/applications/generate_report?application_id='+$(this).attr('data-application-id')+'&rand_value='+$(this).attr('data-rand-value'),
      data: {
        format: 'js'
      },
      dataType: 'script',
      success: function(data) {
        object_selected.removeAttr('disabled');
      }
    })

You need to specify 'partial' option to render template using render method.

Try this

generate_report.js.erb

$("#application-attachments-#{@rand_value}").html("<%= escape_javascript(render partial: 'report_attachment', application_attachments: @rep_application_attachment) %>");

your original code:

$("#application-attachments-#{@rand_value}").html("<%= escape_javascript(render 'report_attachment', application_attachments: @rep_application_attachment) %>");

Rendering partials

Partial rendering in a controller is most commonly used together with Ajax calls that only update one or a few elements on a page without reloading. Rendering of partials from the controller makes it possible to use the same partial template in both the full-page rendering (by calling it from within the template) and when sub-page updates happen (from the controller action responding to Ajax calls). By default, the current layout is not used.

For more information about render

https://apidock.com/rails/ActionController/Base/render

I think the problem is that you're trying to interpolate your ruby instance variable the wrong way (you're using Ruby's string interpolation syntax "#{}"), when you need to use ERB "<%= %>".

This should work:

$("#application-attachments-<%= @rand_value %>").html("<%= escape_javascript(render 'report_attachment', application_attachments: @rep_application_attachment) %>");
Related