我想在我的JavaScript中使用控制器变量。

由于这不能直接做到。我用宝石。 https://github.com/gazay/gon

这样,我所做的就是在我的基本控制器的before过滤器中(哪个充当所有控制器的before过滤器)我执行gon.variable_name = value并且在我的js文件中,我使用gon.variable_name。这对于整个页面重新加载都很好。

但是该变量不会针对ajax请求进行更新。

例如说:

在页面重新加载时,在我的控制器中

gon.variable_name = value1


在我的js中,gon.variable_name给了我value1

在我的控制器中的ajax请求之后

gon.variable_name = value2


在我的js中,我仍然只将gon.variable_name视为value1

有什么办法可以在ajax请求中更新gon.variable_name?

谢谢

最佳答案

您可以将watch: true开关用于gon

#app/views/layouts/application.html.erb
<head>
  <%= include_gon(watch: true) %>

#app/controllers/application_controller.rb
class ApplicationController < ActionController::Base
   def update_vars
      @value1 = User.count
      gon.watch.value1 = @users_count
   end
end


这就是文档所说的。我不同意,但应该可以。
看起来ajax polling效率极低。

-

为了给您一些上下文,您必须记住gon基本上在layout中创建了一个小的javascript哈希,并使用您在控制器中分配的gon变量填充了它:

<script>
   gon = {
      value1: "test",
      value2: "test"
   }
</script>


在此之前,我们已经使用了它:

javascript - 在javascript中使用 Controller 变量(Ruby on Rails)-LMLPHP

之所以如此重要,是因为此gon JS变量是在运行时调用的-意味着它会保持静态,直到您重新加载页面为止。

解决方法是动态重新加载gon变量值(使用上面的watch)或通过ajax请求传递新值(如注释中建议的Sergio):

#app/controllers/application_controller.rb
class ApplicationController < ActionController::Base
   def update
      respond_to do |format|
         format.json { render json: {value_2: "test"}.to_json %>
      end
   end
end


然后,您可以按以下方式使用它:

$.ajax({
   url: "/update",
   success: function(data) {
      var value2 = data.value2;
   }
});

10-05 22:33