authorize myself to mailchimp api - node.js

guys, I am trying to authorize myself to Mailchimp API but its give me 401 error can any find a problem in the code I am using request
app.post('/',function(req,res){
var firstname=req.body.first;
var lastname= req.body.last;
var email= req.body.email;
var options={
url:'https://us10.api.mailchimp.com/3.0/lists/47303a99f3',
method: 'POST',
header:{
'Authorization':'Basic 55adfb745d93168c37966fbd734e46d1-us10'
}
};
request(options,function(e,r,b){
if(e){
console.log(e);
}else if(r){
console.log(r.statusCode);
}
});
});

There is an issue with your options object.
The request module expects the headers attribute in options instead of header attribute. Hence your authorization header is not getting identified on the server side.
It should work if you update your options to:
var options={
url:'https://us10.api.mailchimp.com/3.0/lists/47303a99f3',
method: 'POST',
headers:{
'Authorization':'Basic 55adfb745d93168c37966fbd734e46d1-us10'
}
};
Reference.

Related

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')
};

Unable to authenticate with Google token in Node JS

On a Node server, I am trying to validate a Google user but it always returns with a "Bad Request". What is wrong in my code?
var post_data = querystring.stringify({
'alt': 'json',
'access_token': <token from REST API params>
});
var post_options = {
host: 'www.googleapis.com',
port: '443',
path: '/oauth2/v1/userinfo',
method: 'GET',
headers: {
'Content-Length': Buffer.byteLength(post_data)
}
};
var post_req = https.request(post_options, function (result) {
if (result.statusCode == 200) {
result.on('data', function (chunk) {
//Valid user stuff
});
}
else {
//Invalid user stuff
}
});
post_req.write(post_data);
post_req.end();
The scenario here is that my client app is a chrome extension that successfully gets a token. The token is passed to my REST API hosted on the Node server. I try to replay that token to authenticate the Google user. (Note that if I use the token on the Chrome extension to make the same request, it succeeds and I get the profile information! It's only the request on the Node server that fails.) Help me! Please?
The problem is that you are:
Using the property host instead of hostname
Providing the port parameter (not sure about this one, but it will work without it)
Method should be POST, not GET
So, your new post_options object should be:
var post_options = {
hostname: 'www.googleapis.com',
path: '/oauth2/v1/userinfo',
method: 'POST',
headers: {
'Content-Length': Buffer.byteLength(post_data)
}
};
If you want to make it easier on yourself you could use a module such as google-auth-library or google-sign-in.

Mailchimp API v3.0 add email to list via NodeJS http

I'm using NodeJS to call the new MailChimp 3.0 API in order to add an email to a list. While I can get it working via POSTman, I'm having a hard time with Node's http:
var http = require('http');
var subscriber = JSON.stringify({
"email_address": "test#test.com",
"status": "subscribed",
"merge_fields": {
"FNAME": "Tester",
"LNAME": "Testerson"
}
});
var options = {
host: 'https://us11.api.mailchimp.com',
path: '/3.0/lists/<myListID>/members',
method: 'POST',
headers: {
'Authorization': 'randomUser myApiKey',
'Content-Type': 'application/json',
'Content-Length': subscriber.length
}
}
var hreq = http.request(options, function (hres) {
console.log('STATUS CODE: ' + hres.statusCode);
console.log('HEADERS: ' + JSON.stringify(hres.headers));
hres.setEncoding('utf8');
hres.on('data', function (chunk) {
console.log('\n\n===========CHUNK===============')
console.log(chunk);
res.send(chunk);
});
hres.on('end', function(res) {
console.log('\n\n=========RESPONSE END===============');
});
hres.on('error', function (e) {
console.log('ERROR: ' + e.message);
});
});
hreq.write(subscriber);
hreq.end();
Rather than getting even some sort of JSON error from Mailchimp, however, I'm getting HTML:
400 Bad Request
400 Bad Request
nginx
Is it clear at all what I"m doing wrong here? It seems pretty simple, yet nothing I've tried seems to work.
A few additional thoughts:
While http's options have an "auth" property, I'm using the headers instead to ensure the authorization is sent without the encoding (as mentioned here). Still, I've also tried with the "auth" property, and I get the same result.
I'm actually making this call from inside an ExpressJS API (my client calls the Express API, that calls the above code - I've edited all that out of this example for simplicity). That's why my variables are "hres" and "hreq", to distinguish them from the "res" and "req" in Express. Is there any reason that could be the issue?
As mentioned above, I am able to get successful results when using POSTman, so I at least know my host, path, list ID, and API key are correct.
It turns out this had a very simple solution: the "host" property of the options object needed to have only the domain name. IE, remove the "https://" protocol:
var options = {
host: 'us11.api.mailchimp.com',
path: '/3.0/lists/<myListID>/members',
method: 'POST',
headers: {
'Authorization': 'randomUser myApiKey',
'Content-Type': 'application/json',
'Content-Length': subscriber.length
}
}
Try this , its working fine for Me.
var request = require('request');
function mailchimpAddListCall(email, cb){
var subscriber = JSON.stringify({
"email_address": email,
"status": "subscribed"
});
request({
method: 'POST',
url: 'https://us13.api.mailchimp.com/3.0/lists/<Your list id>/members',
body: subscriber,
headers:
{
Authorization: 'apikey <your Mailchimp API key>',
'Content-Type': 'application/json'
}
},
function(error, response, body){
if(error) {
cb(err, null)
} else {
var bodyObj = JSON.parse(body);
console.log(bodyObj.status);
if(bodyObj.status === 400){
cb(bodyObj.detail, null);
}
var bodyObj = JSON.parse(body);
cb(null, bodyObj.email_address +" added to list.");
}
});
}
request is a node module, that you'll need to install into your package.json. npm install --save request
You can use the auth properties just fine with API v3, but if you're getting a 400, that's not the problem. The body of the 400 Error should provide more detailed information, but one thing that jumps out immediately: MailChimp doesn't allow fake or fake-looking emails to be added to lists (like test#test.com), so I'd try a real address and see if that works for you.

