I am using an Axios interceptor in my React application to add an Authorization header. This works fine on desktop browsers (Chrome), however on mobile browsers (iOS, Safari and Chrome) the Authorization header is not set.
I am using Axios (0.23.0).
Here is the Axios code:
// api.js
export const ProtectedAPI = axios.create({
baseURL: `${REACT_APP_API_URL}/`,
});
ProtectedAPI.interceptors.request.use(
(config) => {
const currentUser = JSON.parse(window.localStorage.getItem("current_user"));
config.headers = {
Authorization: "Bearer " + currentUser.accessToken,
};
return config;
},
(error) => {
return Promise.reject(error);
}
);
Here is how it is called in my component:
// myComponent/index.js
const accountRes = await ProtectedAPI.get(
"account/get_account"
);
These are the headers received by the API from mobile browsers:
{
Connection: "upgrade",
Host: "<MY_API_ENDPOINT>",
"X-Real-Ip": "<IP_REMOVED_BY_ME>",
"X-Forwarded-For": "<IP_REMOVED_BY_ME>",
Accept: "*/*",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "en-US,en;q=0.9",
Origin: "<MY_ORIGIN>",
"User-Agent":
"Mozilla/5.0 (iPhone; CPU iPhone OS 15_0 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) CriOS/94.0.4606.76 Mobile/15E148 Safari/604.1",
"X-Forwarded-Port": "443",
"X-Forwarded-Proto": "https",
};
These are the headers received by the API from desktop browsers:
{
Connection: "upgrade",
Host: "<MY_API_ENDPOINT>",
"X-Real-Ip": "<IP_REMOVED_BY_ME>",
"X-Forwarded-For": "<IP_REMOVED_BY_ME>",
Accept: "*/*",
"Accept-Encoding": "gzip, deflate, br",
"Accept-Language": "en-US,en;q=0.9",
Authorization:
"Bearer <MY_ACCESS_TOKEN>",
Dnt: "1",
Origin: "<MY_ORIGIN>",
"Sec-Ch-Ua":
'"Chromium";v="94", "Google Chrome";v="94", ";Not A Brand";v="99"',
"Sec-Ch-Ua-Mobile": "?0",
"Sec-Ch-Ua-Platform": '"Windows"',
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-site",
"User-Agent":
"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.81 Safari/537.36",
"X-Forwarded-Port": "443",
"X-Forwarded-Proto": "https",
};
As you can see, the desktop browser request includes the Authorization header and token, while the mobile request does not. Is there something different about the way Axios interceptors work on mobile browsers?
Related
const headers = event.request.headers
console.log('headers: ', headers)
console.log('type is ', typeof headers)
console.log('keys are ', Object.keys(headers))
console.log('cookie are ', headers.cookie)
Output:
headers: {
accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9',
'accept-encoding': 'gzip, deflate, br',
'accept-language': 'en-GB,en-US;q=0.9,en;q=0.8',
'cache-control': 'max-age=0',
connection: 'keep-alive',
cookie: 'userid=7599271f-87de-4f44-8625-5d4dc4af4069; authToken=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6ImNsMWl4d2Y2aTAwMTdmNzNlcnVweWhqY3UiLCJpYXQiOjE2NDk1MTIzMjB9.ltrLZV7aFeNCmCtC5ZMVZvRhM5c285TAEWf_zFbVGs0',
host: 'localhost:3000',
'if-none-match': '"1l79fw0"',
referer: 'http://localhost:3000/profile',
'sec-fetch-dest': 'document',
'sec-fetch-mode': 'navigate',
'sec-fetch-site': 'same-origin',
'sec-gpc': '1',
'upgrade-insecure-requests': '1',
'user-agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.4844.45 Safari/537.36'
}
type is object
keys are []
cookie are undefined
Click here to see my code screenshot
Can anyone say what's wrong with it?
It should be event.request.headers.get(“cookie”)
I have the following curl command. Curl in bash works ok but when I write equivalent in node.js (any http library), it doesn't seem to work
curl --location --request POST 'https://www.delta.com/shop/modals/flightspecific' \
--header 'user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36' \
--header 'Content-Type: application/json; charset=UTF-8' \
--header 'cachekey: d6469dbe-b47e-4f46-be02-12b900011c7c' \
--header 'Accept-Encoding: compressed' \
--data-raw '{"legList":[{"originAirportCode":"BOS","destinationAirportCode":"JFK","schedLocalDepartDate":"2020-03-10T08:30","marketingAirlineCode":"DL","operatingAirlineCode":"9E","classOfServiceList":["NE","NV","SN","OZ"],"flightNumber":"5419"}],"pageId":"dynamic-modal","appId":"sho","channelId":"ecomm"}'
Which works fine (returns JSON). But this code does not work
const axios = require("axios");
headers = {
"user-agent":
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36",
"Content-Type": "application/json; charset=UTF-8",
cachekey: "d6469dbe-b47e-4f46-be02-12b900011c7c",
"Accept-Encoding": "compressed"
};
data =
'{"legList":[{"originAirportCode":"BOS","destinationAirportCode":"JFK","schedLocalDepartDate":"2020-03-10T08:30","marketingAirlineCode":"DL","operatingAirlineCode":"9E","classOfServiceList":["NE","NV","SN","OZ"],"flightNumber":"5419"}],"pageId":"dynamic-modal","appId":"sho","channelId":"ecomm"}';
url = "https://www.delta.com/shop/modals/flightspecific";
options = {
method: "POST",
headers: headers,
data: data,
url: url
};
axios(options).then(function(response) {
console.log(response);
});
Try something Like this :
var Request = require("request");
var headers = {
"user-agent":
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.130 Safari/537.36",
"Content-Type": "application/json; charset=UTF-8",
cachekey: "d6469dbe-b47e-4f46-be02-12b900011c7c",
"Accept-Encoding": "compressed"
};
data =
'{"legList":[{"originAirportCode":"BOS","destinationAirportCode":"JFK","schedLocalDepartDate":"2020-03-10T08:30","marketingAirlineCode":"DL","operatingAirlineCode":"9E","classOfServiceList":["NE","NV","SN","OZ"],"flightNumber":"5419"}],"pageId":"dynamic-modal","appId":"sho","channelId":"ecomm"}';
Request.post({
"headers": headers,
"url": "https://www.delta.com/shop/modals/flightspecific",
"body": JSON.stringify(data )
}, (error, response, body) => {
if (error) {
console.dir(error);
}
if (body) {
console.dir(JSON.parse(body));
}
});
I want to use the size and data of my POST request. I was doing some research and found out about the Content-Length header of a request, but I can't find it in my axios request headers.
I tried using interceptors, like that :
axios.interceptors.request.use(
config => {
console.log('config', config.headers);
if (config.url != `${API_URL}/login`)
config.headers.Authorization = 'Bearer ' + getAccessToken();
return config;
},
error => {
return Promise.reject(error);
}
);
And here is the response that I get:
Authorization: "Bearer [...access_token]"
Content-Type: "multipart/form-data"
common:
Accept: "application/json, text/plain, */*"
X-CSRF-TOKEN: "..."
X-Requested-With: "XMLHttpRequest"
__proto__: Object
delete: {}
get: {}
head: {}
patch: {Content-Type: "application/x-www-form-urlencoded"}
post: {Content-Type: "application/x-www-form-urlencoded"}
put: {Content-Type: "application/x-www-form-urlencoded"}
But in in Chrome this is what is shown:
Accept: application/json, text/plain
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9,ro;q=0.8,la;q=0.7
Authorization: Bearer [...access_token]
Connection: keep-alive
Content-Length: 5266672 <---- this is what I need
Content-Type: multipart/form-data; boundary=----WebKitFormBoundaryGMzak87LIZH05nme
Cookie: XSRF-TOKEN= ...
Host: ...
Origin: ...
Referer: ...
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/77.0.3865.90 Safari/537.36
X-CSRF-TOKEN: ...
X-Requested-With: XMLHttpRequest
X-XSRF-TOKEN: ...
Is there any way to make axios give me the content-length header? If not, is there any way to access it from anywhere else?
content-length will auto add by http adapter.
This question already has answers here:
Trying to use fetch and pass in mode: no-cors
(9 answers)
Closed 3 years ago.
I try to create a Header for a following fetch() like this
var myheaders = new Headers(
{ "Accept": "application/json",
"Content-Type": "application/json; charset=UTF-8"
});
let b = JSON.stringify ({ "cmd2" : "ytdl", "url" : "x"});
let params =
{ headers : myheaders,
body : b,
method : "POST",
mode : "no-cors"
};
let response = await fetch("http://127.0.0.1:5000/ytdl",params);
....
If I print the headers in the receiving Server (Flask) I get:
Host: 127.0.0.1:5000
Connection: keep-alive
Content-Length: 67
Accept: application/json
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36
Sec-Fetch-Mode: no-cors
Content-Type: text/plain;charset=UTF-8
Origin: chrome-extension://mnihgjnpmkpgeichhdfhejagbefjpnnb
Sec-Fetch-Site: cross-site
Accept-Encoding: gzip, deflate, br
Accept-Language: de-DE,de;q=0.9,en-US;q=0.8,en;q=0.7
Any Idea, what I´m doing wrong?
I didn't understand what is the reason but when you call without mode: 'no-cors' content type is:
let params = {
headers : myheaders,
body : b,
method : "POST",
mode : "cors"
};
response = await fetch("http://127.0.0.1:5000/", params);
The output of the flask request.headers:
...
Accept: application/json
User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36
Sec-Fetch-Mode: cors
Content-Type: application/json; charset=UTF-8
...
I followed this article build a web api with token in Node.js:
var token = req.body.token || req.query.token || req.headers['x-access-token'];
if (token) {console.log("passed!");}
else
{console.log("No token provided.");}
I tested with Postman and tried with http://localhost:3000?token=eyJ0eXAiO
all work fine, but when call API in client side:
app.controller('myCtrl', function($scope, $http, $cookies) {
var apikey=$cookies.get('apikey');
$http({url: 'http://localhost:3000/', method: 'GET', headers: {'x-access-token': apikey}})
.success(function (data) {
console.log(data);
}).error(function(error){console.log(error);});
and jquery call:
jQuery.ajax( {
url: 'http://localhost:3000/',
type: 'GET',
beforeSend : function( xhr ) {
xhr.setRequestHeader( 'x-access-token', 'eyJ0eXAi');
},
success: function( response ) {
console.log(response);
},
error : function(error) {
console.log(error);
}
} );
What every Angular or jquery did not work and return "No token provided."
what did I miss? Please help me.
Here is headers from req.headers
Angular.JS
{ host: 'localhost:3000',
connection: 'keep-alive',
'cache-control': 'max-age=0',
'access-control-request-method': 'GET',
origin: 'localhost:3001',
'user-agent': 'Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML,
like Gecko) Chrome/43.0.2357.132 Safari/537.36',
'access-control-request-headers': 'accept, max-age, x-access-token',
accept: '/',
referer: 'localhost:3001',
'accept-encoding': 'gzip, deflate, sdch',
'accept-language': 'en-CA,en;q=0.8,en-US;q=0.6,zh-CN;q=0.4,zh;q=0.2,zh-TW;q=0.
2' }
No token provided.
Postman
{ host: 'localhost:3000',
connection: 'keep-alive',
csp: 'active',
'cache-control': 'no-cache',
'x-access-token': 'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJuYW1lIjoibGF3cmVuY2
UiLCJwYXNzd29yZCI6InNreTIwMDAiLCJhZG1pbiI6dHJ1ZSwiaWF0IjoxNDM2Mzc0NTYzLCJleHAiOj
E0MzY0NjA5NjN9.OycP6xdUlG3vLyZHcj4rLjyYKE1GnlWc3h-f0r1ZpZ0',
'user-agent': 'Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML,
like Gecko) Chrome/43.0.2357.132 Safari/537.36',
'postman-token': 'ab2a26e3-f6a1-09e0-c21a-85e3cef0aff5',
accept: '/',
'accept-encoding': 'gzip, deflate, sdch',
'accept-language': 'en-CA,en;q=0.8,en-US;q=0.6,zh-CN;q=0.4,zh;q=0.2,zh-TW;q=0.
2' }
passed!
It turned out this is a Chrome issue, have to run Chrome with --disable-web-security then the headers request works.
CORS, Cordova, AngularJs $http and file:// confusion