I need to share cookies between WKWebView instances - for this i'm using a single WKWebViewConfiguration instance which is then used to init every WKWebView.
In order to do this I assume I have to use a shared WKProcessPool, ex:
let websiteDataStore = WKWebsiteDataStore.default()
websiteDataStore.httpCookieStore.add(self)
let configuration = WKWebViewConfiguration()
configuration.websiteDataStore = websiteDataStore
configuration.processPool = WKProcessPool() /* !!! */
However doing so causes the setCookie completion handler to NOT fire.
let cookieStore = self.webConfiguration.websiteDataStore.httpCookieStore
cookieStore.setCookie(cookie, completionHandler: {
})
If i do not set the WKProcessPool (*) instance - then completion block fires fine, but obviously WebViews do not see the cookies ; / Did anyone encounter this? Ideas on how else to share the cookies?
iOS: 11.2.6
Use a WKHTTPCookieStore to specify the initial cookies for your webpages, and to manage cookies for your web content. For example, you might use this object to delete the cookie for the current session when the user logs out. To detect when the webpage changes a cookie, install a cookie observer using the add (_:) method.
An object that manages the HTTP cookies associated with a particular web view. Use a WKHTTPCookieStore to specify the initial cookies for your webpages, and to manage cookies for your web content. For example, you might use this object to delete the cookie for the current session when the user logs out.
To add cookies to a WKWebview we can use the cookie store WKHTTPCookieStore which has a set of methods for cookie manipulation, setCookie, getAllCookies and delete cookie. All of those methods work with a completion handler which gets called after the operation was made.
Previous to iOS 11, the cookies used by the app would be shared and stored in the NSHTTPCookieStorage . UIWebView would use cookies from this cookie storage (parent app cookie storage). All of those has changed with the introduction of WKHTTPCookieStore.
After further testing I've managed to find solution - although i'm not sure what is happening. In short - above completion handler fires OK after WKWebView is instantiated.
In my case I need to set some cookies after login (so no webviews are displayed ATM). So calling setCookie only queues these operations somewhere - they are flushed when web client is fired. If someone can link documentation - that's be great!
So as this issue is still present - I've finally got back to this. My solution for now is to:
Cache cookie value in keychain (every time app calls HTTPCookieStore.setCookie - which may complete or not (which is the problem)
When HTTPCookieStore.setCookie{ } completion block fires (confirmation that cookie was indeed set) i then remove the value from keychain and webview is now responsible for lifecycle of the cookie value)
On every start of app i check if cookie values are cached in keychain -> if so HTTPCookieStore.setCookie()
Above can loop infinitely UNTIL webview is actually opened.
My problem was with deleting cookies to log a user out of the application. The completion handler for getAllCookies()
was not firing, so what is working for me is forcing the webView
to reload which will flush the queue and delete the cookies.
webView.configuration.websiteDataStore.httpCookieStore.getAllCookies { cookies in
for cookie in cookies {
if cookie.name == "authentication" {
self.webView.configuration.websiteDataStore.httpCookieStore.delete(cookie)
}
}
}
webView.reload()
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With