ChatGPT解决这个技术问题 Extra ChatGPT

iOS 6 上的 Safari 是否缓存 $.ajax 结果?

自从升级到 iOS 6 后,我们看到 Safari 的 Web 视图可以随意缓存 $.ajax 调用。这是在 PhoneGap 应用程序的上下文中,因此它使用的是 Safari WebView。我们的 $.ajax 调用是 POST 方法,我们将缓存设置为 false {cache:false},但这种情况仍在发生。我们尝试手动将 TimeStamp 添加到标题中,但没有帮助。

我们进行了更多研究,发现 Safari 仅返回具有静态函数签名且不会随调用而变化的 Web 服务的缓存结果。例如,想象一个名为的函数:

getNewRecordID(intRecordType)

这个函数一遍又一遍地接收相同的输入参数,但它每次返回的数据应该是不同的。

一定是 Apple 急于让 iOS 6 快速运行,他们对缓存设置太满意了。有没有其他人在 iOS 6 上看到过这种行为?如果是这样,究竟是什么原因造成的?

我们找到的解决方法是将函数签名修改为如下所示:

getNewRecordID(intRecordType, strTimestamp)

然后总是传递一个 TimeStamp 参数,并在服务器端丢弃该值。这可以解决这个问题。

这绝对令人震惊。我们还花了几个小时试图找出什么东西停止了工作。我们执行 POST 的 AJAX 登录(并且还具有防止缓存的标头)正在被 Safari 缓存,因此它只返回与上次相同的 JSON,甚至没有尝试服务器......难以置信!我们必须破解一个修复程序,但你永远不应该缓存 POST,这太疯狂了。
将您的解决方案发布为答案,而不是问题的更新。
POST 请求是非幂等的,这意味着它们不应被缓存,除非响应通过其响应标头明确建议这样做。
要让 Apple 解决此问题,请在 bugreport.apple.com 提交错误。我也做过同样的事情。
Mark Nottingham(IETF HTTPbis 工作组主席)今天就此写了一篇有趣的博文:mnot.net/blog/2012/09/24/caching_POST

K
Kieran

经过一番调查,事实证明 iOS6 上的 Safari 将缓存没有 Cache-Control 标头甚至“Cache-Control: max-age=0”的 POST。

我发现防止这种缓存在全局级别发生而不是不得不将随机查询字符串破解到服务调用结束的唯一方法是设置“Cache-Control:no-cache”。

所以:

没有 Cache-Control 或 Expires 标头 = iOS6 Safari 将缓存

Cache-Control max-age=0 和立即 Expires = iOS6 Safari 将缓存

Cache-Control: no-cache = iOS6 Safari 不会缓存

我怀疑 Apple 正在从第 9.5 节关于 POST 的 HTTP 规范中利用这一点:

对此方法的响应是不可缓存的,除非响应包含适当的 Cache-Control 或 Expires 标头字段。但是,303(请参阅其他)响应可用于指示用户代理检索可缓存资源。

所以理论上你可以缓存 POST 响应......谁知道呢。但到目前为止,还没有其他浏览器制造商认为这是一个好主意。但是,当没有设置 Cache-Control 或 Expires 标头时,这并不能说明缓存,仅当有一些设置时。所以应该是bug。

下面是我在 Apache 配置的正确位置中使用的内容来定位我的整个 API,因为碰巧我实际上并不想缓存任何东西,甚至不会缓存。我不知道如何仅为 POST 设置它。

Header set Cache-Control "no-cache"

更新:刚刚注意到我没有指出只有当 POST 相同时,所以更改任何 POST 数据或 URL 就可以了。因此,您可以像其他地方提到的那样,向 URL 中添加一些随机数据或一些 POST 数据。

更新:如果您希望在 Apache 中这样,您可以将“无缓存”限制为 POST:

SetEnvIf Request_Method "POST" IS_POST
Header set Cache-Control "no-cache" env=IS_POST

