Search code examples
ruby-on-railsturbolinks

Turbolinks causes JavaScript file to run several times


I'm using Rails 5.1.4, I'm new on the platform and I have problems with turboblinks, I have a file containing jquery code that has to run once the page loads, but Whenever the page loads the file runs several times but when I disable the turboblinks there it works as I want it. So I would like to know if there is one less to fix it without turning off the turboblinks. Thank you in advance..

So there is my layout file.// app/views/layouts/application.html.erb

<html lang="en">
 <head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <meta http-equiv="x-ua-compatible" content="ie=edge">
  <title>Rails web app</title>
   <%= stylesheet_link_tag    'application', media: 'all', 'data-turbolinks-
   track' => true %>
   <%= csrf_meta_tags %>
 </head>
 <body class="<%= controller_name %> <%= action_name %>">
  <%= render 'layouts/header' %>

  <p class="notice"><%= notice %></p>
  <p class="alert"><%= alert %></p>

  <div class="container">
   <%= yield %>
  </div>

  <%= javascript_include_tag 'application', 'data-turbolinks-track' => true 
  %>
 </body>
</html>

About my js file as you will see i try to load automatically a bootstrap modal with an animation when the page loaded, actually the problem happens when i clik to any link on this page which takes me to another page and i try to come back to the initial page where the js file is loaded, then the problem happens. i see the page refresh many times and the js file as well.

So there is my js file with jquery code. //app/assets/javascripts/file.js

$(document).ready(function(){
  $('#myModal').on('hide.bs.modal', function (e) {
   $('.modal .modal-dialog').attr('class', 'modal-dialog animated rollOut');
  });
  $('#myModal').on('show.bs.modal', function (e) {
   $('.modal .modal-dialog').attr('class', 'modal-dialog  fadeIn  
    animated');
  });

  $('#myModal').modal('toggle');
});

Solution

  • Turbolinks replaces the body so put this line in your head tag :

    <%= javascript_include_tag 'application', 'data-turbolinks-track' => true %>
    

    Like this :

     <html lang="en">
     <head>
      <meta charset="utf-8">
      <meta name="viewport" content="width=device-width, initial-scale=1">
      <meta http-equiv="x-ua-compatible" content="ie=edge">
      <title>Rails web app</title>
       <%= stylesheet_link_tag    'application', media: 'all' %>
       <%= csrf_meta_tags %>
       <%= javascript_include_tag 'application', 'data-turbolinks-track' => true %>
     </head>
     <body class="<%= controller_name %> <%= action_name %>">
      <%= render 'layouts/header' %>
    
      <p class="notice"><%= notice %></p>
      <p class="alert"><%= alert %></p>
    
      <div class="container">
       <%= yield %>
      </div>
     </body>
    </html>
    

    or add data-turbolinks-eval=false to the script tag that includes turbolinks.

    Also you need use the turbolinks:load event :

    $(document).on('turbolinks:load', function() {
      $('#myModal').on('hide.bs.modal', function (e) {
       $('.modal .modal-dialog').attr('class', 'modal-dialog animated rollOut');
      });
      $('#myModal').on('show.bs.modal', function (e) {
       $('.modal .modal-dialog').attr('class', 'modal-dialog  fadeIn  
        animated');
      });
    
      $('#myModal').modal('toggle');
    });