处理304未在jQuery Ajax中修改的正确方法

问题描述:

从jQuery 1.5开始,按照XMLHTTPRequest的W3C规范,ajax方法现在可以通过调用success()处理函数来正确处理304 Not Modified响应.即使服务器实际上没有返回任何数据(因为您已经缓存了最新的数据),这也使您的应用程序可以将请求视为成功.

As of jQuery 1.5, the ajax methods now correctly handle 304 Not Modified responses by calling the success() handler, as per the W3C spec for XMLHTTPRequest. This allows your application to treat the request as being successful, even if the server didn't actually return any data (because you already have the latest data cached).

对于普通的(未缓存的)GET请求,将使用以下参数调用成功处理程序:

For a normal (uncached) GET request, the success handler is called with the following args:

  • 数据:{来自服务器的数据}
  • 状态:确定
  • jqXHR:
    • 状态:200
    • statusText:确定
    • responseText:{来自服务器的数据}
    • data: { the data from the server }
    • status: OK
    • jqXHR:
      • status: 200
      • statusText: OK
      • responseText: { the data from the server }

      对于缓存的GET请求,将使用以下args调用成功处理程序:

      For a cached GET request, the success handler is called with the following args:

      • 数据:未定义
      • 状态:未修改
      • jqXHR:
        • 状态:304
        • statusText:未修改
        • responseText:{来自缓存的数据}
        • data: undefined
        • status: notmodified
        • jqXHR:
          • status: 304
          • statusText: notmodified
          • responseText: { the data from the cache }

          (至少,对于通过清单文件使用应用程序缓存的Web应用程序,这是在IOS 4.2中返回的方式.我假设这与大多数平台/浏览器上的常规浏览器缓存一致).

          (at least, this is how it is returned in IOS 4.2, for a web-app that uses the application cache via a manifest file. I'm assuming this is consistent for general browser caching on most platforms/browsers).

          您可以看到,仅当请求为200 OK时才填充数据"参数.在jqXHR.responseText中始终填充数据,而不管该数据是来自服务器(200 OK)还是来自缓存(304 Not Modified).

          You can see that the "data" argument is only populated if the request was 200 OK; where as the jqXHR.responseText is always populated with data, regardless of whether that data came from the server (200 OK) or from the cache (304 Not Modified).

          鉴于在大多数GET请求中,您的成功处理程序将想要对所获取的数据进行某些处理,无论其来自何处,对于成功代码而言,始终使用jqXHR似乎是最有意义的.responseText,而不是像这样做:

          Given that, in most GET requests, your success handler is going to want to do something with the data you got regardless of where it came from, it would seem to make the most sense for your success code to always use the jqXHR.responseText, rather than doing something like this:

          if ("notmodified" === status) {
            // do something with jqXHR.responseText
          } else {
            // do something with data
          }
          

          或者是否有可能不会在成功处理程序中填充jqXHR.responseText ,但是数据参数?

          Or is there ever a case when jqXHR.responseText wouldn't be populated in the success handler, but the data arg would?

          我必须遍历代码库并更改所有成功的处理程序(以前我使用的是jQuery 1.4.2,它总是返回数据,即使是从缓存中也是如此);所以我只想确保我以正确的方式处理它. (不要走到尽头,然后意识到我应该以另一种方式来做.)

          I have to go through my codebase and change all success handlers (previously I was on jQuery 1.4.2, which always returned data, even from the cache); so I just want to make sure I'm handling it the right way. (Don't wan't to get to the end and then realise I should have done it another way).

我刚刚发现了我的问题中的明显缺陷....我假设数据始终是文本,因此优先使用jqXHR.responseText来代替数据参数很有意义.

I've just spotted the obvious flaw in my question....I was assuming that the data was always text, so using jqXHR.responseText in preference to the data argument made sense.

但是在dataType为JSON,JSONP,脚本等的情况下...如果304 Not Modified响应中返回的数据返回未定义状态,则需要将jqXHR.responseText从字符串转换为首先是所需的类型,例如.

But in the case that the dataType is JSON, JSONP, script etc...if the data returned in a 304 Not Modified response comes back as undefined, you'd need to convert the jqXHR.responseText from a string to the desired type first, eg.

if (data === undefined) {
  data = $.parseJSON(jqXHR.responseText);
}

...而您只在真正需要时才进行此转换(可能非常昂贵).

...and you'd only want to do this (potentially expensive) conversion when you need really to.

现在我想起来,Kinda变得有意义了……数据总是从服务器返回来的(在某些情况下,对于304来说,不是是不确定的...例如服务器可能会返回一些其他的text/html);这样,开发人员可以灵活地选择在发生304事件时想要做的事情.

Kinda makes sense now that I think about it...data is always going to be what came back from the server (which in some cases might not be undefined for a 304...eg. the server could return some additional text/html); which allows the developer the flexibility to choose what they want to do in the event of a 304, eg.

  • 显示来自服务器的响应(如果有)
  • 使用jqXHR.responseText
  • 完全做其他事情...