我看到了 Apple 的做法,但我们看到了对 POST 请求的缓存响应,即使我们的响应不包含任何 Cache-Control 或 Expires 标头。这个实例iOS6不应该缓存和发送每个请求。这没有发生。
您引用的 HTTP 规范部分不能证明 iOS 6 的缓存行为是合理的。默认行为应该是不缓存 POST 响应(即,当未定义“Cache-Control”标头时)。该行为违反了规范,应被视为错误。任何构建 xml/json api Web 服务的人都应该使用“Cache-control: no-cache”来装饰他们的 POST 响应以解决这个问题。
POST 请求是非幂等的,这意味着它们不应被缓存,除非响应通过其响应标头明确建议这样做。
正如大卫所说,这明显违反了你引用的句子。如果没有“Cache-Control 或 Expires 标头字段”,则显然不包括适当的此类标头。然而,您自己的调查显示它在这种情况下缓存。请编辑您的答案。
有谁知道结果在设备上缓存了多长时间?我试过杀死 safari 并重新启动我的手机,但它仍然被缓存。我知道它可以清除浏览器缓存,但我想知道曾经遇到问题的用户需要多长时间才能消失。不是每个人都会想到清除缓存...
D
Dave

我希望这对其他在这个问题上碰壁的开发人员有用。我发现以下任何一项都会阻止 iOS 6 上的 Safari 缓存 POST 响应:

在请求标头中添加 [cache-control: no-cache]

添加可变 URL 参数,例如当前时间

在响应标头中添加 [pragma: no-cache]

在响应标头中添加 [cache-control: no-cache]

我的 Javascript 中的解决方案如下(我所有的 AJAX 请求都是 POST)。

$.ajaxSetup({
    type: 'POST',
    headers: { "cache-control": "no-cache" }
});

我还将 [pragma: no-cache] 标头添加到我的许多服务器响应中。

如果您使用上述解决方案,请注意您进行的任何 $.ajax() 调用都设置为 global: false 将不会使用 $.ajaxSetup() 中指定的设置,因此您需要再次添加标头。


这是该错误的正确解决方案。错误是 iOS 6 将从它的缓存中为 POST 请求提供服务,而不是将它们发送到服务器。该错误不是它缓存来自 POST 请求的响应(这是允许的)。如果您仍希望响应从缓存中检索到的 POST 请求,以用于对该 URI 的后续 GET 请求,请使用此解决方案。
这对我有用,但我不明白如何。我已经在我的 ajaxSetup 中指定了 cache: false,并查看了请求标头,这归结为 Cache-Control: no-cache 和 Pragma: no-cache - 但它仍会缓存在 iPad 上。然后,当我在 ajaxSetup 中添加标头:{“cache-control”:“no-cache”} 时,它会将 Cache-Control 标头加倍为“no-cache, no-cache” - 并停止缓存。这里发生了什么事?
完美运行 - 您还可以将请求添加为参数 $.ajax({type: 'POST', headers: { 'cache-control': 'no-cache' }, etc.})
什么是 [pragma: no-cache]? pragma 键是做什么用的?
我也认为这是最好的方法,而不是使用附加参数的解决方法。我们只在需要它的调用上添加了它,对于始终具有相同返回的调用,缓存对最终用户来说可能是一件好事。
C
Charles

假设您使用 jQuery,所有 Web 服务请求的简单解决方案:

$.ajaxPrefilter(function (options, originalOptions, jqXHR) {
    // you can use originalOptions.type || options.type to restrict specific type of requests
    options.data = jQuery.param($.extend(originalOptions.data||{}, { 
      timeStamp: new Date().getTime()
    }));
});

阅读有关 jQuery 预过滤器调用 here 的更多信息。

如果您不使用 jQuery,请查看您选择的库的文档。它们可能具有类似的功能。


