Issues while calling Wikipedia Api using node.js - node.js

var request = require("request");
var query = "english";
var url = "https://en.wikipedia.org/w/api.php?action=opensearch&search="${query}"&format=json";
request(url, function (err, response, body) {
if(err){
var error = "cannot connect to the server";
console.log(error);
} else {
console.log("body:",body);
}
});
I have written this code in code editor.
I have used npm install request --save but while running the program in console, it is displaying only "body:" not the content .
Please suggest what changes are required.

Your main code should not be in an else statement. It should simply be in the function and have the error in the if statement.
var request = require('request');
var query = 'english';
var url = `https://en.wikipedia.org/w/api.php?action=opensearch&search=${query}&format=json`
request(url, function (err, response, body) {
console.log('body:',body);
if(err){
var error = "cannot connect to the server";
console.log(error);
}
});

You have some syntax errors in your code. Change the part before the request function to the following:
var request = require('request')
var query = 'english'
var url = `https://en.wikipedia.org/w/api.php?action=opensearch&search=${query}&format=json`

Related

Can't remove headers after they are sent in Koa

I coded a minimalist server to manage REST services. The only coded route is supposed to retrieve data from mongo, then to send it to the client. Code is below.
var kr = require('koa-route');
var koa = require('koa');
var app = koa();
var MongoClient = require("mongodb").MongoClient;
var events = function * ()
{
var _this = this;
MongoClient.connect("mongodb://localhost/eventdata", function(error, db) {
if (error) throw(error);
console.log("Connecté à la base de données");
db.collection('events').find().toArray(function(err, array)
{
console.log('returning %d objects', array.length);
db.close();
_this.body = {eventsArray : array};
});
});
}
app.use(kr.get('/events', events));
app.listen(3000);
Koa is version 1.2.4
When I try to reach it, I get the error message "Can't remove headers after they are sent". I managed to understand that the program (sort of) finishes to send back response before the find() is over. So when the _this.body = { ... } is called, this causes the error.
Now question is : how to fix that ?
I just began to practice Koa, so there are a lot of stuff I'm not used to.
I tested solution proposed here : Can't remove headers after they are sent but it doesn't work. I get the following error message :
eventsArray = yield db.collection('events').find({})
^^
SyntaxError : unexpected identifier
Thanks in advance for your help.
it looks like you need to wrap db req to promise. Try in this way
var kr = require('koa-route');
var koa = require('koa');
var app = koa();
var MongoClient = require("mongodb").MongoClient;
var eventsPromise = function(){
return new Promise(function(resolve, reject){
MongoClient.connect("mongodb://localhost/eventdata", function(error, db) {
if (error){
return reject(error);
}
console.log("Connecté à la base de données");
db.collection('events').find().toArray(function(err, array)
{
console.log('returning %d objects', array.length);
db.close();
return reslove({eventsArray : array});
});
});
});
}
var events = function * ()
{
var event = yiled eventsPromise();
this.body = event;
}
app.use(kr.get('/events', events));
app.listen(3000);

Pass body of request to calling function using node request module

I wrote a small module that makes a Get Request using the 'request' module. I want to do call it from another script, and use the result of the Get on the calling function like so:
var request = require('request');
function SendGet(uri) {
var outer_body = "test";
request(uri, function(error, response, body) {
console.log(body);
outer_body = body;
});
console.log(outer_body);
return outer_body;
}
exports.GetRequest = SendGet;
Then I use it like this:
var MyReq = require('./reqtest');
var uri = "http://api.myhost.com";
var result = MyReq.GetRequest(uri);
console.log("My result is:",result);
When I run it, I see in the console the body of the response when using the GetRequest but the variable that is returned still has the value used to initialize it:
c:\node messages.js
test
My result is: test
<full body here>
c:\
How can I pass back the body to the calling function?
thank you
Try this
var request = require('request');
function SendGet(uri) {
var outer_body = "test";
outer_body = request(uri, function(error, response, body) {
console.log(body);
return body;
});
console.log(outer_body);
return outer_body;
}
exports.GetRequest = SendGet;
Here you are returning the result of your callback to the variable outer_body

Calling a module's local function as callback in "request"

In my main code, I do the following:
var module = require('./module')
module.FooA(module.FooB);
module.js contains the next code:
var request = require('request'); //using of npm "request"
exports.FooB = function(data){ /*operations on data here*/ };
exports.FooA = function(callback){
var url = some_link;
request(url, function (error, response, body) {
if (!error && response.statusCode == 200) {
callback(body);
};
});
};
The issue is that apparently, callback(body) doesn't run even if the conditions meet. var result = request(url) followed by exports.FooB(result) does the job, but as far as I can see, obviously does not act like a callback, and would produce troubles.
What is the proper way of defining a callback function in such a case? Do I need at all, or it is actually synchronous and I missed to notice it?
Use first function callback params with error, this is an default in node.js core and is google for your project functions.
And like #ShanSan commend, use console.log, console.error or console.trace for debug.
Example:
var request = require('request'); //using of npm "request"
exports.FooB = function(error, data){ /*operations on data here*/ };
exports.FooA = function(callback){
var url = some_link;
request(url, function (error, response, body) {
if (error || response.statusCode != 200) {
// pass error to callback and if use return you dont need other code block bellow
console.error('Error in request', error);
return callback(error, null);
}
// here run if dont have errors
// if need more info use the console.log(request); or console.log(body);
// use error in first param in callback functions
callback(null, body);
});
};

