I have checked the request body's data. These data run in Android or Postman are all successful, and will use new code to ask access_token every time. But the response status code is always 403 make me confused. However I just first time develop iOS project. I think maybe is somewhere error in my iOS code. here is the code request instagram basic display access_token API
func getShortAccessTokenInfo(requestBody: ShortAccessTokenRequestBody,completionHandler: @escaping (ShortAccessTokenResponse) -> Void) {
let url = URL(string: "https://api.instagram.com/oauth/access_token")!
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
let encoder = JSONEncoder()
encoder.keyEncodingStrategy = .convertToSnakeCase
guard let httpBody = try? encoder.encode(requestBody) else {
print("Invalid httpBody")
return
}
request.httpBody = httpBody
print("httpBody \(httpBody) ")
URLSession.shared.dataTask(with: request) {
data, response, error in
if let data = data {
let decoder = JSONDecoder()
decoder.keyDecodingStrategy = .convertFromSnakeCase
do {
let response = try decoder.decode(ShortAccessTokenResponse.self, from: data)
completionHandler(response)
} catch {
let httpResponse = response as! HTTPURLResponse
print("\nhttpResponse.statusCode = \(httpResponse.statusCode)\n")
print("\nhttpResponse.allHeaderFields = \(httpResponse.allHeaderFields)\n")
print("\nhttpResponse.description = \(httpResponse.description)\n")
let outputStr = String(data: data, encoding: String.Encoding.utf8)! as String
print("data = \(outputStr)")
}
} else {
print("No Data")
}
}.resume()
}
The Data Model is here
struct ShortAccessTokenRequestBody: Encodable {
var clientId: String
var clientSecret: String
var code: String
var grantType: String
var redirectUri: String
}
struct ShortAccessTokenResponse: Decodable {
var accessToken : String
var userId : Int
}
here is log:
statusCode:
httpResponse.statusCode = 403
allHeaderFields:
httpResponse.allHeaderFields = [AnyHashable("origin-trial"): AuqWincgAuXeuu3KypEMnrrFEJHySaesyJS3EaIH40zvafzrU0Irhb7+5QwZpOqMZrPTjgvFl7Z5jJgy1dNAcQMAAAB6eyJvcmlnaW4iOiJodHRwczovL2luc3RhZ3JhbS5jb206NDQzIiwiZmVhdHVyZSI6IkNyb3NzT3JpZ2luT3BlbmVyUG9saWN5UmVwb3J0aW5nIiwiZXhwaXJ5IjoxNjEzNDExNjYyLCJpc1N1YmRvbWFpbiI6dHJ1ZX0=, AnyHashable("cross-origin-opener-policy"): same-origin-allow-popups;report-to="coop", AnyHashable("Cache-Control"): private, no-cache, no-store, must-revalidate, AnyHashable("report-to"): {"group": "coep", "max_age": 86400, "endpoints": [{"url": "/security/coep_report/"}]},{"group": "coop", "max_age": 86400, "endpoints": [{"url": "/security/coop_report/"}]}, AnyHashable("content-security-policy"): report-uri https://www.instagram.com/security/csp_report/; default-src 'self' https://www.instagram.com; img-src data: blob: https://.fbcdn.net https://.instagram.com https://.cdninstagram.com https://.facebook.com https://.fbsbx.com https://.giphy.com; font-src data: https://.fbcdn.net https://.instagram.com https://.cdninstagram.com; media-src 'self' blob: https://www.instagram.com https://.cdninstagram.com https://.fbcdn.net; manifest-src 'self' https://www.instagram.com; script-src 'self' https://instagram.com https://www.instagram.com https://.www.instagram.com https://.cdninstagram.com wss://www.instagram.com https://.facebook.com https://.fbcdn.net https://.facebook.net 'unsafe-inline' 'unsafe-eval' blob:; style-src 'self' https://.www.instagram.com https://www.instagram.com 'unsafe-inline'; connect-src 'self' https://instagram.com https://www.instagram.com https://.www.instagram.com https://graph.instagram.com https://.graph.instagram.com https://graphql.instagram.com https://.cdninstagram.com https://api.instagram.com https://i.instagram.com https://.i.instagram.com wss://www.instagram.com wss://edge-chat.instagram.com https://.facebook.com https://.fbcdn.net https://.facebook.net chrome-extension://boadgeojelhgndaghljhdicfkmllpafd blob:; worker-src 'self' blob: https://www.instagram.com; frame-src 'self' https://instagram.com https://www.instagram.com https://*.instagram.com https://staticxx.facebook.com https://www.facebook.com https://web.facebook.com https://connect.facebook.net https://m.facebook.com; object-src 'none'; upgrade-insecure-requests, AnyHashable("Content-Length"): 20676, AnyHashable("x-frame-options"): SAMEORIGIN, AnyHashable("Pragma"): no-cache, AnyHashable("cross-origin-embedder-policy-report-only"): require-corp;report-to="coep", AnyHashable("Strict-Transport-Security"): max-age=31536000, AnyHashable("x-content-type-options"): nosniff, AnyHashable("Content-Language"): zh-tw, AnyHashable("x-xss-protection"): 0, AnyHashable("proxy-status"): http_request_error; e_clientaddr="AcKYiNAO8yhMSZJyyEYudvZGWQzL-XB3-zoUHCoHbF8NHNnIr-i2ovQf3F3cMLaZ6NllIZz2Qo5Bgx6eJHw"; e_fb_binaryversion="AcLdEktTbz5wJ21gYaJEitTnDh51fwKoh1TWEJBnCTDeDsuWyGfrhaGoKLWBuytlTD_jNpYGEqTKkjuZHHl7upVezSs6uJlj8ok"; e_upip="AcJJDJlMUJsyHsIAGFauA9kxrXY2wohcrnfn50hqCMIY2ykTyJKp6Yzgq3HMhBdEfDpJdFdON7xvDmFgevxPXHhO4y4f7PITGNIpgvs"; e_proxy="AcJPFaA_DemVAz4l_ZIcLlO6dqLEWUrH1S3qyfM0Psu4Qqzm3d7g1IZeYuFfciVB_2EGkehYmN4GEjA"; e_fb_builduser="AcISyC6CAEhH54reK-ewAmKXLcNC8aeHIx4_8Dz6aY83oAk05yOr1kaVHEqYAN-Jcck"; e_fb_vipaddr="AcInfxChauRQiPpxzGfxHV2lNUNaz0TDhZFUIoS85agFhatn6NyYkeG6swkbzrGDNCmkyZk", http_request_error; e_clientaddr="AcIY794j6DB_pmP2rk4VsK1zivmZkN9gKrGfvjHfleRJNRB91E-eM7XwFHBZCUBY8zxtV5TVCl3bZAUl0ZOyUSNYP7HHQgvSuXGPRxosSOaG"; e_fb_binaryversion="AcITNqtpSK2R5tDP_gcliynnda3OUKCZgzK-Xsb-r4KXoTzmkEkQmC9Nir7f8yfGz50vSf-gAKhLabX9TQoI0dDOI6LlWW4BHaI"; e_upip="AcKdip7JMVCIyHNm4r3n_lc1FxZ8WRKNQWBDBUwsupTD4rNfKXV4LFfbOLVbapi7jcyqgp1OMZev9Mrb-zxwQ2fryGpF7P3D-Q"; e_proxy="AcI1jEPhkHHVfIX0U-99CwCpJd9bHFInKVHw9EqNNgHvgWSlCPPyPZ-hKEHGtNUxph6CrXt8H8drm0RL3DAn"; e_fb_builduser="AcKOj-xkkvFvzA7RHW34q4gu4tq7NuVcT_WRvsQwxdJFoGmDmQGrefnKdcJ7Hpb4KEo"; e_fb_vipaddr="AcKa3V32l88jLiYn7E5uzcjwzVyAsdvUFKuu1lo_qhJx5qKrGr1ffkqtyIr9Pxh8QrmPf1EHN5vZItcLz3j9_s-6lutm2G-44iYcaiE", AnyHashable("Content-Type"): text/html; charset=utf-8, AnyHashable("x-ig-push-state"): c2, AnyHashable("Set-Cookie"): rur="FTW\0541700458427\0541660136279:01f7f1716e996e603ddf484bdfbc12a6fad1ff6f56053129280eb54ca5906d3e6cf24459"; Domain=.instagram.com; HttpOnly; Path=/; Secure, AnyHashable("access-control-expose-headers"): X-IG-Set-WWW-Claim, AnyHashable("x-aed"): 46, AnyHashable("Vary"): Accept-Language, Cookie, AnyHashable("x-fb-trip-id"): 19638678, AnyHashable("Expires"): Sat, 01 Jan 2000 00:00:00 GMT, AnyHashable("Alt-Svc"): h3-29=":443"; ma=3600,h3-27=":443"; ma=3600, AnyHashable("x-ig-origin-region"): ftw, AnyHashable("Date"): Tue, 10 Aug 2021 12:57:59 GMT]
description:
<NSHTTPURLResponse: 0x280a5a6e0> { URL: https://api.instagram.com/oauth/access_token } { Status Code: 403, Headers {
"Alt-Svc" = (
"h3-29=\":443\"; ma=3600,h3-27=\":443\"; ma=3600"
);
"Cache-Control" = (
"private, no-cache, no-store, must-revalidate"
);
"Content-Language" = (
"zh-tw"
);
"Content-Length" = (
20676
);
"Content-Type" = (
"text/html; charset=utf-8"
);
Date = (
"Tue, 10 Aug 2021 12:57:59 GMT"
);
Expires = (
"Sat, 01 Jan 2000 00:00:00 GMT"
);
Pragma = (
"no-cache"
);
"Set-Cookie" = (
"rur=\"FTW\\0541700458427\\0541660136279:01f7f1716e996e603ddf484bdfbc12a6fad1ff6f56053129280eb54ca5906d3e6cf24459\"; Domain=.instagram.com; HttpOnly; Path=/; Secure"
);
"Strict-Transport-Security" = (
"max-age=31536000"
);
Vary = (
"Accept-Language, Cookie"
);
"access-control-expose-headers" = (
"X-IG-Set-WWW-Claim"
);
"content-security-policy" = (
"report-uri https://www.instagram.com/security/csp_report/; default-src 'self' https://www.instagram.com; img-src data: blob: https://*.fbcdn.net https://*.instagram.com https://*.cdninstagram.com https://*.facebook.com https://*.fbsbx.com https://*.giphy.com; font-src data: https://*.fbcdn.net https://*.instagram.com https://*.cdninstagram.com; media-src 'self' blob: https://www.instagram.com https://*.cdninstagram.com https://*.fbcdn.net; manifest-src 'self' https://www.instagram.com; script-src 'self' https://instagram.com https://www.instagram.com https://*.www.instagram.com https://*.cdninstagram.com wss://www.instagram.com https://*.facebook.com https://*.fbcdn.net https://*.facebook.net 'unsafe-inline' 'unsafe-eval' blob:; style-src 'self' https://*.www.instagram.com https://www.instagram.com 'unsafe-inline'; connect-src 'self' https://instagram.com https://www.instagram.com https://*.www.instagram.com https://graph.instagram.com https://*.graph.instagram.com https://graphql.instagram.com https://*.cdninstagram.com https://api.instagram.com https://i.instagram.com https://*.i.instagram.com wss://www.instagram.com wss://edge-chat.instagram.com https://*.facebook.com https://*.fbcdn.net https://*.facebook.net chrome-extension://boadgeojelhgndaghljhdicfkmllpafd blob:; worker-src 'self' blob: https://www.instagram.com; frame-src 'self' https://instagram.com https://www.instagram.com https://*.instagram.com https://staticxx.facebook.com https://www.facebook.com https://web.facebook.com https://connect.facebook.net https://m.facebook.com; object-src 'none'; upgrade-insecure-requests"
);
"cross-origin-embedder-policy-report-only" = (
"require-corp;report-to=\"coep\""
);
"cross-origin-opener-policy" = (
"same-origin-allow-popups;report-to=\"coop\""
);
"origin-trial" = (
"AuqWincgAuXeuu3KypEMnrrFEJHySaesyJS3EaIH40zvafzrU0Irhb7+5QwZpOqMZrPTjgvFl7Z5jJgy1dNAcQMAAAB6eyJvcmlnaW4iOiJodHRwczovL2luc3RhZ3JhbS5jb206NDQzIiwiZmVhdHVyZSI6IkNyb3NzT3JpZ2luT3BlbmVyUG9saWN5UmVwb3J0aW5nIiwiZXhwaXJ5IjoxNjEzNDExNjYyLCJpc1N1YmRvbWFpbiI6dHJ1ZX0="
);
"proxy-status" = (
"http_request_error; e_clientaddr=\"AcKYiNAO8yhMSZJyyEYudvZGWQzL-XB3-zoUHCoHbF8NHNnIr-i2ovQf3F3cMLaZ6NllIZz2Qo5Bgx6eJHw\"; e_fb_binaryversion=\"AcLdEktTbz5wJ21gYaJEitTnDh51fwKoh1TWEJBnCTDeDsuWyGfrhaGoKLWBuytlTD_jNpYGEqTKkjuZHHl7upVezSs6uJlj8ok\"; e_upip=\"AcJJDJlMUJsyHsIAGFauA9kxrXY2wohcrnfn50hqCMIY2ykTyJKp6Yzgq3HMhBdEfDpJdFdON7xvDmFgevxPXHhO4y4f7PITGNIpgvs\"; e_proxy=\"AcJPFaA_DemVAz4l_ZIcLlO6dqLEWUrH1S3qyfM0Psu4Qqzm3d7g1IZeYuFfciVB_2EGkehYmN4GEjA\"; e_fb_builduser=\"AcISyC6CAEhH54reK-ewAmKXLcNC8aeHIx4_8Dz6aY83oAk05yOr1kaVHEqYAN-Jcck\"; e_fb_vipaddr=\"AcInfxChauRQiPpxzGfxHV2lNUNaz0TDhZFUIoS85agFhatn6NyYkeG6swkbzrGDNCmkyZk\", http_request_error; e_clientaddr=\"AcIY794j6DB_pmP2rk4VsK1zivmZkN9gKrGfvjHfleRJNRB91E-eM7XwFHBZCUBY8zxtV5TVCl3bZAUl0ZOyUSNYP7HHQgvSuXGPRxosSOaG\"; e_fb_binaryversion=\"AcITNqtpSK2R5tDP_gcliynnda3OUKCZgzK-Xsb-r4KXoTzmkEkQmC9Nir7f8yfGz50vSf-gAKhLabX9TQoI0dDOI6LlWW4BHaI\"; e_upip=\"AcKdip7JMVCIyHNm4r3n_lc1FxZ8WRKNQWBDBUwsupTD4rNfKXV4LFfbOLVbapi7jcyqgp1OMZev9Mrb-zxwQ2fryGpF7P3D-Q\"; e_proxy=\"AcI1jEPhkHHVfIX0U-99CwCpJd9bHFInKVHw9EqNNgHvgWSlCPPyPZ-hKEHGtNUxph6CrXt8H8drm0RL3DAn\"; e_fb_builduser=\"AcKOj-xkkvFvzA7RHW34q4gu4tq7NuVcT_WRvsQwxdJFoGmDmQGrefnKdcJ7Hpb4KEo\"; e_fb_vipaddr=\"AcKa3V32l88jLiYn7E5uzcjwzVyAsdvUFKuu1lo_qhJx5qKrGr1ffkqtyIr9Pxh8QrmPf1EHN5vZItcLz3j9_s-6lutm2G-44iYcaiE\""
);
"report-to" = (
"{\"group\": \"coep\", \"max_age\": 86400, \"endpoints\": [{\"url\": \"/security/coep_report/\"}]},{\"group\": \"coop\", \"max_age\": 86400, \"endpoints\": [{\"url\": \"/security/coop_report/\"}]}"
);
"x-aed" = (
46
);
"x-content-type-options" = (
nosniff
);
"x-fb-trip-id" = (
19638678
);
"x-frame-options" = (
SAMEORIGIN
);
"x-ig-origin-region" = (
ftw
);
"x-ig-push-state" = (
c2
);
"x-xss-protection" = (
0
);
} }
data:
data = <!DOCTYPE html>
<html lang="zh-tw" class="no-js logged-in ">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>
查無此頁 • Instagram
</title>
<meta name="robots" content="noimageindex, noarchive">
<meta name="apple-mobile-web-app-status-bar-style" content="default">
<meta name="mobile-web-app-capable" content="yes">
<meta name="theme-color" content="#ffffff">
<meta id="viewport" name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1, maximum-scale=1, viewport-fit=cover">
<link rel="manifest" href="/data/manifest.json">
<script type="text/javascript">
(function() {
var docElement = document.documentElement;
var classRE = new RegExp('(^|\\s)no-js(\\s|$)');
var className = docElement.className;
docElement.className = className.replace(classRE, '$1js$2');
})();
</script>
<script type="text/javascript">
(function() {
if ('PerformanceObserver' in window && 'PerformancePaintTiming' in window) {
window.__bufferedPerformance = [];
var ob = new PerformanceObserver(function(e) {
window.__bufferedPerformance.push.apply(window.__bufferedPerformance,e.getEntries());
});
ob.observe({entryTypes:['paint']});
}
window.__bufferedErrors = [];
window.onerror = function(message, url, line, column, error) {
window.__bufferedErrors.push({
message: message,
url: url,
line: line,
column: column,
error: error
});
return false;
};
window.__initialData = {
pending: true,
waiting: []
};
function asyncFetchSharedData(extra) {
var sharedDataReq = new XMLHttpRequest();
sharedDataReq.onreadystatechange = function() {
if (sharedDataReq.readyState === 4) {
if(sharedDataReq.status === 200){
var sharedData = JSON.parse(sharedDataReq.responseText);
window.__initialDataLoaded(sharedData, extra);
}
}
}
sharedDataReq.open('GET', '/data/shared_data/', true);
sharedDataReq.send(null);
}
function notifyLoaded(item, data) {
item.pending = false;
item.data = data;
for (var i = 0;i < item.waiting.length; ++i) {
item.waiting[i].resolve(item.data);
}
item.waiting = [];
}
function notifyError(item, msg) {
item.pending = false;
item.error = new Error(msg);
for (var i = 0;i < item.waiting.length; ++i) {
item.waiting[i].reject(item.error);
}
item.waiting = [];
}
window.__initialDataLoaded = function(initialData, extraData) {
if (extraData) {
for (var key in extraData) {
initialData[key] = extraData[key];
}
}
notifyLoaded(window.__initialData, initialData);
};
window.__initialDataError = function(msg) {
notifyError(window.__initialData, msg);
};
window.__additionalData = {};
window.__pendingAdditionalData = function(paths) {
for (var i = 0;i < paths.length; ++i) {
window.__additionalData[paths[i]] = {
pending: true,
waiting: []
};
}
};
window.__additionalDataLoaded = function(path, data) {
if (path in window.__additionalData) {
notifyLoaded(window.__additionalData[path], data);
} else {
console.error('Unexpected additional data loaded "' + path + '"');
}
};
window.__additionalDataError = function(path, msg) {
if (path in window.__additionalData) {
notifyError(window.__additionalData[path], msg);
} else {
console.error('Unexpected additional data encountered an error "' + path + '": ' + msg);
}
};
})();
</script><script type="text/javascript">
Okay I've solved the same problem. Seems if you send a request with cookie to the Instagram's API, it will return 403
back. In iOS, URLRequest
by default will add some cookies by the system, which causes this 403
problem.
What you need to do is add:
request.httpShouldHandleCookies = false
to your request to disable adding cookies automatically by the system.