jQueryAjax—处理两种不同的响应类型

jQueryAjax—处理两种不同的响应类型,jquery,ajax,Jquery,Ajax,我正在开发一个应用程序(jquery 3.2.1),在这个应用程序中,进行ajax调用可能会导致以下情况之一——只要服务器给出HTTP 200 OK响应: 返回HTML。这是期望的结果,因为它是对有效请求的“内容”响应 如果存在基于请求数据的验证错误,则返回JSON错误 我的ajax代码如下所示: $.ajax({ url: $('#searchRegulations').attr('action'), type: 'post', cache: false, data: $('#

我正在开发一个应用程序(jquery 3.2.1),在这个应用程序中,进行ajax调用可能会导致以下情况之一——只要服务器给出HTTP 200 OK响应:

  • 返回HTML。这是期望的结果,因为它是对有效请求的“内容”响应

  • 如果存在基于请求数据的验证错误,则返回JSON错误

  • 我的ajax代码如下所示:

    $.ajax({
      url: $('#searchRegulations').attr('action'),
      type: 'post',
      cache: false,
      data: $('#searchRegulations').serialize()
    }).done(function (response) {
        if (response) {
          // Display response (point 1)
          $('main .content').hide();
          $('#ajaxContent').html(response).show();
          return false;
        } else {
            // Handle JSON error (point 2)    
        }
    });
    
    $.ajax({
        url: $('#searchRegulations').attr('action'),
        type: 'post',
        cache: false,
        data: $('#searchRegulations').serialize()
     }).done(function (response, status, xhr) {
    
                // The ajax handler can return either HTML or JSON. So we need to know what's been returned.
                var ct = xhr.getResponseHeader("content-type") || "";
    
                // HTML response == content to display. No validation error.
                if (ct.indexOf('html') > -1) {
                    if (response) {
                        $('main .content').hide();
                        $('#ajaxContent').html(response).show();
                        return false;
                    }
                }
                // JSON response. Validation error(s) occurred.
                if (ct.indexOf('json') > -1) {
                    $.each(response, function(i, v) {
                        $.each(v, function(k, m) {
                             var msg = '<span class="help-block">'+m+'</span>';
                             $('input[name="' + i + '"]').parent().after(msg);
                             $('input[name="' + i + '"]').closest('.form-group').addClass('has-error');
                        });
                    });
                }  
    });
    
    正如我在上面的评论中提到的,如果出现情况1(返回HTML),那么我将其写入
    #ajaxContent
    。那很好

    但是对于情况2,我该怎么做呢?如果我添加以下代码:

    // Handle JSON error (point 2)  
    $('main .content').hide();
    $('#ajaxContent').html(response).show();
    
    #ajaxContent
    中没有任何内容

    这是因为没有返回HTML吗

    每个的响应头都不同:

  • 内容类型:text/html;字符集=UTF-8

  • 内容类型:application/json;字符集=UTF-8

  • 我在jquery上查看了
    数据类型
    ,但不确定这是否相关,因为我实际上收到了基于结果的两个单独的内容类型

    在场景2中返回JSON的原因是有一些代码(未显示)可以在每个字段下写入错误消息,例如

    `{rf_keywords: {length: "Search keywords must under 1500 characters in length."}}`
    
    因此,HTML更适合情况1,JSON更适合情况2


    请有人提供建议?

    正如您所观察到的,在案例2中,您会收到一个json forat的响应。当您的代码被传递到
    response
    参数时,这应该已经被解析了。使用
    JSON.stringify
    再次将其转换为字符串,您将能够以html代码显示它:

    $('#ajaxContent').html(JSON.stringify(response)).show();
    
    请注意,这将不是一个漂亮的视图,因为JSON结构没有转换为等效的html子树

    请看一看完整的示例


    有一些库可以将JSON结构转换为交互式html,例如(对于您的用例来说可能有些过分)。

    好的,我在回答我自己的问题

    这里真正的问题是:在
    .done()

    有。此处记录:

    因此,我的最终ajax代码如下所示:

    $.ajax({
      url: $('#searchRegulations').attr('action'),
      type: 'post',
      cache: false,
      data: $('#searchRegulations').serialize()
    }).done(function (response) {
        if (response) {
          // Display response (point 1)
          $('main .content').hide();
          $('#ajaxContent').html(response).show();
          return false;
        } else {
            // Handle JSON error (point 2)    
        }
    });
    
    $.ajax({
        url: $('#searchRegulations').attr('action'),
        type: 'post',
        cache: false,
        data: $('#searchRegulations').serialize()
     }).done(function (response, status, xhr) {
    
                // The ajax handler can return either HTML or JSON. So we need to know what's been returned.
                var ct = xhr.getResponseHeader("content-type") || "";
    
                // HTML response == content to display. No validation error.
                if (ct.indexOf('html') > -1) {
                    if (response) {
                        $('main .content').hide();
                        $('#ajaxContent').html(response).show();
                        return false;
                    }
                }
                // JSON response. Validation error(s) occurred.
                if (ct.indexOf('json') > -1) {
                    $.each(response, function(i, v) {
                        $.each(v, function(k, m) {
                             var msg = '<span class="help-block">'+m+'</span>';
                             $('input[name="' + i + '"]').parent().after(msg);
                             $('input[name="' + i + '"]').closest('.form-group').addClass('has-error');
                        });
                    });
                }  
    });
    
    $.ajax({
    url:$('searchRegulations').attr('action'),
    键入:“post”,
    cache:false,
    数据:$('#searchRegulations')。序列化()
    }).done(功能(响应、状态、xhr){
    //ajax处理程序可以返回HTML或JSON,所以我们需要知道返回了什么。
    var ct=xhr.getResponseHeader(“内容类型”)| |“”;
    //HTML响应==要显示的内容。无验证错误。
    if(ct.indexOf('html')>-1){
    如果(答复){
    $('main.content').hide();
    $('#ajaxContent').html(response.show();
    返回false;
    }
    }
    //JSON响应。发生验证错误。
    if(ct.indexOf('json')>-1){
    $。每个(响应、功能(i、v){
    $。每个(v,函数(k,m){
    var msg=''+m+'';
    $('input[name=“”+i+“]”)之后的父项();
    $('input[name=“”+i+“]”)。最近('.form group')。addClass('has-error');
    });
    });
    }  
    });
    

    这样做意味着您可以检查HTML是否已返回—在这种情况下,请在
    #ajaxContent
    中显示它。如果发生错误并且从ajax脚本返回JSON,则可以根据返回的JSON将错误消息写入相应的表单字段下方。

    发布一个返回的示例:1。HTML响应,例如父HTML标记2。Json响应,例如Json对象中的父对象您可以更改响应吗?如果是,您可以更改为类似以下内容{htmlContent:”,json:“{yourjsonobject:here}”,并检查响应If(response.htmlContent){//do HTML stuff}If(response.json){//do json stuff}如果出现错误,让服务器相应地更改HTTP状态代码-例如,400表示验证错误,404表示未找到资源,403表示禁止,等等。您会发现各种标准状态非常适合大多数类型的请求错误。这样,您的JS代码将落入“失败”回调,而不是“完成”回调然后您就可以很容易地知道您需要将响应解析为JSON而不是HTML。因此,在
    .done()
    中没有办法查看响应类型(
    text/HTML;
    application/JSON;
    )是什么吗?我必须进入
    .fail()
    method来实现这一点?如果你想要一个好的设计实践,我建议你选择返回HTML或JSON来实现成功或失败的操作。我不建议你朝返回类型可以是this或that的方向前进。就像任何函数/方法一样,它有1个返回类型。遵循现有的编码标准和p如果您真的想与其他开发人员一起编写代码,请尝试。如果您想获得良好的设计实践,我建议您选择返回HTML或JSON,以获得成功或失败的操作。我不建议您朝返回类型可以是this或that的方向继续。与任何函数/方法一样,它有1个返回类型。如果你真的想和其他开发人员一起编码,请遵循现有的编码标准和模式……你有任何资源(链接等)吗哪一个支持您的声明?我不同意。函数的输出可能是需要以HTML格式显示/格式化的有效数据,或者是验证错误消息的不同类型的响应。请求将发送到同一个ajax端点,并且它必须做出相应的响应。在出现错误的情况下,JSON是比HTML更合适的响应因为它可以更容易地应用到适当的零件上