Easybird
Easybird

Reputation: 71

AngularJS - How to connect to Twitter application-only authentication via Oauth2?

I try to receive an accessToken from the Twitter application-only authentication but I keep receiving a 405 (Method Not Allowed) response from the twitter api. Anybody knows how to solve this? I'm desperately stuck..

I am aware of the fact that:
- best practice is doing this from serverside, but I wanted to try this out with angular on client side
- X-Requested-With should be deleted from the header

This is the factory I created:

twitterServices.factory('Connect', function($http){
var factory = {};
var baseUrl = 'https://api.twitter.com/';

var bearerToken = function(){
    var consumerKey = encodeURIComponent('****');
    var consumerSecret = encodeURIComponent('****');
    var tokenCredentials = btoa(consumerKey + ':' + consumerSecret);

    return tokenCredentials;
};

factory.fetchAccessToken = function(scope){
    var oAuthurl = baseUrl + "oauth2/token";
    var headers = {
            'Authorization': 'Basic ' + bearerToken(),
            'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8'
        };
    $http.defaults.useXDomain = true;
    delete $http.defaults.headers.common['X-Requested-With'];
    $http({method: 'POST', url: oAuthurl, headers: headers, data: 'grant_type=client_credentials'}).
        success(function(data, status){
            scope.status = status;
            scope.data = data;
        }).
        error(function(data, status){
            scope.status = status;
            scope.data = data || "Request failed";
        });
};

factory.fetchTimeLine = function(scope){
    scope.fetchAccessToken();
    //the rest
};
return factory;
});

This is the header request/response in Chrome:

Request URL:`https://api.twitter.com/oauth2/token`
Request Method:OPTIONS
Status Code:405 Method Not Allowed
Request Headersview source
:host:api.twitter.com
:method:OPTIONS
:path:/oauth2/token
:scheme:https
:version:HTTP/1.1
accept:*/*
accept-encoding:gzip,deflate,sdch
accept-language:en-US,en;q=0.8
access-control-request-headers:accept, authorization, content-type
access-control-request-method:POST
origin:`http://localhost`
referer:`http://localhost/test/app/
user-agent:Mozilla/5.0 (Macintosh; Intel Mac OS X 10_8_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/30.0.1599.69 Safari/537.36

Response Headersview source
content-length:0
status:405 Method Not Allowed
version:HTTP/1.1

My Console shows the following:

OPTIONS https://api.twitter.com/oauth2/token 405 (Method Not Allowed) angular.js:9312
OPTIONS https://api.twitter.com/oauth2/token Origin http://localhost is not allowed by Access-Control-Allow-Origin. angular.js:9312
XMLHttpRequest cannot load https://api.twitter.com/oauth2/token. Origin http://localhost is not allowed by Access-Control-Allow-Origin. (index):1

Upvotes: 5

Views: 4708

Answers (2)

Dataminion
Dataminion

Reputation: 209

I ran into a similar issue when working with the google API where in request from localhost are denied even if you register it with the system.

We got around this issue by adding a multipart name to our /etc/hosts file and binding it to 127.0.0.1

for example

127.0.0.1 www.devsite.com

This has resolved the most basic issues that I have had writing angular services for APIs

update by request:

One of the ways that companies control access to their APIs is through whitelisting. When you register an application with the service that platform will typically add the domain you list in your application to its whitelist. This is Generally done to force you in to using separate API keys for separate services. This can make work on the dev side difficult when you are testing locally.

In this case I believe that twitter has specifically banned requests using localhost to prevent the use of 3rd party tools and bots.

Binding the domain you registered with your API key into your hosts file will cause any web requests on your machine to that domain to skip a dns lookup and instead route the request to your local dev server. This means that locally you will test your code by visiting:

www.devsite.com:[what ever port your local server is running on]

This may not be the solution to 100% of api access problems but it is one of the most common that I have experienced.

Note based on other responses: There are Multiple reasons why you might experience a CORS related error. But just because you have received one doesn't mean that it isn't possible to implement your code on the front end. Generally in Angular CORS is encountered when:

a) you have failed to format your request correctly -- one example of this might be you have added a header to indicate json is an expected result when infact the response it text.

b) the service or API is configured with a whitelist that needs to include explicitly either "localhost" or some other domain as discussed in this post.

Upvotes: 1

Related Questions