I'm using the Pinterest SDK to download a Pinterest Pin's link, (sample link that I get back from the server: https://www.pinterest.com/r/pin/186195765822871832/4801566892554728205/77314e40aeb26c0dc412e9cfa82f8dccc401fdb2b9806a3fe17ba8bafdb50510).
About 5 days ago I started getting 404 errors in my NSURLSesssion when trying to access similar links that I'd pulled down from Pinterest.
A friend said that he believes Pinterest must now require cookies to access that link.
How can I configure my session so that I can use cookies and get a 200 response back from Pinterest?
UPDATED CODE:
import UIKit
import PlaygroundSupport
var url = URL(string: "https://www.pinterest.com/r/pin/186195765822871832/4801566892554728205/77314e40aeb26c0dc412e9cfa82f8dccc401fdb2b9806a3fe17ba8bafdb50510")
var getSourceURLFromPinterest: URLSessionDataTask? = nil
let sessionConfig: URLSessionConfiguration = URLSessionConfiguration.default
sessionConfig.timeoutIntervalForRequest = 30.0
sessionConfig.timeoutIntervalForResource = 30.0
let cookieJar = HTTPCookieStorage.shared
let cookieHeaderField = ["Set-Cookie": "key=value, key2=value2"]
let cookies = HTTPCookie.cookies(withResponseHeaderFields: cookieHeaderField, for: url!)
HTTPCookieStorage.shared.setCookies(cookies, for: url, mainDocumentURL: url)
let session = URLSession(configuration: sessionConfig)
getSourceURLFromPinterest = session.dataTask(with: url! as URL) { (data: Data?, response: URLResponse?, error: Error?) -> Void in
if error != nil {
print("error is \(error)")
}
if response == nil {
print("no response")
} else if let _ = data {
//Config Request
let request = NSMutableURLRequest(
url: (response?.url)!,
cachePolicy: .reloadIgnoringLocalAndRemoteCacheData,
timeoutInterval: 30.0)
request.httpMethod = "HEAD"
var statusCode = Int()
let session = URLSession.shared
let checkURLForResponse = session.dataTask(with: request as URLRequest) {urlData, myResponse, responseError in
if let httpResponse = myResponse as? HTTPURLResponse {
statusCode = httpResponse.statusCode
switch statusCode {
case _ where statusCode < 500 && statusCode > 299 && statusCode != 405: //whitelisted 405 to exclude Amazon.com false errors
print("status code \(statusCode) for \(url)")
default:
break;
}
} else { print("***NO httpResponse for \(url)") }
}
checkURLForResponse.resume()
}
}
getSourceURLFromPinterest!.resume()
PlaygroundPage.current.needsIndefiniteExecution = true
The other answers may work generally, but specifically for me this is how I coded the request in order to get a response from Pinterest's server. Note that specifically what I am doing I think is related to a possible bug in Pinterest's server, see: https://github.com/pinterest/ios-pdk/issues/124
I commented out my personal Pinterest session ID
var cookieSession = String()
var cookieCSRFToken = String()
var myWebServiceUrl = URL(string: "https://www.pinterest.com/r/pin/186195765821344905/4801566892554728205/a9bb098fcbd6b73c4f38a127caca17491dafc57135e9bbf6a0fdd61eab4ba885")
let requestOne = URLRequest(url: myWebServiceUrl!)
let sessionOne = URLSession.shared
let taskOne = sessionOne.dataTask(with: requestOne, completionHandler: { (data, response, error) in
if let error = error {
print("ERROR: \(error)")
}
else {
print("RESPONSE: \(response)")
if let data = data, let dataString = String(data: data, encoding: .utf8) {
print("DATA: " + dataString)
} // end: if
var cookies:[HTTPCookie] = HTTPCookieStorage.shared.cookies! as [HTTPCookie]
print("Cookies Count = \(cookies.count)")
for cookie:HTTPCookie in cookies as [HTTPCookie] {
// Get the _pinterest_sess ID
if cookie.name as String == "_pinterest_sess" {
//var cookieValue : String = "CookieName=" + cookie.value as String
cookieSession = cookie.value as String
print(cookieSession)
}
// Get the csrftoken
if cookie.name as String == "csrftoken" {
cookieCSRFToken = cookie.value
print(cookieCSRFToken)
}
} // end: for
} // end: if
})
taskOne.resume()
var requestTwo = URLRequest(url: myWebServiceUrl!)
cookieSession = "XXXXXXXX"
cookieCSRFToken = "JHDylCCKKNToE4VXgofq1ad3hg06uKKl"
var cookieRequest = "_auth=1; _b=\"AR4XTkMmqo9JKradOZyuMoSWcMdsBMuBHHIM21wj2RPInwdkbl2yuy56yQR4iqxJ+N4=\"; _pinterest_pfob=disabled; _pinterest_sess=\"" + cookieSession + "\"; csrftoken=" + cookieCSRFToken as String
requestTwo.setValue(cookieRequest as String, forHTTPHeaderField: "Cookie")
let taskTwo = sessionOne.dataTask(with: requestTwo, completionHandler: { (data, response, error) in
if let error = error {
print("ERROR: \(error)")
}
else {
print("RESPONSE: \(response)")
} // end: if
})
taskTwo.resume()
PlaygroundPage.current.needsIndefiniteExecution = true
You can configure a cookie based session in the following way. Please let me know if you need any help. The below is just an example
let session: URLSession = URLSession.shared
session.dataTask(with: myUrlRequest { urlData, response, responseError in
let httpRes: HTTPURLResponse = (response as? HTTPURLResponse)!
let cookies:[HTTPCookie] = HTTPCookie.cookies(withResponseHeaderFields: httpRes.allHeaderFields as! [String : String], for: httpRes.url!)
HTTPCookieStorage.shared.setCookies(cookies, for: response?.url!, mainDocumentURL: nil)
if responseError == nil {
}else {
}
}.resume()
Feel free to suggest edits to make it better. Please let me know if the below doesn't work.
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