Inconsistent method result in node js

I have been trying to figure the following for the last couple of days and just can't seem to figure out the answer. I am new to node and JS (only experience is online tutorials).
I am trying to create a class (function) to scrape the source code from websites. I want to read in a url from the command line and return the html content. However, I seem to be getting different results when running the code different ways (which I think I should be getting the same results).
I have been reading about events in node and so I have used them a little in the code. One listener event prompts the me for the url and then after setting the url it (the listener function) emits a message, which is picked up by another listener which goes out and fetches the html content.
The problem I am having is that when I create an instance of the object, it seems like the request portion of the code does not execute. However, if I call the method from the instance I get the print out of the html content of the page.
Any help is appreciated. Thanks.
function test() {
var events = require('events').EventEmitter;
var request = require('request');
var util = require('util');
var that = this;
that.eventEmitter = new events();
that.url = 'http://www.imdb.com/';
that.eventEmitter.on('setURL',that.setUrl = function(){
console.log("Input the URL: ");
process.stdin.resume();
process.stdin.setEncoding('utf8');
process.stdin.on('data', function (text) {
that.url = util.inspect(text);
that.url = that.url.substr(1, that.url.length - 4);
that.eventEmitter.emit('Get url html');
process.exit();
});
});
that.eventEmitter.on('Get url html',that.httpGet = function() {
console.log("Fetching... " + that.url);
request(that.url, function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body) // Show the HTML for the Google homepage.
} else {
console.log("Error Encountered");
}
});
});
that.eventEmitter.emit('setURL');
}
var scrapper = new test(); //This asks me for the url and then only executes to first line of that.httpGet.
scrapper.httpGet(); // This gives the desired results from that.httpGet
I solved using the Prompt library https://www.npmjs.com/package/prompt
function test() {
var events = require('events').EventEmitter;
var prompt = require('prompt');
var request = require('request');
var util = require('util');
var that = this;
that.eventEmitter = new events();
that.url = 'http://www.imdb.com/';
that.eventEmitter.on('setURL',that.setUrl = function(){
prompt.start();
process.stdin.setEncoding('utf8');
prompt.get(['url'], function( err, result ) {
that.url = result.url;
that.eventEmitter.emit('Get url html');
} );
});
that.eventEmitter.on('Get url html',that.httpGet = function() {
console.log("Fetching... " + that.url);
request(that.url, function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body); // Show the HTML for the Google homepage.
} else {
console.log("Error Encountered");
}
});
});
that.eventEmitter.emit('setURL');
}
var scrapper = new test(); //This asks me for the url and then only executes to first line of that.httpGet.
// scrapper.httpGet(); // This gives the desired results from that.httpGet
I ran the script from the commandline, input http://www.google.com and it retrieved the results without the additional call to scrapper.httpGet();

node.js server handle request callback function ending before writing response

I have an http server with a handleRequest callback that runs another script in vm.runInNewContext for each request. The script that runs inside vm.runInNewContext makes some asynchronous http post requests and writes the server response only after getting the responses from the posts.
As a result, the code of handleRequest callback ends before the server response is written.
Is it safe? or is there a way to avoid this situation?
Here is some code:
var server = http.createServer(handleRequest);
server.listen(8080);
var handleRequest = function (request, response) {
// get request data...
var context = {
ServerRequest : request,
ServerResponse : response
};
var stringScript = // a string with the script that posts data
var script = vm.createScript(stringScript);
script.runInNewContext({ context: context });
}
the script string does this:
var request = require('request');
var options = {....}
var req = request.get(options);
req.on('response', function (res) {
var chunks = [];
res.on('data', function(chunk) {
chunks.push(chunk);
});
res.on('end', function() {
var buffer = Buffer.concat(chunks);
var encoding = res.headers['content-encoding'];
if (encoding == 'gzip') {
zlib.gunzip(buffer, function(err, decoded) {
// set response headers and write the response
context.ServerResponse.end(decoded.toString());
});
} else if (encoding == 'deflate') {
zlib.inflate(buffer, function(err, decoded) {
// set response headers and write the response
context.ServerResponse.end(decoded.toString());
})
} else {
// set response headers and write the response
context.ServerResponse.end(buffer.toString());
}
});
});
Simple solution: Return a promise (e.g. use the Q-library) from the VM-script.
script.runInNewContext will return whatever you return from the VM-script. That way you have a "callback" for when the VM code finishes.
// Script for VM
// I simplified it. Just resolve or reject the promise whenever you are done with your work
'use strict';
var defer = q.defer();
doABarrelRoll(function() {
defer.resolve('RESULT');
});
defer.promise; // This line will return the promise.
When returning a value from a VM-script, you do not need any return construction. Just write the thing you want and let the magic happen.
// Script for current context
'use strict';
var server = http.createServer(handleRequest);
server.listen(8080);
var handleRequest = function (request, response) {
// get request data...
var context = {
ServerRequest : request,
ServerResponse : response
};
var stringScript = // a string with the script that posts data
var script = vm.createScript(stringScript);
var prom = script.runInNewContext({
context: context,
q: require('q'),
});
prom.done(function ($result) {
console.log('VM finished with result: ' + $result);
});
}

Resources