繁体   English   中英

Rails Ajax JS与JSON混淆

[英]Rails Ajax JS vs JSON confusion

使用Rails 4,我想使用Ajax表单post:remote => true,我希望能够以json格式返回响应,以便在出现故障时可以使用任何错误消息。

表单帖子正在使我的控制器操作正常。 控制器动作:

def create
    @comment_hash = comment_params
    @obj = @comment_hash[:commentable_type].constantize.find(@comment_hash[:commentable_id])
    @comment = Comment.build_from(@obj, current_user.id, @comment_hash[:body])
    respond_to do |format|
        if @comment.save
            if @comment_hash[:reply_to].to_i > 0
                @parentcomment = Comment.find(@comment_hash[:reply_to].to_i)
                @comment.move_to_child_of(@parentcomment)
            end

            format.js { render :template => "comments/create.js.erb", :status => :created }
        else
            format.js { render :template => "comments/create.js.erb", :status => :unprocessable_entity }
        end
    end
end

无论成功或错误如何,控制器操作都将呈现create.js.erb。 但是,如果我包含format.json,它将永远不会使用json响应。 我认为这是因为Ajax remote:true请求将始终使用js进行响应。

  1. 如何获取响应json的ajax请求?

  2. 根据观察到rails ajax请求以js格式响应,我对这里提供的示例更加困惑: http//edgeguides.rubyonrails.org/working_with_javascript_in_rails.html其中成功的保存响应提供了js格式但错误响应没有提供任何js格式。

我认为这对于ajaxError响应会出错,因为js格式不可用?:

def create
  @user = User.new(params[:user])

  respond_to do |format|
    if @user.save
      format.html { redirect_to @user, notice: 'User was successfully created.' }
      format.js   {}
      format.json { render json: @user, status: :created, location: @user }
    else
      format.html { render action: "new" }
      format.json { render json: @user.errors, status: :unprocessable_entity }
    end
  end
end

无论成功或错误如何,控制器操作都将呈现create.js.erb。 但是,如果我包含format.json,它将永远不会使用json响应。 我认为这是因为Ajax remote:true请求将始终使用js进行响应

首先,你的假设不正确。 Rails remote: true挂钩到所谓的UJS驱动程序,这使得许多工作涉及使XHR请求更简单。 但是,您可以通过使用form_forform_tag并通过jQuery优秀的$.ajax()纯粹在JS中处理表单提交来实现相同的行为。

我建议你先删除create.js.erb - 这将始终被处理以返回脚本响应,并且你想要渲染JSON。

你也可以在这里更明确一点,

format.json { render json: { @user, status: :created, location: @user } }

#to_json ,Rails在您的Ruby对象(如AR模型)上调用#to_json ,调用简单的哈希。

删除create.js.erb ,转到要呈现表单的视图。 在DOM中查找form元素,您可以通过检查器控制台通过$('form')随便查找它。 最好通过类或直接识别它的ID。 我们假设你的表单的选择器是$('#comments-form')

您需要将另一个JS文件添加到您的app/assets/javascripts/application.js Sprockets清单,并在该文件中

$(function(){
    var $commentForm = $('#comments-form');

    $commentForm.on('ajax:error', function(e, xhr, status, error) {
        console.log('Error: %O', $(this).append(xhr.responseText));
    });

    $commentForm.on('ajax:success', function(e, data, status, xhr) {
        console.log('Data: %O', data);
    });

});

上面的JS片段是一个开始,当触发那些jquery-ujs事件时将触发,将调试输出放入控制台。 在XHR错误上,您将收到错误信息,成功时将显示JSON数据。

附录

format.js在respond_to代码块是纯粹用于处理create.js.erb ,其在提供的示例中执行此$("<%= escape_javascript(render @user) %>").appendTo("#users"); - 它使用用户实例来确定DOM选择器,并将其附加到ID为'users'的DIV中。

就个人而言,我发现通过成功处理程序坚持使用JSON并通过成功处理程序实现相同的行为更简单,尽管是YMMV。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM