如何删除 WKWebview cookies

问题描述 投票:0回答:14

现在我是这样做的

    NSHTTPCookie *cookie;
    NSHTTPCookieStorage *storage = [NSHTTPCookieStorage sharedHTTPCookieStorage];
    for (cookie in [storage cookies])
    {
        [storage deleteCookie:cookie];
    }

但它不适用于 iOS 8、64 位设备。

WKWebview 的 clean cookie 有什么其他方式吗?任何帮助将不胜感激。谢谢。

ios xcode uiwebview wkwebview wkwebviewconfiguration
14个回答
62
投票

Apple 为 iOS 9 和更新版本 发布了新的 API,因此现在我们可以使用以下代码删除为 WKWebView 存储的特定于域的 cookie。

Swift 4/5 版本:

let dataStore = WKWebsiteDataStore.default()
dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { records in
  dataStore.removeData(
    ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(),
    for: records.filter { $0.displayName.contains("facebook") },
    completionHandler: completion
  )
}

以下是Swift 3版本

let dataStore = WKWebsiteDataStore.default()
    dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { (records) in
        for record in records {
            if record.displayName.contains("facebook") {
                dataStore.removeData(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(), for: [record], completionHandler: {
                    print("Deleted: " + record.displayName);
                })
            }
        }
    }

Objective-C 版本 -

WKWebsiteDataStore *dateStore = [WKWebsiteDataStore defaultDataStore];
[dateStore
   fetchDataRecordsOfTypes:[WKWebsiteDataStore allWebsiteDataTypes]
   completionHandler:^(NSArray<WKWebsiteDataRecord *> * __nonnull records) {
     for (WKWebsiteDataRecord *record  in records) {
       if ( [record.displayName containsString:@"facebook"]) {
         [[WKWebsiteDataStore defaultDataStore]
             removeDataOfTypes:record.dataTypes
             forDataRecords:@[record]
             completionHandler:^{
               NSLog(@"Cookies for %@ deleted successfully",record.displayName);
             }
         ];
       }
     }
   }
 ];

上面的代码片段肯定适用于 iOS 9 及更高版本。不幸的是,如果我们在 iOS 9 之前的 iOS 版本中使用WKWebView,我们仍然必须坚持传统的方法并删除整个 cookies 存储,如下所示。

NSString *libraryPath = [NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES) objectAtIndex:0];
NSString *cookiesFolderPath = [libraryPath stringByAppendingString:@"/Cookies"];
NSError *errors;
[[NSFileManager defaultManager] removeItemAtPath:cookiesFolderPath error:&errors];

24
投票

Swift 3版本Sarat的回答:

let dataStore = WKWebsiteDataStore.default()
dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { (records) in
    for record in records {
        if record.displayName.contains("facebook") {
            dataStore.removeData(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(), for: [record], completionHandler: {
                print("Deleted: " + record.displayName);
            })
        }
    }
}

22
投票

支持iOS 11.0及以上版本

以下解决方案对我很有效:

步骤 1. 从

HTTPCookieStorage

中删除 Cookie

Step 2. 从

WKWebsiteDataStore
中获取数据记录并删除它们。

第 3 步。创建一个新的

WKProcessPool

创建 WKWebView 扩展:

extension WKWebView {

    func cleanAllCookies() {
        HTTPCookieStorage.shared.removeCookies(since: Date.distantPast)
        print("All cookies deleted")

        WKWebsiteDataStore.default().fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { records in
            records.forEach { record in
                WKWebsiteDataStore.default().removeData(ofTypes: record.dataTypes, for: [record], completionHandler: {})
                print("Cookie ::: \(record) deleted")
            }
        }
    }

    func refreshCookies() {
        self.configuration.processPool = WKProcessPool()
    }
}

用法:

override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(true)
        webView.cleanAllCookies()
        webView.refreshCookies()
    }

6
投票

这些选项都不适合我,但我找到了一个:

let config = WKWebViewConfiguration()
if #available(iOS 9.0, *) {
    config.websiteDataStore = WKWebsiteDataStore.nonPersistentDataStore()
} else {
     // I have no idea what to do for iOS 8 yet but this works in 9.
}

let webView = WKWebView(frame: .zero, configuration: config)

5
投票

在iOS9中:

//// Optional data
NSSet *websiteDataTypes
= [NSSet setWithArray:@[
                        WKWebsiteDataTypeDiskCache,
                        //WKWebsiteDataTypeOfflineWebApplicationCache,
                        WKWebsiteDataTypeMemoryCache,
                        //WKWebsiteDataTypeLocalStorage,
                        //WKWebsiteDataTypeCookies,
                        //WKWebsiteDataTypeSessionStorage,
                        //WKWebsiteDataTypeIndexedDBDatabases,
                        //WKWebsiteDataTypeWebSQLDatabases
                        ]];
//// All kinds of data
//NSSet *websiteDataTypes = [WKWebsiteDataStore allWebsiteDataTypes];
//// Date from
NSDate *dateFrom = [NSDate dateWithTimeIntervalSince1970:0];
//// Execute
[[WKWebsiteDataStore defaultDataStore] removeDataOfTypes:websiteDataTypes modifiedSince:dateFrom completionHandler:^{
    // Done
    NSLog(@"remove done");
}];

3
投票

在所有现有答案的基础上,如果您尝试清除特定 WKWebView 实例“webView”的 cookie 和数据记录,而不是“默认”存储的 cookie 和数据记录,您可以使用以下内容:

