NSHTTPCookieStorage 状态不会在应用程序退出时保存。那里有任何明确的知识/文档吗?

发布于 2024-11-04 01:26:47 字数 2357 浏览 1 评论 0原文

正在努力解决这个问题,并且不愿意实施自定义 cookie 管理系统。

iOS 的 HTTP 实现的某些隐藏级别似乎无法正确管理无会话 cookie。每当 HTTP 响应设置或删除 cookie 时,立即检查 NSHTTPCookieStorage cookie 将产生预期结果并指示正确的 sessionOnly 值。

但是,如果应用程序在响应更新 cookie 后很快退出,则重新启动时,这些 sessionOnly=FALSE cookie 将恢复到以前的状态,并且最近的更新会丢失。

无论是通过响应头还是 NSHTTPCookieStorage setCookie: 设置/删除 cookie 都没有区别。

一定有一些缓存/同步巫术在幕后进行。 cookie 变得持久化所需的时间最长可达 5 秒。

有谁已经或可以指出这种行为的明确解释吗?这是一个简单明了的错误吗?或者一些我无法理解其用途的未记录功能?

您可以使用一些代码来重现:

- (void)applicationDidBecomeActive:(UIApplication *)application
{

    [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookieAcceptPolicy:NSHTTPCookieAcceptPolicyAlways];

    NSHTTPCookie *cookie;
    for (cookie in [NSHTTPCookieStorage sharedHTTPCookieStorage].cookies) {
        NSLog(@"%@=%@", cookie.name, cookie.value);
    }

    NSMutableDictionary *cookieProperties = [NSMutableDictionary dictionary];
    [cookieProperties setObject:@"testCookie" forKey:NSHTTPCookieName];
    [cookieProperties setObject:[NSString stringWithFormat:@"%f", [[NSDate date] timeIntervalSince1970]] forKey:NSHTTPCookieValue];
    [cookieProperties setObject:@"www.example.com" forKey:NSHTTPCookieDomain];
    [cookieProperties setObject:@"www.example.com" forKey:NSHTTPCookieOriginURL];
    [cookieProperties setObject:@"/" forKey:NSHTTPCookiePath];
    [cookieProperties setObject:@"0" forKey:NSHTTPCookieVersion];

    // set expiration to one month from now
    [cookieProperties setObject:[[NSDate date] dateByAddingTimeInterval:2629743] forKey:NSHTTPCookieExpires];

    cookie = [NSHTTPCookie cookieWithProperties:cookieProperties];
    [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookie:cookie];

}

此代码应在每次启动时输出一个新值。相反,您会看到,如果您快速退出应用程序,则该值不会改变。

一些可能相关的堆栈溢出问题:

iphone NSHTTPCookieStorage 在应用程序重新打开时可用?

iPhone:NSHTTPCookie 是应用重新启动时不保存

NSHTTPCookie 拒绝删除

如果应用程序终止,则删除的 NSHTTPCookie 返回

Struggling with this problem and loath to implement a custom cookie management system.

It appears some hidden level of iOS's implementation of HTTP fails to manage sessionless cookies properly. Any time an HTTP response sets or deletes a cookie, immediate inspection of NSHTTPCookieStorage cookies will yield the expected results and indicate the correct sessionOnly value.

But if the app quits soon after a response updates cookies, upon relaunch those sessionOnly=FALSE cookies will be reverted to some previous state and the most recent updates lost.

Whether the cookies are set/deleted by a response header or NSHTTPCookieStorage setCookie: makes no difference.

Some caching/syncing voodoo must be going on behind the scenes. The time it takes for the cookie to become persistent can be up to 5 seconds.

ANYONE out there who has or can point to some definitive explanation of this behavior? Is it a bug, plain and simple? Or some undocumented feature whose purpose I can't comprehend?

Some code you can use to reproduce:

