Nodejs twitter api 403 - node.js

I am trying to use the twitter api with nodejs 5.4.1, using the twitter api as a guide. Initially my bearer access token appears to be generated properly, though when I run the actuall request I keep getting a '403 Forbidden' error message. Any idea why this is?
var R = require("request");
var stream = require('twitter');
var https = require('https');
var key = 'my-key';
var secret = 'my-secret';
var cat = key +":"+secret;
var credentials = new Buffer(cat).toString('base64');
var url = 'https://api.twitter.com/oauth2/token';
R({ url: url,
method:'POST',
headers: {
"Authorization": "Basic " + credentials,
"Content-Type":"application/x-www-form-urlencoded;charset=UTF-8"
},
body: "grant_type=client_credentials"
}, function(err, resp, body) {
var an = JSON.parse(body);
console.log( an['access_token']);
runIt(an['access_token']);
console.dir(body); //the bearer token...
});
function runIt(key){
var options = {
host: 'api.twitter.com',
path: '/1.1/users/search.json?q=Twitter%20API&page=1&count=3',
headers: {
'Host': 'api.twitter.com',
'Authorization' : 'Bearer ' + key,
'Accept-Encoding': 'gzip'
}
};
https.get(options,(res)=>{
console.log(res.statusCode);
console.log(res);
});
}

For Twitter User Api you'll have to follow the proper oauth steps to get things work properly.
Initialy there will be 2-step request process that will leave you with token and secret of user.
You will use that information to sign request with method like HMAC-SHA1 so that you can access data from twitter, node-auth can be helpful in this step. Twitter Link - Authorizing requests
For further understanding see these tutorials:
Implement Twitter Sign
Nodejs Twitter api
and for code inspiration:
Twitter Streamming | A NodeJS Component

Related

Ansible Tower API call using OAuth2 Token from Nodejs App

Can we call Ansible Tower Api by passing only Oauth2 token no username or password?
(Say I want to fetch my inventories from ansible tower by passing only Oauth2 token to my nodejs script. Is that possible?)
If yes, please share syntax of that script.
Script which i have used is giving me correct output but it is using credentials as username and password but i want to do the same task by passing only OAuth2 token(generating from my username and password)
var unirest = require('unirest');
process.env.NODE_TLS_REJECT_UNAUTHORIZED = '0';
var Request = unirest.get('http://<tower-host>/api/v2/inventories');
Request
.auth({
user: 'foo',
pass: 'bar',
})
.then(function (response) {
var data = response.body;
console.log(data);
})
You can simply pass the authorization token in a header.
Here's an example function:
const fetch = require('node-fetch');
function job_inventory(tower_url, token) {
return fetch(tower_url+ "/api/v2/inventories", {
method: "GET",
headers: {
"content-type": "application/json",
"authorization": "Bearer " + token
}
});
}

How to get the correct acces token for Firebase Dynamic Link Analytics Rest API (NodeJS)

I have a problem with my access_token which I get with the serveracceskey. Here is my code in NodeJS:
const admin = require('firebase-admin');
var request = require("request");
const serviceAccount = require('./serverAccountKey.json');
const credential = admin.credential.cert(serviceAccount);
credential.getAccessToken().then((accessTokenInfo) => {
const accessToken = accessTokenInfo.access_token;
const expirationTime = accessTokenInfo.expires_in;
console.log("accessToken " + accessToken );
console.log("expirationTime " +expirationTime);
var s = "Bearer " + accessToken;
request({
headers:{
'Authorization': s
},
uri:"https://firebasedynamiclinks.googleapis.com/v1/SHORTLINK/linkStats?durationDays=7",
method: "GET",
}, function(error, response, body) {
console.log(body);
});
});
and the result is like below:
{
"error": {
"code": 403,
"message": "Request had insufficient authentication scopes.",
"status": "PERMISSION_DENIED"
}
}
What am I doing wrong ? I test the link in Postman too. Something is wrong, I read all the firebase Rest API Doc.
Admin SDK creates tokens with a specific set of scopes: https://github.com/firebase/firebase-admin-node/blob/master/src/auth/credential.ts#L272
Clearly, Dynamic Links API requires additional OAuth2 scopes in the token. You're better off using some OAuth2 library for this use case. If you were using Java or Python, Google Cloud provides libraries that handles this for you.
I solve the problem with a helpful GitHub user. If anyone get the same problem,press this link it will be helped. https://github.com/firebase/firebase-admin-node/issues/111

IIS authentication for http request with Nodejs