let dataStore = webView.configuration.websiteDataStore
let cookieStore = dataStore.httpCookieStore
cookieStore.getAllCookies {
    $0.forEach { cookie in
        cookieStore.delete(cookie)
    }
}
dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { records in
    records.forEach { record in
        dataStore.removeData(ofTypes: record.dataTypes, for: [record]) { }
    }
}

2
投票

Swift 4 和更短的版本:

let dataStore = WKWebsiteDataStore.default()
dataStore.fetchDataRecords(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes()) { records in
    dataStore.removeData(ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(),
                         for: records.filter { $0.displayName.contains("facebook") },
                         completionHandler: completion)
}

2
投票

斯威夫特 5

    /// old API cookies
    for cookie in HTTPCookieStorage.shared.cookies ?? [] {
        HTTPCookieStorage.shared.deleteCookie(cookie)
    }
    /// URL cache
    URLCache.shared.removeAllCachedResponses()
    /// WebKit cache
    let date = Date(timeIntervalSince1970: 0)
    WKWebsiteDataStore.default().removeData(
        ofTypes: WKWebsiteDataStore.allWebsiteDataTypes(),
        modifiedSince: date,
        completionHandler:{})

1
投票

除了清除共享 cookie 存储中的 cookie 之外,我还会尝试清除缓存 (NSURLCache) 并丢弃 WKWebView 并使用新的 WKProcessPool 创建一个新的


0
投票

似乎 NSHTTPCookieStorage 现在在 iOS 8.2 中被用于根据需要正确清除 cookie。我已经发布了一个应用程序,它会在打开基于 WKWebView 的登录之前运行此代码:

NSHTTPCookieStorage *storage = [NSHTTPCookieStorage sharedHTTPCookieStorage];
for (NSHTTPCookie *cookie in [storage cookies])
{
    [storage deleteCookie:cookie];
}

在 iOS 8.2 之前,网站会使用保存的 cookie 自动登录,现在它会正确地要求用户重新登录。所有这一切都发生在我没有发布应用程序更新的情况下。 :)


0
投票

Esqarrouth 的回答只对了一部分。
正确的 swift 版本是:

var libraryPath : String = NSFileManager().URLsForDirectory(.LibraryDirectory, inDomains: .UserDomainMask).first!.path!
libraryPath += "/Cookies"
do {
    try NSFileManager.defaultManager().removeItemAtPath(libraryPath)
} catch {
    print("error")
}
NSURLCache.sharedURLCache().removeAllCachedResponses()

0
投票

WKWebview 在 [NSHTTPCookieStorage sharedHTTPCookieStorage] 中不存储任何内容。

清除 WKWebsiteDataStore 将解决这个问题。

还是IOS8使用WKwebview,这个方法不适用..


0
投票

在 WKWebView 中,写入和读取需要花费一些时间,因此当您有时获取 cookie 时,您会得到更新的 cookie,但有时它会是旧的,并且您会在任何服务器请求上出错。我在 3 天内遇到了这个问题,

解决方案:无需在WKWebsiteDataStore中存储cookie。

获取饼干:

斯威夫特:

extension WKWebView {
private var httpCookieStore: WKHTTPCookieStore  { return WKWebsiteDataStore.default().httpCookieStore }
func getCookies(for domain: String? = nil, completion: @escaping ([String : Any])->())  {
        var cookieDict = [String : AnyObject]()
        httpCookieStore.getAllCookies { cookies in
            for cookie in cookies {
                if let domain = domain {
                    if cookie.domain.contains(domain) {
                        cookieDict[cookie.name] = cookie.properties as AnyObject?
                    }
                } else {
                    cookieDict[cookie.name] = cookie.properties as AnyObject?
                }
            }
            completion(cookieDict)
        }
    }
}

目标-c:

-(void )getAllCookies
{
    NSMutableString *updatedCockies= [[NSMutableString alloc] init];
    if (@available(iOS 11.0, *)) {
        WKHTTPCookieStore *cookieStore = _webView.configuration.websiteDataStore.httpCookieStore;
        NSLog(@"cookieStore *********************: %@",cookieStore);
        [cookieStore getAllCookies:^(NSArray* cookies) {
            NSHTTPCookie *cookie;
            for(cookie in cookies){
               NSLog(@"%@",cookie)
            }
            self->updatedCookie = updatedCockies;
            NSLog(@"cookie *********************: %@", self->updatedCookie);
        }];
    }
}

每次你想要新的cookie所以你需要写下面的代码: 鉴于夏皮奥

斯威夫特:

let config = WKWebViewConfiguration()
if #available(iOS 9.0, *) {
    config.websiteDataStore = WKWebsiteDataStore.nonPersistentDataStore()
} else {
     // I have no idea what to do for iOS 8 yet but this works in 9.
}

let webView = WKWebView(frame: .zero, configuration: config)

目标C--

WKWebViewConfiguration *wkWebConfig = [WKWebViewConfiguration new];
    wkWebConfig.websiteDataStore = [WKWebsiteDataStore nonPersistentDataStore];


self.webView = [[WKWebView alloc] initWithFrame: CGRectZero
                                      configuration: wkWebConfig];

*********每次你都会得到新的饼干********


-6
投票

Swift版本:

var libraryPath = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.LibraryDirectory, NSSearchPathDomainMask.UserDomainMask, false).first!
libraryPath += "/Cookies"

do {
  let result = try NSFileManager.defaultManager().removeItemAtPath(libraryPath)
  print(result)
} catch {
  print("error")
}
NSURLCache.sharedURLCache().removeAllCachedResponses()
© www.soinside.com 2019 - 2024. All rights reserved.