它对我不起作用,服务器响应:“无效的原始 JSON:timeStamp”asp.net / iis 7.5
$.ajax({ "cache": false ...}) 怎么样?它会在附加 _=[TIMESTAMP] 时起作用吗? (我没有这样的设备来测试它)
我已经发布了 Karussell 提出的解决方案的完整实现。请看下面我的回答。
@卡鲁塞尔。刚刚尝试设置 $.ajax({ "cache": false ...})。这不能解决 iOS6 上 POST 请求的问题。大概是因为 JQuery 根据他们的文档假设没有浏览器愚蠢到可以缓存发布请求。 “使用 POST 获取的页面永远不会被缓存,因此 jQuery.ajaxSetup() 中的缓存和 ifModified 选项对这些请求没有影响。”
这行不通。它不合并帖子参数。 Dave 的帖子是一个更好的解决方案。
P
Peter Mortensen

我刚刚在 PhoneGap 应用程序中也遇到了这个问题。我通过以下方式使用 JavaScript 函数 getTime() 解决了这个问题:

var currentTime = new Date();
var n = currentTime.getTime();
postUrl = "http://www.example.com/test.php?nocache="+n;
$.post(postUrl, callbackFunction);

我浪费了几个小时来弄清楚这一点。 Apple 最好通知开发人员这个缓存问题。


我将评论使用 {cache:false} 作为 $.post()$.ajaxSetup() 的选项,但根据 the docs,这些参数被忽略; jQuery 将“从不缓存”发布请求,但不考虑浏览器。也许更简洁的选择是使用 $.ajaxPrefilter() 为请求添加时间戳。
我花了将近 5 个小时来解决这个问题,最后添加时间戳就可以了function send_ajax(my_data,refresh) .. 参考这里stackoverflow.com/questions/14733772/…
T
Tadej

我从 ASP.NET webservice 获取数据的 webapp 遇到了同样的问题

这对我有用:

public WebService()
{
    HttpContext.Current.Response.Cache.SetCacheability(HttpCacheability.NoCache);
    ...
}

非常感谢!我快要疯了,想弄清楚为什么 iPhone 的行为与其他平台如此不同。这个特定于 ASP.NET 的解决方案为我节省了大量时间。
在 iOS6 上不起作用,请参阅我在线程末尾的回答
请!!!!仅在 IOS 6 上应用此条件,内容缓存对任何应用程序都至关重要。
g
goker

最后,我有一个解决上传问题的方法。

在 JavaScript 中:

var xhr = new XMLHttpRequest();
xhr.open("post", 'uploader.php', true);
xhr.setRequestHeader("pragma", "no-cache");

PHP 中:

header('cache-control: no-cache');

k
kiranvj

来自我自己的博文iOS 6.0 caching Ajax POST requests

如何解决:有多种方法可以防止请求缓存。推荐的方法是添加一个无缓存标头。这就是它的完成方式。

jQuery:

检查 iOS 6.0 并像这样设置 Ajax 标头:

$.ajaxSetup({ cache: false });

ZeptoJS:

检查 iOS 6.0 并像这样设置 Ajax 标头:

