Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Passport.js - browser GET requests are OK, but AJAX requests from JS code are not?

I have configured Passport on a Node.js server and am using the Twitter auth strategy primarily.

I am confused by a recent discovery that seems to suggest that a GET request with a browser URL (using the web browser searchbar) seems to be authenticated differently than a AJAX request from inside the application code. For example, if I login with Passport, I can access everything by pointing my browser to certain urls that make a request directly to the backend server. But any request by Angular or jQuery to the backend API seems to be unauthorized.

Could this be at all correct? If so, how would Passport know the difference between a browser request and the AJAX request from inside the JS code?

like image 557
Alexander Mills Avatar asked Nov 17 '15 06:11

Alexander Mills


2 Answers

By default, a cross-origin XHR request won't include cookies (which are normally used to maintain state in applications that require authentication).

You can change that by setting withCredentials:

var xhr = new XMLHttpRequest();
xhr.open(...);
xhr.withCredentials = true;

You may need to adjust the CORS rules on the server to say Access-Control-Allow-Credentials: true.

See also MDN.

like image 143
Quentin Avatar answered Sep 30 '22 05:09

Quentin


The Twitter auth strategy requires that the user be signed into Twitter and has allowed your "app" permission to access your Twitter account information. This cannot be done with a XHR because how would the user enter their Twitter credentials to log into Twitter if the user wasn't already signed in? How would the user approve the permissions your Twitter "app" is requesting if the request is sent via XHR?

This applies to all of the Passport strategies that utilize OAuth or OpenID. The user's browser has to go directly to the auth provider's site so that they can either A) login to the auth provider or B) approve the permissions you're requesting in your application. Once the user has done that the auth provider (in your case Twitter) will then redirect the user's browser back to your application's endpoint with some kind of token which your application will then use to request information from the auth provider (such as email address, full name, etc.)

like image 33
idbehold Avatar answered Sep 30 '22 04:09

idbehold