ajax post后,erb数组没有更新

时间:2014-07-30 08:55:43

标签: jquery ruby-on-rails highcharts

我想通过highcharts在我的rails app中显示统计信息。当用户单击每个表行中可见的按钮时,将显示图表。单击按钮后,将使用数据库查询中使用的条目的id完成ajax发布。使用.done-回调,我试图遍历结果并将数据添加到图表中,但视图中的数组始终为空。查询的结果在控制器中正确显示,但在视图中始终为零。

查看:

$('.stats_btn').click(function() {
    var info = $($(this).parent().siblings("#data_id")).get()
    var data_id = parseInt(info[0].innerHTML);
    $.ajax({
      type: 'POST',
      url: "/my_page/get_stats",
      data: {id: data_id}
      })
            .done(function() {
              $('#stats_modal').modal();
              <%if @stats !=nil%>
                chart = new Highcharts.Chart({
                  chart: {
                    renderTo: "stats_chart"
                  },
                  title: {
                    text: "Stats"
                  },
                  xAxis: {
                    type: "datetime"
                  },
                  yAxis: {
                    title: {
                      text: "Hits"
                    }
              },
              tooltip: {
                formatter: function() {
                  return Highcharts.dateFormat("%B %e, %Y", this.x) + ': ' + Highcharts.numberFormat(this.y, 2) + " views";
                }
              },
              series: [{
                  data: [
                  <%@stats.each do |video|%>
                     <%=video.hits%>,
                  <%end%>
                  ]
                }]
            });
          <%end%>
        });


 });

控制器:

@serdata_id = params[:id]
@stats = Serdata_serkeyword.group("date(serkeywords.date)").select("count(*) as hits").joins(:serdata).where("serdata.id = ?", @serdata_id).joins(:serkeyword).where("serkeywords.id = serkeyword_id")
@stats.each do |record|
  logger.info record.hits
end

我知道ruby代码是在服务器端执行的,但是当我执行ajax post时,会创建一个新的控制器实例(?),因此必须初始化该数组。我是否误解了Rails中的工作原理,是否有更好的方法可以做到这一点?

1 个答案:

答案 0 :(得分:1)

<强> JS

首先,我会确保您的javascript是从document对象委派的,因为这样可以确保您能够捕获事件,无论您是否使用Turbolinks:< / p>

#app/assets/javascripts/application.js
$(document).on("click", ".stats_btn", function() {
  // stuff here
})

虽然这不会对您的问题有所帮助,但它会帮助臭名昭着的JS赢得工作,因为Turbolinks只刷新<body>标签,而不是{{1}标签&#34;问题

-

<强>控制器

关于你的控制器,如果服务器端查询被触发,则意味着你的ajax请求正在通过(这是个好消息)。解决问题的方法是确保您的<head>处理程序可以收到响应

通常,您将使用respond_to代码块处理响应:

ajax

-

<强> JSON

我实际上建议您将ajax请求的#app/controllers/my_pages_controller.rb Class MyPagesController < ApplicationController def get_stats respond_to do |format| format.js #-> returns JS response format.json #-> returns JSON response end end end 属性更改为dataType,因为这意味着您将能够接收纯JSON数据:

JSON

这意味着您可以执行以下操作:

$.ajax({
      type: 'POST',
      dataType: 'JSON',
      url: "/my_page/get_stats",

-

查看

我认为您的主要问题是您设置#app/controllers/my_pages_controller.rb Class MyPagesController < ApplicationController respond_to :json, only: :get_stats def get_stats @serdata_id = params[:id] @stats = Serdata_serkeyword.group("date(serkeywords.date)").select("count(*) as hits").joins(:serdata).where("serdata.id = ?", @serdata_id).joins(:serkeyword).where("serkeywords.id = serkeyword_id") respond_with @stats #-> automatically encodes JSON end end 回调的方式 -

$.ajax

首先,您的$.ajax({ type: 'POST', url: "/my_page/get_stats", data: {id: data_id} }) .done(function() { $('#stats_modal').modal(); <%if @stats !=nil%> chart = new Highcharts.Chart({ chart: { renderTo: "stats_chart" }, title: { text: "Stats" }, xAxis: { type: "datetime" }, yAxis: { title: { text: "Hits" } }, tooltip: { formatter: function() { return Highcharts.dateFormat("%B %e, %Y", this.x) + ': ' + Highcharts.numberFormat(this.y, 2) + " views"; } }, series: [{ data: [ <%@stats.each do |video|%> <%=video.hits%>, <%end%> ] }] }); <%end%> }); 与任何事件/元素都没有关联,这意味着它不会运行。其次,.done方法(或用于捕获done响应的方法只有在您将返回的ajax传递给它时才有效

我建议使用以下内容:

data

此外,您无法在标准JS中使用$.ajax({ type: 'POST', url: "/my_page/get_stats", data: {id: data_id} success: function(data) { // returned data here } }); - 您只能在后端代码中使用@instance variables。在您的情况下,您应该将JSON请求传递给您的控制器&amp;然后使用@instance variables函数中的data参数来处理返回的JSON对象

这将确保您能够处理前端所需的数据


如果您希望我对所提供的代码更加具体,请告知我们&amp;我会更新你的信息!

-

<强>更新

您不能在前端JS / Ajax中使用success的原因只是前端。 Ajax(Asynchronous Javascript And XML)用于发送HTTP请求&#34;在幕后&#34; - 意味着您的Ajax请求就像&#34;伪&#34;浏览器(IE唯一的前端)

您遇到的问题是如果在后端(您的控制器)中设置@instance variables - 因为您的Ajax只是前端,这意味着它无法从控制器访问@instance variables。这意味着您的ajax只能读取您从控制器后端发送的数据

如果您在views文件夹中创建了@instance variables,那么您就可以使用所需的js.erb