$.ajax({
    type: 'POST',
    headers : { "cache-control": "no-cache" },
    url : ,
    data:,
    dataType : 'json',
    success : function(responseText) {…}

服务器端

爪哇:

httpResponse.setHeader("Cache-Control", "no-cache, no-store, must-revalidate");

确保在将任何数据发送到客户端之前将其添加到页面顶部。

。网

Response.Cache.SetNoStore();

或者

Response.Cache.SetCacheability(System.Web.HttpCacheability.NoCache);

PHP

header('Cache-Control: no-cache, no-store, must-revalidate'); // HTTP 1.1.
header('Pragma: no-cache'); // HTTP 1.0.

.NET 的一个很好的无缓存属性 stackoverflow.com/questions/10011780/…
J
Jonathan

这个 JavaScript 片段非常适用于 jQuery 和 jQuery Mobile:

$.ajaxSetup({
    cache: false,
    headers: {
        'Cache-Control': 'no-cache'
    }
});

只需将它放在 JavaScript 代码中的某个位置(在加载 jQuery 之后,最好在执行 AJAX 请求之前),它应该会有所帮助。


P
Peter Mortensen

您还可以通过修改 jQuery Ajax 函数来解决此问题,方法是在 Ajax 函数的顶部执行以下操作(从 1.7.1 开始)(函数从第 7212 行开始)。此更改将为所有 POST 请求激活 jQuery 的内置反缓存功能。

(完整的脚本可在 http://dl.dropbox.com/u/58016866/jquery-1.7.1.js 获得。)

在第 7221 行下方插入:

if (options.type === "POST") {
    options.cache = false;
}

然后修改以下内容(从 ~7497 行开始)。

if (!s.hasContent) {
    // If data is available, append data to URL
    if (s.data) {
        s.url += (rquery.test(s.url) ? "&" : "?") + s.data;
        // #9682: remove data so that it's not used in an eventual retry
        delete s.data;
    }

    // Get ifModifiedKey before adding the anti-cache parameter
    ifModifiedKey = s.url;

    // Add anti-cache in URL if needed
    if (s.cache === false) {
        var ts = jQuery.now(),
        // Try replacing _= if it is there
        ret = s.url.replace(rts, "$1_=" + ts);

        // If nothing was replaced, add timestamp to the end.
        s.url = ret + ((ret === s.url) ? (rquery.test(s.url) ? "&" : "?") + "_=" + ts : "");
    }
}

至:

// More options handling for requests with no content
if (!s.hasContent) {
    // If data is available, append data to URL
    if (s.data) {
        s.url += (rquery.test(s.url) ? "&" : "?") + s.data;
        // #9682: remove data so that it's not used in an eventual retry
        delete s.data;
    }

    // Get ifModifiedKey before adding the anti-cache parameter
    ifModifiedKey = s.url;
}

// Add anti-cache in URL if needed
if (s.cache === false) {
    var ts = jQuery.now(),
    // Try replacing _= if it is there
    ret = s.url.replace(rts, "$1_=" + ts);

    // If nothing was replaced, add timestamp to the end.
    s.url = ret + ((ret === s.url) ? (rquery.test(s.url) ? "&" : "?") + "_=" + ts : "");
}

这不是更改 jQuery 或任何您不拥有的代码的好方法。 (每次您想要更新版本时,您都必须再次进行更改。(或者另一个开发人员更新并且程序不起作用))
如果您需要尽可能快的解决方案来减轻 Apple 的愚蠢行为,这是一种完全有效的方法。该解决方案已用于解决每天接收数百万次点击的大型网站的问题,它使我们能够通过更改一个文件来完成此操作。
您可以查看 jQuery.ajaxPrefiler,它允许您在发出之前修改您的 ajax 请求。您可以使用更优化和更新的安全代码将其存档。
preFilter 方法的问题是您需要注册过滤器。如果您有一个在每个页面加载时运行的通用脚本,那很好,但如果您没有,则必须为使用 ajax 的每个页面设置 preFilter。我面临的情况是,我们有一个 JQ 文件的公共位置,该文件用作 7 多个单独网站的资源。由于这个错误,我们每小时损失了数千英镑,而我建议的方法使我们能够通过更改一个文件在最短的时间内解决它。我原则上同意你的观点,但有时你必须务实!
然后,您可以再次将其添加到该文件的末尾。很好,你解决了它,你的公司一定为你高兴。
L
Lars Høidahl

GWT-RPC 服务的一个快速解决方法是将其添加到所有远程方法中:

getThreadLocalResponse().setHeader("Cache-Control", "no-cache");

我们大多数人在他们的 GWT 部署中都有数百个远程方法。是否有一种通用方法为所有请求设置缓存控制标头?
r
remcoder

这是 Baz1nga 答案的更新。由于 options.data 不是一个对象,而是一个字符串,我只是求助于连接时间戳:

$.ajaxPrefilter(function (options, originalOptions, jqXHR) {
  if (originalOptions.type == "post" || options.type == "post") {

    if (options.data && options.data.length)
      options.data += "&";
    else
      options.data = "";

    options.data += "timeStamp=" + new Date().getTime();
  }
});

添加时间戳是一个坏主意,请尝试使用 Dave 的解决方案。
C
Community

为了解决添加到主屏幕的 WebApp 的此问题,需要遵循两个投票最多的解决方法。需要在网络服务器上关闭缓存以防止新请求被缓存,并且需要向每个发布请求添加一些随机输入,以便已经缓存的请求能够通过。请参考我的帖子:

iOS6 - Is there a way to clear cached ajax POST requests for webapp added to home screen?

警告:对于通过在请求中添加时间戳而不关闭服务器上的缓存来实现解决方法的任何人。如果您的应用程序被添加到主屏幕,现在将缓存每个发布响应,清除 safari 缓存不会清除它并且它似乎不会过期。除非有人有办法清除它,否则这看起来像是潜在的内存泄漏!


所有响应都会缓存到手机上的文件或内存中吗?
我不是这种情况。我在我的 url 上附加了一个时间戳(不是发布参数),它在从 safari 浏览和保存到主屏幕时都可以正常工作。
B
Brian Ogden

iPad 4/iOS 6 不适合我的事情:

我的请求包含: Cache-Control:no-cache

//asp.net's:
HttpContext.Current.Response.Cache.SetCacheability(HttpCacheability.NoCache)

在我的 jQuery ajax 调用中添加 cache: false

 $.ajax(
        {
            url: postUrl,
            type: "POST",
            cache: false,
            ...

只有这样做了:

var currentTime = new Date();
var n = currentTime.getTime();
postUrl = "http://www.example.com/test.php?nocache="+n;
$.post(postUrl, callbackFunction);

什么是反对票?这是重要信息缓存:false 不适用于 iPad4/iOS6,//asp.net 的:HttpContext.Current.Response.Cache.SetCacheability(HttpCacheability.NoCache)
后人:从 2017 年开始,$.ajax cache: false 将使用查询参数 _=Date.prototype.getTime() 附加 url,因此不再需要手动附加时间戳。
S
Spiff

这就是 GWT-RPC 的解决方法

class AuthenticatingRequestBuilder extends RpcRequestBuilder 
{
       @Override
       protected RequestBuilder doCreate(String serviceEntryPoint) 
       {
               RequestBuilder requestBuilder = super.doCreate(serviceEntryPoint);           
               requestBuilder.setHeader("Cache-Control", "no-cache");

               return requestBuilder;
       }
}

AuthenticatingRequestBuilder builder = new AuthenticatingRequestBuilder();
((ServiceDefTarget)myService).setRpcRequestBuilder(builder);    

P
Peter Mortensen

我在 ASP.NET 中的解决方法(页面方法、网络服务等)

protected void Application_BeginRequest(object sender, EventArgs e)
{
    Response.Cache.SetCacheability(HttpCacheability.NoCache);
}

I
Ivo Jansch

虽然添加缓存破坏器参数以使请求看起来不同似乎是一个可靠的解决方案,但我建议不要这样做,因为它会损害任何依赖于实际缓存发生的应用程序。使 API 输出正确的标头是最好的解决方案,即使这比向调用者添加缓存破坏器稍微困难一些。


虽然我同意你的大多数情况,但我认为这个问题的真正解决方案是让 Apple 正确实现 HTTP。考虑到这一点,在此之前,我不会责怪许多开发人员实施最简单的解决方案。对我来说,修改 jquery 实现是最简单的修复,因为它允许我进行一次编辑并确信它对我的整个站点都是有效的。
c
cbmeeks

对于那些使用 Struts 1 的人,这是我解决问题的方法。

web.xml

<filter>
    <filter-name>SetCacheControl</filter-name>
    <filter-class>com.example.struts.filters.CacheControlFilter</filter-class>
</filter>

<filter-mapping>
    <filter-name>SetCacheControl</filter-name>
    <url-pattern>*.do</url-pattern>
    <http-method>POST</http-method>
</filter-mapping>

com.example.struts.filters.CacheControlFilter.js

package com.example.struts.filters;

import java.io.IOException;
import java.util.Date;
import javax.servlet.*;
import javax.servlet.http.HttpServletResponse;

public class CacheControlFilter implements Filter {

        public void doFilter(ServletRequest request, ServletResponse response,
                     FilterChain chain) throws IOException, ServletException {

        HttpServletResponse resp = (HttpServletResponse) response;
        resp.setHeader("Expires", "Mon, 18 Jun 1973 18:00:00 GMT");
        resp.setHeader("Last-Modified", new Date().toString());
        resp.setHeader("Cache-Control", "no-store, no-cache, must-revalidate, max-age=0, post-check=0, pre-check=0");
        resp.setHeader("Pragma", "no-cache");

        chain.doFilter(request, response);
    }

    public void init(FilterConfig filterConfig) throws ServletException {
    }

    public void destroy() {
    }

}

S
ShadeTreeDeveloper

我能够通过结合使用 $.ajaxSetup 并将时间戳附加到我的帖子的网址(而不是帖子参数/正文)来解决我的问题。这是基于先前答案的建议

$(document).ready(function(){
    $.ajaxSetup({ type:'POST', headers: {"cache-control","no-cache"}});

    $('#myForm').submit(function() {
        var data = $('#myForm').serialize();
        var now = new Date();
        var n = now.getTime();
        $.ajax({
            type: 'POST',
            url: 'myendpoint.cfc?method=login&time='+n,
            data: data,
            success: function(results){
                if(results.success) {
                    window.location = 'app.cfm';
                } else {
                    console.log(results);
                    alert('login failed');
                }
            }
        });
    });
});

G
Giacomo1968

我想你已经解决了你的问题,但让我分享一个关于网络缓存的想法。

确实,您可以在您使用的每种语言(服务器端、客户端)中添加许多标头,并且您可以使用许多其他技巧来避免 Web 缓存,但始终认为您永远无法知道客户端从哪里连接到您的服务器,你永远不知道他是否使用了使用 Squid 或其他缓存产品的酒店“热点”连接。

如果用户正在使用代理来隐藏他的真实位置等……避免缓存的唯一方法是请求中的时间戳,如果未使用的话。

例如:

/ajax_helper.php?ts=3211321456

然后,您必须传递的每个缓存管理器都没有在缓存存储库中找到相同的 URL,然后重新下载页面内容。


旧答案,但我的两分钱:这通常是一个很好的建议,大多数有能力的 Web 开发人员都理解,但在 jQuery 的特定情况下,如果你创建一个 $.ajax 并将选项设置为 {cache:false},那么 jQuery 本身就会自动在幕后添加缓存清除,而您无需执行任何其他操作。
B
BoltClock

根据应用程序,您现在可以在 iOS 6 中使用 Safari>Advanced>Web Inspector 解决问题,这有助于解决这种情况。

将手机连接到 Mac 上的 Safari,然后使用开发人员菜单对 Web 应用程序进行故障排除。

更新到 iOS6 后清除 iPhone 上的网站数据,包括特定于使用 Web 视图的应用程序。只有一个应用程序有问题,这在 IOS6 Beta 测试期间解决了它,从那时起没有真正的问题。

您可能还需要查看您的应用程序,如果在自定义应用程序的 WebView 中,请查看 NSURLCache。

https://developer.apple.com/library/ios/#documentation/Cocoa/Reference/Foundation/Classes/NSURLCache_Class/Reference/Reference.html#//apple_ref/doc/uid/TP40003754

我想这取决于您的问题、实施等的真实性质。..

参考:$.ajax 调用


虽然这不能直接解决最初的问题,但它对于能够解决一般设备上的问题非常有用,所以我赞成它。
C
CM Kanode

我找到了一种解决方法,让我对它为什么起作用感到好奇。在阅读 Tadej 关于 ASP.NET Web 服务的回答之前,我试图想出一些可行的方法。

我并不是说这是一个很好的解决方案,但我只是想在这里记录一下。

主页:包括一个 JavaScript 函数 checkStatus()。该方法调用另一个方法,该方法使用 jQuery AJAX 调用来更新 html 内容。我使用 setInterval 调用 checkStatus()。当然,我遇到了缓存问题。

解决方法:使用另一个页面调用更新。

在主页上,我设置了一个布尔变量 runUpdate,并将以下内容添加到 body 标记中:

<iframe src="helper.html" style="display: none; visibility: hidden;"></iframe>

在 helper.html 中:

<meta http-equiv="refresh" content="5">
<script type="text/javascript">
    if (parent.runUpdate) { parent.checkStatus(); }
</script>

因此,如果从主页调用 checkStatus(),我会得到缓存的内容。如果我从子页面调用 checkStatus,我会得到更新的内容。


A
Adriano Rosa

虽然我的登录和注册页面在 Firefox、IE 和 Chrome 中的工作方式就像一个魅力......我一直在为 IOS 和 OSX 的 Safari 中努力解决这个问题,几个月前我在 SO 上找到了一种解决方法。

<body onunload="">

或通过 javascript

<script type="text/javascript">
window.onunload = function(e){
    e.preventDefault();
    return;
};
</script>   

这有点丑陋,但可以工作一段时间。

我不知道为什么,但是将 null 返回到 onunload 事件页面不会在 Safari 中缓存。


C
CaptureWiz

我们发现运行 iOS 版本 9 和 10 的旧 iPhone 和 iPad 偶尔会返回虚假的空白 AJAX 结果,这可能是由于 Apple 降低了 CPU 速度。返回空白结果时,iOS 不会调用服务器,就像从缓存中返回结果一样。频率变化很大,大约 10% 到 30% 的 AJAX 调用返回空白。

很难相信解决方案。只需等待 1 秒,然后再次调用。在我们的测试中,只需要重复一次,但我们编写的代码最多可以调用 4 次。我们不确定是否需要等待 1 秒,但我们不想冒着让服务器承受大量重复调用的风险。

我们发现问题发生在两个不同的 AJAX 调用上,它们使用不同的数据调用不同的 API 文件。但我担心它可能发生在任何 AJAX 调用上。我们只是不知道,因为我们不会检查每个 AJAX 结果,也不会在旧设备上多次测试每个调用。

两个问题 AJAX 调用都在使用:POST, Asynchronously = true, setRequestHeader = ('Content-Type', 'application/x-www-form-urlencoded')

当问题发生时,通常只有一个 AJAX 调用正在进行。所以这不是由于重叠的 AJAX 调用。有时问题会在设备繁忙时发生,但有时不会,而且如果没有 DevTools,我们真的不知道当时发生了什么。

iOS 13 没有这样做,Chrome 或 Firefox 也没有。我们没有任何运行 iOS 11 或 12 的测试设备。也许其他人可以测试这些设备?

我在这里注意到这一点,因为在搜索此问题时,此问题是 Google 搜索结果中排名靠前的。


P
Peter Mortensen

只有在 IIS 中添加 pragma:no-cache 标头后,它才能与 ASP.NET 一起使用。 Cache-Control: no-cache 还不够。


f
fred1234

我建议一种解决方法来修改函数签名,如下所示:

getNewRecordID(intRecordType, strTimestamp) 然后总是传入一个 TimeStamp 参数,并在服务器端丢弃该值。这可以解决这个问题。