I am calling an api of sending OTP from my nodejs app. I need to send the response of that OTP Api to the angular app.
my api service on angular look like this:
sendOtp(params): Observable<any> {
return this.apiService.post("/user/send-otp", params)
}
my router on express app look like this
this.router.post("/user/send-otp", userController.sendOtpMessage);
and the code inside userController look like this.
static sendOtpMessage(req, res ,next) {
const phone = req.body.phone;
var http = require("https");
var options = {
"method": "GET",
"hostname": "api.msg91.com",
"port": null,
"path": `/api/v5/otp?mobile=${phone}`,
"headers": {
"content-type": "application/json"
}
};
var callOtpApi = http.request(options, function (res) {
var chunks = [];
res.on("data", function (chunk) {
chunks.push(chunk);
});
res.on("end", function () {
var body = Buffer.concat(chunks);
console.log(body.toString());
// I need to send this data in response to my angular app ==>> body.toString()
});
});
callOtpApi.write();
callOtpApi.end();
}
OTP Api ref document: https://docs.msg91.com/p/tf9GTextN/e/B1NUt3C8MY/MSG91
It seems that the code above is missing the res.send() to return the data from server. Could you please try with this?
static sendOtpMessage(req, res ,next) {
const serverRes = res;
// Rest of your code
...
var callOtpApi = http.request(options, function (res) {
// Rest of your code
...
res.on("end", function () {
var body = Buffer.concat(chunks);
console.log(body.toString());
// Return data to client
serverRes.send(body.toString());
});
// Rest of your code
...
});
}
You can call the msg91 api using axios
const axios = require('axios');
async function sendOtpTOUser(phone) {
const template = "template _id";
const apiKey = "api_key";
const sendotp = "https://api.msg91.com/api/v5/otp?template_id="+template+"&mobile="+phone+"&authkey="+apiKey;
let request_options1 = {
method: 'get',
url: sendotp
};
let otpResponse = await axios(request_options1);
console.log(otpResponse.data)
return otpResponse.data;
}
it will return the object as
{ request_id: '3166686e7867313634383535', type: 'success' }
Related
I am working on a little project to learn how to work with APIs by making GET requests to the Twitter API v2 via a node server.
For the get requests I am using Node's built in https package.
I made a basic GET request that returns a list of the last 10 tweets from a user.
I think in order to increase the amount of tweets I can get I have to make a separate parameter object, which I then implement in the get request.
Right now my function looks like this:
function getTweets() {
const options = {
host: "api.twitter.com",
path: `/2/users/${userId}/tweets`,
headers: {
authorization:
`Bearer ${bearerToken}`,
},
};
https
.get(options, (response) => {
let data = "";
response.on("data", (chunk) => {
data += chunk;
});
response.on("end", () => {
let jsonObject = JSON.parse(data);
tweetObjects = jsonObject.data;
tweetObjects.map((item) => {
let tweetWords = "";
tweetWords += item.text;
userTweets.push(tweetWords);
});
const result = userTweets.flatMap((str) => str.split(" "));
console.log(result);
});
})
.on("error", (error) => {
console.log(error);
});
}
Right now I only have the options object with host, path, and headers in the request.
This is what I am trying to do:
function getTweets() {
const options = {
host: "api.twitter.com",
path: `/2/users/${userId}/tweets`,
headers: {
authorization:
`Bearer ${bearerToken}`,
},
};
let params = {
max_results: 100,
};
https
.get(params, options, (response) => {
let data = "";
response.on("data", (chunk) => {
data += chunk;
});
response.on("end", () => {
let jsonObject = JSON.parse(data);
tweetObjects = jsonObject.data;
tweetObjects.map((item) => {
let tweetWords = "";
tweetWords += item.text;
userTweets.push(tweetWords);
});
const result = userTweets.flatMap((str) => str.split(" "));
console.log(result);
});
})
.on("error", (error) => {
console.log(error);
});
}
But I get
throw new ERR_INVALID_ARG_TYPE('listener', 'Function', listener);
^
TypeError [ERR_INVALID_ARG_TYPE]: The "listener" argument must be of type function. Received an instance of Object
at checkListener (events.js:131:11)
at ClientRequest.once (events.js:496:3)
at new ClientRequest (_http_client.js:215:10)
at request (https.js:326:10)
at Object.get (https.js:330:15)
at IncomingMessage.emit (events.js:388:22)
at endReadableNT (internal/streams/readable.js:1336:12)
at processTicksAndRejections (internal/process/task_queues.js:82:21) {
code: 'ERR_INVALID_ARG_TYPE'
You can either only pass the URL or an object containing options as stated in the docs:
https://nodejs.org/api/https.html#https_https_get_url_options_callback
So you might want to try something like this:
function getTweets() {
let params = {
max_results: 100,
};
const options = {
host: "api.twitter.com",
path: `/2/users/${userId}/tweets?max_results=${params.max_results}`,
headers: {
authorization:
`Bearer ${bearerToken}`,
},
};
https
.get(options, (response) => {
let data = "";
...
}
I am not sure to understand what you are calling parameters that you want to give to the get request.
Anyway a get request does not take some body or parameter. If you want to add some data to the core of your request you have to use the post method and not the get one.
Can you show us the import of https library just to check the functions that it propose?
Best Regards,
Hugo Delatte
Maybe you can help me with the following problem.
I'm currently working on a project.
Github Project // On Netifly
On the client side, I'm using Axios to perform a post request with route /getContent. Once on the server, the content is sent to a third party API to perform analysis. The Response is then send back to the client side.
Everything is working well locally but when deploying the project on Netifly, I have an error 404 when the browser is targeting that route `/getContent'
POST request on the client Side:
const getData = async (txt) => {
const response = await axios.post("/getContent", { txt });
return response;
};
On the server side with express
/**
* MeaningCloud Object
* main param + url
*/
const meaningCloudReq = {
params: {
key: null,
lang: "uk",
txt: null,
txtf: "plain",
},
url: `https://api.meaningcloud.com/sentiment-2.1`,
getData: async function () {
const { params } = this;
const response = await axios.get(this.url, { params });
return response.data;
},
};
const callApi = async (req, res) => {
const { txt } = req.body;
const key = process.env.API_KEY;
const params = { ...meaningCloudReq.params, txt, key };
const requestApi = { ...meaningCloudReq, params };
try {
const data = await requestApi.getData();
res.send(data);
} catch (error) {
const status = {
status: "500",
msg: "Request did not go throught, contact support.",
};
res.send({ status });
}
};
app.post("/getContent", callApi); // the getContent route
Yet, I kept receiving the following error:
XHR POST https://fervent-rosalind-abbe0e.netlify.app/getContent
[HTTP/2 404 Not Found 1072ms]
Let me know if you have any idea about what's going on.
I created Azure function app with http trigger which should return JSON file.
Here is part of my nodejs script.
var promise = Promise.all([getFood("first"), getFood("second"), getFood("third")]);
promise.then(function(data) {
let res = JSON.stringify(data);
context.res = {
body: res
};
context.done();
});
It returns nothing.
But when I try script with something like this it works:
var promise = Promise.all([getFood("first"), getFood("second"), getFood("third")]);
promise.then(function(data) {
let res = JSON.stringify(data);
});
context.res = {
body:"This is text"
};
context.done();
And it will return string in body.
Try this:
module.exports = async function (context, req) {
var data = await Promise.all([getFood("first"), getFood("second"),getFood("third")]);
return {
body: JSON.stringify(data)
};
}
I would like to use two IBM Watson services and combine the responses from both in one variable and return it as a callback. I couldn't figure out how to get response1 value outside the http request to combine it with response2 from the other IBM Watson service.
I tried the below code and it didn't work. I read that I can use promises, but I'm pretty new to this, and couldn't figure out how to do this.
Can anyone help please?
const AWS = require('aws-sdk');
var http = require('https');
exports.handler = (event, context, callback) => {
var text = JSON.stringify(event.text);
var options = {
method: process.env.method,
hostname: process.env.watson_hostname,
port: null,
path: process.env.path,
headers: {
'content-type': process.env.content_type,
authorization: process.env.authorization,
'cache-control': process.env.cache_control,
'X-Watson-Learning-Opt-Out': 'true'
}
};
var req = http.request(options, function (res) {
var chunks = "";
res.on("data", function (chunk) {
chunks+ = chunk.toString();;
});
res.on("end", function () {
var response1 = (chunks);
//////////////here I need to get reponse2
var response2 = IBM2();
var bothResponses = response1 + response2
callback(null,bothResponses)
});
})
req.write(text);
req.end()
function IBM2(){
var text = JSON.stringify(event.text);
var options = {
method: process.env.method2,
hostname: process.env.watson_hostname2,
port: null,
path: process.env.path2,
headers: {
'content-type': process.env.content_type2,
authorization: process.env.authorization2,
'cache-control': process.env.cache_control,
'X-Watson-Learning-Opt-Out': 'true'
}
};
var req = http.request(options, function (res) {
var chunks = [];
res.on("data", function (chunk) {
chunks.push(chunk);
});
res.on("end", function () {
var response2 = JSON.parse(Buffer.concat(chunks));
return(response2)
}
Return a promise from your IBM2 function and handle using async await in the calling function. Notice the async keyword before on end callback.
I have tried to add Promise to your existing flow:
const AWS = require('aws-sdk');
var http = require('https');
exports.handler = (event, context, callback) => {
var text = JSON.stringify(event.text);
var options = {
method: process.env.method,
hostname: process.env.watson_hostname,
port: null,
path: process.env.path,
headers: {
'content-type': process.env.content_type,
authorization: process.env.authorization,
'cache-control': process.env.cache_control,
'X-Watson-Learning-Opt-Out': 'true'
}
};
var req = http.request(options, function (res) {
var chunks = "";
res.on("data", function (chunk) {
chunks += chunk.toString();;
});
res.on("end", async function () {
var response1 = (chunks);
//////////////here I need to get reponse2
var response2 = await IBM2();
// validate response2 (in case IBM2 throws error)
var bothResponses = response1 + response2;
callback(null,bothResponses)
});
});
req.write(text);
req.end();
function IBM2(){
return new Promise((resolve, reject) =>{
var text = JSON.stringify(event.text);
var options = {
method: process.env.method2,
hostname: process.env.watson_hostname2,
port: null,
path: process.env.path2,
headers: {
'content-type': process.env.content_type2,
authorization: process.env.authorization2,
'cache-control': process.env.cache_control,
'X-Watson-Learning-Opt-Out': 'true'
}
};
var req = http.request(options, function (res) {
var chunks = [];
res.on("data", function (chunk) {
chunks.push(chunk);
});
res.on("end", function () {
var response2 = JSON.parse(Buffer.concat(chunks));
resolve(response2)
});
res.on("error", function (err) {
reject(err);
});
})
});
}
};
Before making any changes to your code, I would suggest you go thru these topics first.
For reference, do take a look into the concept of promises and async-await
Promiese
Async/Await
Dont know if you have other errors, but it looks like youre not waiting for response2 to finish, maybe something like
const response2 = await IBM2():
or if you want to use promises maybe something like:
res.on('end', function () {
var response2 = IBM2().then(
val => {
var bothResponses = response1 + val;
callback(null, bothResponses);
},
reject => {
/* handle rejection here */
},
);
});
I'm banging my head for not learning from the basics and just jumping in.
I'm building an API that returns the SSL Certificate status of a domain.
It's working fine on console.log but the JSON output is empty, obviously because the exports get executed before the https request ends.
How do I incorporate the exports in response.on(end) function?
Thanks a lot!
function getSSL(domain) {
var options = {
host: 'www.'+domain+'.com',
method: 'get',
path: '/'
};
var isAuth = false;
callback = function(response) {
response.on('data', function () {
isAuth = response.socket.authorized;
});
response.on('end', function () {
console.log(isAuth);
});
}
var req = https.request(options, callback).end();
}
exports.findByDomain = function (req, response) {
var id = req.params.id;
sslCheck = getSSL(id);
response.send(sslCheck);
};
Yes, the response.send(sslCheck); gets executed before getSSL(id); has a chance to finish. You need to send in a callback so it can be executed after getSSL(id); finishes:
function getSSL(domain, callback) {
var options = {
host: 'www.'+domain+'.com',
method: 'get',
path: '/'
};
var isAuth = false;
var httpCallback = function(response) {
response.on('data', function () {
isAuth = response.socket.authorized;
});
response.on('end', function () {
console.log(isAuth);
callback(isAuth);
});
}
var req = https.request(options, httpCallback).end();
}
exports.findByDomain = function (req, response) {
var id = req.params.id;
getSSL(id, function(sslCheck) {
response.send(sslCheck);
});
};