I have one problem with HTTP GET/POST request.
When I use the DHC/Postman, send the parameters to the URL + endpoint, works perfectly. 200 is returned.
But with code, like my example, show one 401 error.
I have searched about that and the problem is with the auth, not sure, see... Maybe is the same.
With this explanation, need to set the Authorization, I think. But the problem is when I access the site, the auth is automatic, see:
My code:
var jsonObject = JSON.stringify({ "UserName": login});
// prepare the header
var postheaders = {
'Content-Type' : 'application/json',
'Content-Length' : Buffer.byteLength(jsonObject, 'utf8')
};
// the post options
var optionspost = {
host: "xxxxxxxxxx.com",
// path: '/Home/endpoint', //send the data for the endpoit with Postma works fine
method: 'POST',
headers : postheaders
};
console.info('Options prepared:');
console.info(optionspost);
console.info('Do the POST call');
// do the POST call
var reqPost = http.request(optionspost, function(res) {
console.log("statusCode: ", res.statusCode);
// uncomment it for header details
// console.log("headers: ", res.headers);
res.on('data', function(d) {
console.info('POST result:\n');
process.stdout.write(d);
console.info('\n\nPOST completed');
});
});
// write the json data
reqPost.write(jsonObject);
reqPost.end();
reqPost.on('error', function(e) {
console.error(e);
});
Obs.: This website it's from my Company (.NET) and is Integrated with IIS (Active Directory login users for authenticate), when I access, automatically is logged... I really don't know how to solve this.
Obs II.: I Try to use one anonymous new tab and use DHC online, and my post doesn't work. This application just works inside network company and with Client side (Using postman with my computer).
Obs III.: The request is from Server and the login from my server have all permissions to access this site, and when I request, is like I'm anonymous, but if I did the same with REST Client/Postman, works perfectly. I need that it works with http request from my Server.
You can use a module like ntlm-webapi which will allow you to use NTLM auth. That way the request will go through. Just make sure the user you use is authorized for that server.
var Request = require('ntlm-webapi');
var request = new Request({
url: "http://some.restful.api.org/you/want/to/call",
username: 'username',
password: 'password',
domain: 'company_domain'
});
request.get(function(err, result){
if (err) console.log (err);
console.log (result);
});
It seems that you forgot to add the Authorization header in your code
// prepare the header
var postheaders = {
'Authorization' : 'Negotiate '+ yourAccessKey,
'Content-Type' : 'application/json',
'Content-Length' : Buffer.byteLength(jsonObject, 'utf8')
};

Clean Instagram oauth using node.js and express and minimal middlewares

I am trying to get a clean Instagram oauth without relying on middlewares such as passport, or instagram-node to learn the process and have maximum control. I have been trying to follow instagram Server-side (Explicit) Flow, which is a 2 step operation:
request an access code
request an access token
right now my server is set up using:
express = require('express'),
app = express();
and to initiate the first step I am using :
app.get('/', function(req, res){
var url = 'https://api.instagram.com/oauth/authorize/?client_id='+CLIENT-ID+'&redirect_uri='+YOUR-REDIRECT-URI+'&response_type=code'
res.redirect(url);
});
The above step sends me properly to instagram for authentication and the redirect callback of instagram gets picked up bellow at which point the console.log does display the correct instagram code. But the res.set part is wrong and does not work.
app.get('/auth/instagram/callback', function(req, res){
console.log('/// here to keep track of how many times this is called');
console.log('Instagram code: ', req.query.code);
var url = 'https://api.instagram.com/oauth/access_token';
res.set({
'client_id' : 'CLIENT-ID',
'client_secret' : 'CLIENT-SECRET',
'grant_type' : 'authorization_code',
'redirect_uri' : 'YOUR-REDIRECT-URI',
'code' : req.query.code
}).redirect(url);
});
Unfortunately it hangs at this point and clearly does not provide back the right data back.
Instagram suggest to do the following, but I am unsure how this would translate in express:
curl \-F 'client_id=CLIENT-ID' \
-F 'client_secret=CLIENT-SECRET' \
-F 'grant_type=authorization_code' \
-F 'redirect_uri=YOUR-REDIRECT-URI' \
-F 'code=CODE' \https://api.instagram.com/oauth/access_token
Any insight on this would be most welcome!
Thank you for your help.
And here is the actual response for the second part of OAuth with Instagram! Might not
var data = {'client_id' : process.env.FANCRAWLCLIENTID,
'client_secret' : process.env.FANCRAWLCLIENTSECRET,
'grant_type' : 'authorization_code',
'redirect_uri' : process.env.INSURIREDIRECT,
'code' : req.query.code
};
// Configure the request
var options = {
uri: 'https://api.instagram.com/oauth/access_token',
method: 'POST',
form: data
}
request(options, function (error, response, body) {
// to convert the string body to a usable object
var pbody = JSON.parse(body);
// pbody should look like this:
// {"access_token":"8943851.83434d.697342341324jkfdjsf41afd784932a2e8",
// "user":
// {"username":"my_user_name",
// "bio":"blah blah...",
// "website":"http:\/\/www.something.com",
// "profile_picture":"http:\/\/images.ak.instagram.com\/profiles\/profile_851_73sq_115.jpg",
// "full_name":"Full Name",
// "id":"8943851"}
// }
});
Enjoy!!!
I would suggest studying passport code (and instagram in particular).
In any case, after getting the code back (which works for you), you need to send a request from your backend code to Instagram. So your code would look more like (top of my head):
app.get('/auth/instagram/callback', function(req, res){
console.log('/// here to keep track of how many times this is called');
console.log('Instagram code: ', req.query.code);
var data = {
'url': url
'client_id' : 'CLIENT-ID',
'client_secret' : 'CLIENT-SECRET',
'grant_type' : 'authorization_code',
'redirect_uri' : 'YOUR-REDIRECT-URI',
'code' : req.query.code
};
var url = 'https://api.instagram.com/oauth/access_token';
request.post({
method: 'POST',
url: url,
body: JSON.stringify(data),
},
function (e, r, body) {
//body will contain the access_token
});
});
Then after you get the token you can set session, etc.
Ok got it to work to do post request for specific API calls but not yet the OAUTH part.. and WITH instagram secure header.
This exemple is to follow a user when you have an access token for a user.
var crypto = require('crypto'),
request = require('request');
var hmac = crypto.createHmac('SHA256', 'INSTAGRAM_CLIENT_ID');
hmac.setEncoding('hex');
hmac.write('IP_ADDRESS_127.0.0.1_OR_12.34.56.78');
hmac.end();
var hash = hmac.read();
// Set the headers
var headers = {
'X-Insta-Forwarded-For': 'IP_ADDRESS_127.0.0.1_OR_12.34.56.78|'+hash
}
// Configure the request
var options = {
uri: 'https://api.instagram.com/v1/users/1234/relationship_ OR WHATEVER API CALL',
qs: {'access_token': 'INSTAGRAM ACCESS TOKEN'},
method: 'POST',
headers: headers,
form:{action:'follow'}
}
request(options, function (error, response, body) {
// body response is what you are interested in
// NOTE that the body info is a string response so use var your_variable = JSON.parse(body) to use it as an object.
// Some exemples bellow
// USER NOT EXISTANT
// {"meta":{"error_type":"APINotFoundError","code":400,"error_message":"this user does not exist"}}
//
// successful response from unfollow
// {"meta":{"code":200},"data":{"outgoing_status":"none","target_user_is_private":false}}
//
// NOT FOLLOWING OR FOLLOWED BY
// {"meta":{"code":200},"data":{"outgoing_status":"none","target_user_is_private":false,"incoming_status":"none"}}
//
// you are following user 1234 but not followed back by them
// {"meta":{"code":200},"data":{"outgoing_status":"follows","target_user_is_private":false,"incoming_status":"none"}}
//
// Following and followed by
// {"meta":{"code":200},"data":{"outgoing_status":"follows","target_user_is_private":true,"incoming_status":"followed_by"}}
//
// PRIVATE users
// {"meta":{"code":200},"data":{"outgoing_status":"requested","target_user_is_private":true}}
});
I hope this helps.