angular $resource delete won't send body to express.js server

hye,
i am building an app with angular.js and node.js (Express.js) on the server side.
for some reason i am having a problem handling a delete request. no body is getting to the server side.
this is my angular.js resource code:
$scope.deleteProject = function(projectName){
var postData = {username: 'name', projectName: projectName};
Project.deleteProject.delete({}, postData,
function(res){
alert('Project Deleted');
},
function(err){
alert(err.data);
});
}
on the server side i have this:
var deleteProject = function(req, res){
console.log(req.body);
console.log(req.params);
if (req.body.projectName){
//do something
return res.send(200);
}
else
return res.send(400, 'no project name was specified');
}
now for some reason there is no body at all!! it is empty.
i have defined the route as app.delete.
if i change the route in node.js to post and in angular.js to save it works fine.
what am i missing here (banging my head).
thanks.
As per this stack overflow question and the $http service source code, a DELETE request using $http does not allow for data to be sent in the body of the request. The spec for a DELETE request is somewhat vague on whether or not a request body should be allowed, but Angular does not support it.
The only methods that allow for request bodies are POST, PUT, and PATCH. So the problem is not anywhere in your code, its in Angular's $http service.
My suggestion would be to use the generic $http(...) function and pass in the proper method:
$http({
method: 'DELETE',
url: '/some/url',
data: {...},
headers: {'Content-Type': 'application/json;charset=utf-8'}
})
Angular by default sends the Content-Type as text/plain for DELETE requests. Just add this to the headers:
var config = {
method: "DELETE"
url: yourUrl
data: yourData
headers: {"Content-Type": "application/json;charset=utf-8"}
};
$http(config);
If you want to add them to every single DELETE request add this to the app.config method in your main controller:
$httpProvider.defaults.headers.delete = { "Content-Type": "application/json;charset=utf-8" };
If you want to use the $resource object instead of $http you need to add hasBody and headers as follow:
delete: {
method: 'DELETE',
hasBody: true,
headers: {"Content-Type": "application/json;charset=UTF-8"}
}
Worked for me
Just ran into this problem. You'll have to use url params to send an id with delete.
in express:
app.delete('/api/user/:userId', user.remove);
and add to the url in angular:
$http({url: 'whatever/api/'+obj.id, method: 'DELETE'}) ...
The following works for me:
$httpProvider.defaults.headers.common['X-Requested-With'] = 'XMLHttpRequest';
$httpProvider.defaults.headers.common['Content-Type'] = 'application/json;charset=utf-8';
XMLHttpRequest is optional but useful if you are sending ajax.
https://docs.angularjs.org/api/ng/provider/$httpProvider for more information.
This worked for me.
$httpProvider.defaults.headers.delete = { "Content-Type": "application/json;charset=utf-8" };
And then
$http.delete(url, { data: data })

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