- (void)applicationDidBecomeActive:(UIApplication *)application
{

    [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookieAcceptPolicy:NSHTTPCookieAcceptPolicyAlways];

    NSHTTPCookie *cookie;
    for (cookie in [NSHTTPCookieStorage sharedHTTPCookieStorage].cookies) {
        NSLog(@"%@=%@", cookie.name, cookie.value);
    }

    NSMutableDictionary *cookieProperties = [NSMutableDictionary dictionary];
    [cookieProperties setObject:@"testCookie" forKey:NSHTTPCookieName];
    [cookieProperties setObject:[NSString stringWithFormat:@"%f", [[NSDate date] timeIntervalSince1970]] forKey:NSHTTPCookieValue];
    [cookieProperties setObject:@"www.example.com" forKey:NSHTTPCookieDomain];
    [cookieProperties setObject:@"www.example.com" forKey:NSHTTPCookieOriginURL];
    [cookieProperties setObject:@"/" forKey:NSHTTPCookiePath];
    [cookieProperties setObject:@"0" forKey:NSHTTPCookieVersion];

    // set expiration to one month from now
    [cookieProperties setObject:[[NSDate date] dateByAddingTimeInterval:2629743] forKey:NSHTTPCookieExpires];

    cookie = [NSHTTPCookie cookieWithProperties:cookieProperties];
    [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookie:cookie];

}

This code should output a new value on every launch. Instead you will see that if you quit the app quickly the value is unchanged.

Some possibly related stack overflow questions:

iphone NSHTTPCookieStorage avaible on app reopen?

iPhone: NSHTTPCookie is not saved across app restarts

NSHTTPCookies refuse to be deleted

deleted NSHTTPCookie returns if app is terminated

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

冷…雨湿花 2024-11-11 01:26:47

我认为答案在于您问题中链接的其中一个帖子:

我制作了一个示例项目来重现此问题 - 并发现它
仅当应用程序收到 SIGKILL 信号时才会发生,例如
调试器在 Xcode 中停止。在我的实验中,未处理
异常、崩溃、exit() 和 abort() 不会导致
NSHTPPCookieStorage 会丢失数据。

因为这看起来像是一个仅调试问题(仅在使用时才会发生)
调试器),我关闭了之前填充的雷达。

您可以通过正常重新启动手机并观察对 NSHTTPCookieStorage 的所有更改是否正确保存并重新加载来测试这一点。

I think the answer lies in one of the SO posts linked to in your question:

I made a sample project to reproduce this issue — and found that it
would only occur when the app receives a SIGKILL signal, like when the
debugger is stopped from within Xcode. In my experiments, unhandled
exceptions, crashes, exit() and abort() don't cause
NSHTPPCookieStorage to loose data.

As this looks like a debugging-only issue (it only occurs when using
the debugger), I closed the radar I filled previously.

You can test this by restarting the phone normally and observing that all changes to NSHTTPCookieStorage are correctly persisted and reloaded.

无敌元气妹 2024-11-11 01:26:47

我也遇到了同样的问题,但我找到了解决方案。我保存了浏览器创建的 cookie,然后在应用程序重新启动时重新创建它们。

1) 当 uiwebview 创建 cookie 时保存它们。

 NSMutableArray *cookieArray = [[NSMutableArray alloc] init];
    for (NSHTTPCookie *cookie in [[NSHTTPCookieStorage sharedHTTPCookieStorage] cookies]) {
        [cookieArray addObject:cookie.name];
        NSMutableDictionary *cookieProperties = [NSMutableDictionary dictionary];
        [cookieProperties setObject:cookie.name forKey:NSHTTPCookieName];
        [cookieProperties setObject:cookie.value forKey:NSHTTPCookieValue];
        [cookieProperties setObject:cookie.domain forKey:NSHTTPCookieDomain];
        [cookieProperties setObject:cookie.path forKey:NSHTTPCookiePath];
        [cookieProperties setObject:[NSNumber numberWithInt:cookie.version] forKey:NSHTTPCookieVersion];

        [cookieProperties setObject:[[NSDate date] dateByAddingTimeInterval:2629743] forKey:NSHTTPCookieExpires];

        [[NSUserDefaults standardUserDefaults] setValue:cookieProperties forKey:cookie.name];
        [[NSUserDefaults standardUserDefaults] synchronize];

    }

    [[NSUserDefaults standardUserDefaults] setValue:cookieArray forKey:@"cookieArray"];
    [[NSUserDefaults standardUserDefaults] synchronize];

