How to handle ETIMEDOUT error? - javascript

How to handle etimedout error on this call ?
var remotePath = "myremoteurltocopy"
var localStream = fs.createWriteStream("myfil");;
var out = request({ uri: remotePath });
out.on('response', function (resp) {
if (resp.statusCode === 200) {
out.pipe(localStream);
localStream.on('close', function () {
copyconcurenceacces--;
console.log('aftercopy');
callback(null, localFile);
});
}
else
callback(new Error("No file found at given url."), null);
})
There are a way to wait for longer? or to request the remote file again?
What exactly can cause this error? Timeout only?

This is caused when your request response is not received in given time(by timeout request module option).
Basically to catch that error first, you need to register a handler on error, so the unhandled error won't be thrown anymore: out.on('error', function (err) { /* handle errors here */ }). Some more explanation here.
In the handler you can check if the error is ETIMEDOUT and apply your own logic: if (err.message.code === 'ETIMEDOUT') { /* apply logic */ }.
If you want to request for the file again, I suggest using node-retry or node-backoff modules. It makes things much simpler.
If you want to wait longer, you can set timeout option of request yourself. You can set it to 0 for no timeout.

We could look at error object for a property code that mentions the possible system error and in cases of ETIMEDOUT where a network call fails, act accordingly.
if (err.code === 'ETIMEDOUT') {
console.log('My dish error: ', util.inspect(err, { showHidden: true, depth: 2 }));
}

In case if you are using node js, then this could be the possible solution
const express = require("express");
const app = express();
const server = app.listen(8080);
server.keepAliveTimeout = 61 * 1000;
https://medium.com/hk01-tech/running-eks-in-production-for-2-years-the-kubernetes-journey-at-hk01-68130e603d76

Try switching internet networks and test again your code. I got this error and the only solution was switching to another internet.
Edit: I now know people besides me that have had this error and the solution was communicating with the ISP and ask them to chek the dns configuration because the http request were failing. So switching networks definitely could help with this.
That is why I will not delete the post. I could save people a few days of headaches (especially noobs like me).

Simply use a different network. Using a different network solved this issue for me within seconds.

Related

how can make mongoose fail when executing find query

Hi everyone I'm writing mocha unit tests for my server. How can I get error for mongoose find query. I've tried close the connection before execute but there's nothing firing.
User.find({}, (err, result) => {
if (err) {
// I want to get here
}
return done(result);
});
The following DO NOT WORK with mongoose, at least for now (5.0.17) :
Closing the connection to mongoose is a way to test it, in addition to a proper timeout to set on the find request.
const request = User.find({});
request.maxTime(1000);
request.exec()
.then(...)
.catch(...);
or
User.find({}, { maxTimeMS: 1000 }, (err, result) => {
if (err) {
// I want to get here
}
return done(result);
});
EDIT after further researches :
After trying it myself, it seems that I never get an error from the request.
Changing request maxTime or connection parameters auto_reconnect, socketTimeoutMS, and connectTimeoutMS do not seems to have any effect. The request still hang.
I've found this stack overflow answer saying that all request are queued when mongoose is disconnected from the database. So we won't get any timeout from there.
A soluce I can recommand and that I use on my own project for another reason would be to wrap the mongoose request into a class of my own. So I could check and throw an error myself in case of disconnected database.
In my opinion, the best way to test your error handling is to use mock. More information in this previous stackoverflow topic.
You can mock the mongoose connection and api to drive your test (raise errors...).
Libraries:
sinonjs
testdouble
I solved it like below. Here is the solution.
User = sinon.stub(User.prototype, 'find');
User.yields(new Error('An error occured'), undefined);
By this code it will return error. #ormaz #grégory-neut Thanks for the help.

How to call web service from Alexa Lambda function

I want to make a GET request to a web site using the Amazon Profile API. I am trying to do what is described in the last code chunk in this article: https://developer.amazon.com/blogs/post/Tx3CX1ETRZZ2NPC/Alexa-Account-Linking-5-Steps-to-Seamlessly-Link-Your-Alexa-Skill-with-Login-wit (very end of article) and it just does not happen. My callback function never seems to get called.
I have added the required context.succeed(), actually the latest version of that, and am still not getting results. I know the url is good, as I can take it and copy/paste into a browser and it returns an expected result.
Here is a SO answer on using the appropriate context function calls within the callback, which I have tried. Why is this HTTP request not working on AWS Lambda?
I am not using a VPC.
What am I doing wrong? I feel like a moron, as I have been researching this and trying solutions for 2 days. I log the full URL, and when I copy/paste that out of the log file, and put it in a browser window, I do get a valid result. Thanks for your help.
Here is the code:
function getUserProfileInfo(token, context) {
console.log("IN getUserProfileInfo");
var request = require('request');
var amznProfileURL = 'https://api.amazon.com/user/profile?access_token=';
amznProfileURL += token;
console.log("calling it");
console.log(amznProfileURL);
console.log("called it");
request(amznProfileURL, function(error, response, body) {
if (!error && response.statusCode == 200) {
var profile = JSON.parse(body);
console.log("IN getUserProfileInfo success");
console.log(profile);
context.callbackWaitsForEmptyEventLoop = false;
callback(null, 'Success message');
} else {
console.log("in getUserProfileInfo fail");
console.log(error);
context.callbackWaitsForEmptyEventLoop = false;
callback('Fail object', 'Failed result');
}
});
console.log("OUT getUserProfileInfo");
}
This is the logging output I get in CloudWatch:
2017-03-08T22:20:53.671Z 7e393297-044d-11e7-9422-39f5f7f812f6 IN getUserProfileInfo
2017-03-08T22:20:53.728Z 7e393297-044d-11e7-9422-39f5f7f812f6 OUT getUserProfileInfo
Problem might be that you are using var request = require('request'); which is external dependency and will require you to make a packaged lambda deployment for it to work. See this answer for relevant information.
AWS Node JS with Request
Another way is that you can use NodeJS module such as var http= require('http'); which is builtin module to make the requests. This way you can just make plain lambda script deployment.
Reference
http://docs.aws.amazon.com/lambda/latest/dg/nodejs-create-deployment-pkg.html

