Ruby on Rails Ajax调用运行控制器代码,返回成功,但不渲染视图

我的页面上有一个工作搜索机制; 带有文本字段和“搜索”标记的提交按钮的表单。

我的页面上还有一个基于raphael.js的动画项目,上面有可点击的项目,我想要执行搜索。

点击后,我发送给我的控制器params数据,这些数据是从raphael对象中获取的搜索项。

正在传递数据,并且控制器代码运行,但相应的视图无法呈现,因此单击对用户显示为什么都不做。

所以点击后,我就像这样做一个Ajax调用:

文件searchthing.js

// Add a search function circle.click(function (e) { var csrch = this.data('label'); // alert('clicked ' + csrch); e.preventDefault(); $.ajax({ type: "GET", url: "/bubbleBar", data: $.param({ srchterm: csrch} ), success: function(){ // window.location.replace("/pictures"); }, error: function(XMLHttpRequest, textStatus, errorThrown) { alert("--- error: " + errorThrown); } }); }); 

我的控制器中的’bubbleBar’操作成功触发,传输搜索条件,并重定向到处理搜索的工作索引操作:

文件myController.rb:

 def bubbleBarSearch redirect_to pictures_path(:srchterm => params[:srchterm]) end def index # Initialize the pictures array # @pictures = Picture.first if params[:srchterm].present? # If the search button was hit, search pictures for the terms @pictures = [] results = Picture.search(params[:srchterm], page: params[:page]) results.each do |x| @pictures < kw.picture_id) pics.each do |pic| # Only add to results if unique # if !@pictures.include? pic @pictures << pic end end end respond_to do |format| format.html { puts '---------------- ding -----------------' # Redirect_to pictures_path } format.js {alert('dong');} end else @pictures = Picture.all.order("RANDOM()") end end 

我遇到的问题是Ajax返回成功,但“index”操作的相应视图不会呈现。

如果我取消注释’window.location.replace(“/ pictures”);’ 在我的JavaScript代码中,我可以强制渲染成功,但是我丢失了控制器代码为我获得的搜索结果。如果我取消注释控制器中的’redirect_to pictures_path’行,我当然会得到一个无限循环错误出。

我到目前为止所做的研究告诉我,我应该在控制器中捕捉响应。

我之前没有使用respond_to,看起来format.html被Ajax调用击中,但是当我使用页面上已经设置的搜索字段/按钮机制手动执行搜索时,也会触发。 我不清楚为什么我的Ajax调用以HTML而不是JavaScript的forms出现。

所以这意味着如果我在控制器中手动处理视图的渲染,当搜索没有通过已经运行的机制并且冒着渲染页面两次或者在我的操作中引入故障的风险时,我没有抓住这种情况现场。

在控制器动作发生后,我迷失了如何使我的click / Ajax调用成功地从click函数渲染所需的视图。 我在这里想念的是什么? 实现这一目标的理想方法是什么,而不是丢失成功渲染所需的控制器数据?

Ruby on Rails的输出表明服务器认为它正在呈现正确的Haml视图文件,但是我在文件的底部放置了一个JavaScript标记以将输出记录到控制台,并且在单击后控制台为空。 如果我通过站点导航到同一视图,则语句将输出到控制台。

我已经修改了我的Ajax成功回调以获得一个参数,并且在检查时该变量包含视图的HTML代码。 那么Ruby on Rails是否将输出定向到Ajax而不是浏览器? 然后我如何从Ajax成功回调中呈现该输出?

成功调用控制器包含一个不在我的Ajax调用中的utf8参数。 这是一个因素吗?

format.js不是你的情况。 我想你应该这样:

 if request.xhr? # render data on ajax request else # render view end 

通过返回重定向到浏览器的状态代码来重定向工作,这会导致浏览器对响应头中返回的url发出后续请求。 所以,问题是你的bubbleBarSearch操作返回的状态是重定向到你的ajax调用。 它实际上并不是在索引操作中运行代码。 为什么不直接为索引操作创建路由并直接调用它?

编辑 – 这是错的,我现在看到你在问什么。 在回复中回答你的问题:

啊,我知道,看起来你想要做AlexeyKuznetsov所建议的。

而不是respond_to do |format| if request.xhr你会想要的。 当你发出ajax(xhr)请求时,request.xhr条件为true,否则rails知道它的标准请求。 我认为您的问题是您没有正确响应,这将呈现并返回它所呈现的任何html,并将其返回到您的ajax请求。 您可以告诉rails对不同类型的请求进行不同的呈现。 要使用javascript代码段进行响应,您可以使用render js:http://guides.rubyonrails.org/layouts_and_rendering.html搜索Rendering Vanilla JavaScript)

 if request.xhr render js: "alert('dong')" # this is an ajax request else puts '-------- ding ---------` # this is not 

或者你可以渲染json render json: ,这将传回一个json响应。

 if request.xhr render json: {message: "ding"} else puts '-------- ding ---------` # this is not 

然后在你的axax成功函数:

 success: function(data){ console.log(data) // will have message: ding // window.location.replace("/pictures"); }, 

我有一个可行的解决方案,可以实现我的目标。 它在chrome中产生以下控制台警告:

 Synchronous XMLHttpRequest on the main thread is deprecated because of its detrimental effects to the end user's experience. For more help, check https://xhr.spec.whatwg.org/. 

但是,它确实为我的浏览器呈现了适当的结果。 如果有更合适的方法来做到这一点,我很乐意学习它。

我发现重定向到的呈现页面的整个HTML(包括application.html.haml中的站点页眉和页脚)正在返回到Ajax成功回调,而不是被rails识别为HTML。 所以我现在用返回的数据替换整个页面正文的HTML。 这是通过三行代码完成的:

  $.ajax({ type: "GET", url: "/bubbleBar, data: $.param({ srchterm: csrch} ), > dataType: "html", > success: function(response, status, request){ > $('body').html(response); )}; 

我仍然不确定这是否 – “成功回调”的页面是正常的和预期的。 此外,如果我的解决方案是将浏览器更改为所需页面的理想方式,或者我可以做的事情是将此页面呈现给回调之外的浏览器。 可能不是因为这是异步请求。

我可以想象,如果用户在等待搜索完成的同时正处于其他任务中,这可能会导致我的站点出现问题,但我目前没有更好的解决方案。 我将考虑重组网站布局以防止出现这样的问题。

我还从控制器中删除了respond_to块,因为我无法确定是否有任何方法让它仅在我需要时执行我需要的操作。 现在我可能已经知道了dataType:ajax属性,我可能会认为只有这个请求可能会ping,但是我在确定在该语句的任何情况下适当的响应时都没有成功,我只得到了我所有的尝试都出现了ajax错误。

谢谢大家的建议,他们帮助我尽我所能。