Node.js and twilio integration

I am trying to integrate twilio with Node.js+express.
I don't have a site yet. what value should I give for HOSTNAME, along with SID and AUTH_TOKEN, these values I got from twilio site.
I have written some code, whatever suggestion given below I have placed in to views folder in twiclient.js , I have added a route in app.js to redirect the request if /twi is called , but I am not getting any result. some errors are appearing in the console, would you please help me figure out what I'm doing wrong? I have placed the correct SID, token and hostname, as specified below.
app.js has the following entry, does anything else need to be done for the twilio calling part to work?
Also, where should I define the GUI for calling a phone in the views folder?
var TwilioClient = require('twilio').Client,
      Twiml = require('twilio').Twiml,
      sys = require('sys');
var client = new TwilioClient('MY_ACCOUNT_SID', 'MY_AUTH_TOKEN', 'MY_HOSTNAME');
var phone = client.getPhoneNumber('+2323232323');
phone.setup(function() { phone.makeCall('+15555555555', null, function(call) {});
phone.setup(function() {
    phone.makeCall('+15555555555', null, function(call) {
        call.on('answered', function(callParams, response) {
            response.append(new Twiml.Say('Hey buddy. Let\'s meet for drinks later tonight.'));
            response.send();
        });
    });
});
The hostname is 'api.twilio.com'. Your SID and AUTH_TOKEN come from your twilio account. When you log in, go to the dashboard. You'll find your SID and AUTH_TOKEN listed there.
Here's the code I use to make a request to twilio to place a call. It should help you get started.
var https = require('https');
var qs = require('querystring');
var api = 'your api key';
var auth = 'your auth token';
var postdata = qs.stringify({
'From' : '+5554321212',
'To' : '+5552226262',
'Url' : 'http://yourwebsite.com/call'
});
var options = {
host: 'api.twilio.com',
path: '/2010-04-01/Accounts/<your api key>/Calls.xml',
port: 443,
method: 'POST',
headers: {
'Content-Type' : 'application/x-www-form-urlencoded',
'Content-Length' : postdata.length
},
auth: api + ':' + auth
};
var request = https.request(options, function(res){
res.setEncoding('utf8');
res.on('data', function(chunk){
console.log('Response: ' + chunk);
})
})
request.write(postdata);
request.end();

Resources