Node http.ClientRequest does not fire "error" event

I have the following javascript node.js code:
var options = {
host: "x.y.z"
,path: "/api/abc/"
,method: "GET"
};
var req = http.request(options);
req.on('response' , function(data) {
console.log("response: ",data.statusCode);
done();
});
req.on('error' , function() {
console.log("error");
done();
});
req.end();
I can't get the error event when an actual HTTP request error occurs. What am I missing ?
Preliminary findings: It would appear that the failure case "no response from server" (e.g. due to network issue) does not fire any event. So, the workaround is to create a 'timer' and trap this condition by yourself.
Try using an if / else statement instead of two independent functions.
if(response you want && response.statusCode = 200){
//logic
} else {
//console.log("error")
}
You should create your own Timeout function inside the request. In fact, I believe that after a lot of time (maybe a minute?) the request would fail. But, if you require something more earlier, you can check this thread that asks for the same thing:
How to set a timeout on a http.request() in Node?

React/Redux + super agent, first call gets terminated

I am writing a react-redux app where I am making some service calls in my middlewares using superagent. I have found a very strange behavior where the first call to my search api always gets terminated. I have tried waiting 10-30 seconds before making the first call, and logging every step along the process and I cannot seem to pinpoint why this is happening.
My action creator looks like
export function getSearchResults(searchQuery) {
return {
query: searchQuery,
type: actions.GO_TO_SEARCH_RESULTS
}
}
It hits the middleware logic here :
var defaultURL = '/myServer/mySearch';
callPendingAction();
superagent.get(defaultURL)
.query({query: action.query})
.end(requestDone);
//sets state pending so we can use loading spinner
function callPendingAction() {
action.middlewares.searchIRC.readyState = READY_STATES.PENDING;
next(action);
}
//return error or response accordingly
function requestDone(err, response) {
console.log("call error", err);
const search = action.search;
if (err) {
search.readyState = READY_STATES.FAILURE;
if (response) {
search.error = response.err;
} else if (err.message) {
search.error = err.message;
} else {
search.error = err;
}
} else {
search.readyState = READY_STATES.SUCCESS;
search.results = fromJS(response.body);
}
return next(action);
}
The query is correct even when the call is terminated, I get this err message back :
Request has been terminated
Possible causes: the network is offline, Origin is not allowed by Access-Control-Allow-Origin, the page is being unloaded, etc.
at Request.crossDomainError (http://localhost:8000/bundle.js:28339:14)
at XMLHttpRequest.xhr.onreadystatechange (http://localhost:8000/bundle.js:28409:20)
It appears the page refreshes each time too.
I cannot seem to find any clues as to why this happens, it seems not matter what the first call fails, but then it is fine after that first terminated call. Would appreciate any input, thanks!
UPDATE: so it seems this is related to chrome, I am on Version 47.0.2526.80 (64-bit). This app is an iframe within another app and I believe that is causing a problem with chrome because when I try this in firefox there is no issue. What is strange is only the first call gives the CORS issue, then it seems to be corrected after that. If anyone has input or a workaround, I would greatly appreciate it. Thanks for reading.
Had the same problem, just figured it out thanks to the answer provided by #KietIG on the topic ReactJS with React Router - strange routing behaviour on Chrome.
The answer had nothing to do with CORS. The request was cancelled because Chrome had navigated away from the page in the middle of the request. This was happening because event.preventDefault() had not been called in one of the form submit handlers. It seems Chrome handles this differently than other browsers.
See the answer link above for more detail.
In my case this was happening when I tried to set a random HTTP request header (like X-Test) on the client side and either AWS Lambda rejected it during the OPTIONS request or something else did that.
I don't know about the side effects, but you're getting CORS errors. Add the .withCredentials() method to your request.
From the superagent docs:
The .withCredentials() method enables the ability to send cookies from
the origin, however only when "Access-Control-Allow-Origin" is not a
wildcard ("*"), and "Access-Control-Allow-Credentials" is "true".
This should fix it:
superagent.get(defaultURL)
.query({query: action.query})
.withCredentials()
.end(requestDone);
More information on Cross Origin Resource Sharing can be found here.

Error conditions for NPM Request lib

An error is being passed by the callback in my request function. I am trying to determine under what conditions an error is passed to the callback.
var request = require('request');
request('http://www.google.com', function (error, response, body) {
if(error){
//why or when would an error be created?
}
else if (response.statusCode == 200) {
console.log(body) // Show the HTML for the Google homepage.
}
else{
// when would this happen ?
}
})
the documentation doesn't seem to cover what conditions will cause an error object to be created and passed. Right now I just assume anything but a 200 or 300 will cause an error to be created, but I am just guessing.
request library uses the node.js http module internally for making GET request. From it's doc:
If any error is encountered during the request (be that with DNS
resolution, TCP level errors, or actual HTTP parse errors) an 'error'
event is emitted on the returned request object.
I guess you have to go though the http module source to exactly find out what are the errors.

Categories

Resources