2)现在在应用程序重新启动时重新创建它们:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{

    NSMutableArray* cookieDictionary = [[NSUserDefaults standardUserDefaults] valueForKey:@"cookieArray"];
     NSLog(@"cookie dictionary found is %@",cookieDictionary);

    for (int i=0; i < cookieDictionary.count; i++) 
{


        NSLog(@"cookie found is %@",[cookieDictionary objectAtIndex:i]);
        NSMutableDictionary* cookieDictionary1 = [[NSUserDefaults standardUserDefaults] valueForKey:[cookieDictionary objectAtIndex:i]];
        NSHTTPCookie *cookie = [NSHTTPCookie cookieWithProperties:cookieDictionary1];
        [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookie:cookie];


 }

    // other code

}

谢谢

I also got the same problem but i found a solution. I saved the cookies as it get created by the browser and then recreate them as app restarts.

1) Save cookie when they get created by uiwebview.

 NSMutableArray *cookieArray = [[NSMutableArray alloc] init];
    for (NSHTTPCookie *cookie in [[NSHTTPCookieStorage sharedHTTPCookieStorage] cookies]) {
        [cookieArray addObject:cookie.name];
        NSMutableDictionary *cookieProperties = [NSMutableDictionary dictionary];
        [cookieProperties setObject:cookie.name forKey:NSHTTPCookieName];
        [cookieProperties setObject:cookie.value forKey:NSHTTPCookieValue];
        [cookieProperties setObject:cookie.domain forKey:NSHTTPCookieDomain];
        [cookieProperties setObject:cookie.path forKey:NSHTTPCookiePath];
        [cookieProperties setObject:[NSNumber numberWithInt:cookie.version] forKey:NSHTTPCookieVersion];

        [cookieProperties setObject:[[NSDate date] dateByAddingTimeInterval:2629743] forKey:NSHTTPCookieExpires];

        [[NSUserDefaults standardUserDefaults] setValue:cookieProperties forKey:cookie.name];
        [[NSUserDefaults standardUserDefaults] synchronize];

    }

    [[NSUserDefaults standardUserDefaults] setValue:cookieArray forKey:@"cookieArray"];
    [[NSUserDefaults standardUserDefaults] synchronize];

2) Now recreate them as app restarts:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{

    NSMutableArray* cookieDictionary = [[NSUserDefaults standardUserDefaults] valueForKey:@"cookieArray"];
     NSLog(@"cookie dictionary found is %@",cookieDictionary);

    for (int i=0; i < cookieDictionary.count; i++) 
{


        NSLog(@"cookie found is %@",[cookieDictionary objectAtIndex:i]);
        NSMutableDictionary* cookieDictionary1 = [[NSUserDefaults standardUserDefaults] valueForKey:[cookieDictionary objectAtIndex:i]];
        NSHTTPCookie *cookie = [NSHTTPCookie cookieWithProperties:cookieDictionary1];
        [[NSHTTPCookieStorage sharedHTTPCookieStorage] setCookie:cookie];


 }

    // other code

}

thanks

沧桑㈠ 2024-11-11 01:26:47

听起来像需要一个底层 NSUserDefaults 风格的“同步”调用。我认为最好的办法是在标准 NSUserDefaults 中单独管理应用程序的所有 cookie,并在启动时将任何丢失的 cookie 同步到 NSHTTPCookieStorage 中。或者如果你勇敢的话,看看是否有一些私有同步方法:)

Sounds like an underlying NSUserDefaults-style "synchronize" call is required. I think your best shot is managing all your app's cookies separately in the standard NSUserDefaults and synching any missing ones into the NSHTTPCookieStorage's at startup. Or see if there's some private synchronize method if you're feeling brave :)

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文