2013-11-25 13 views
20

ho scritto semplice proxy nodejs e sembraGestione degli errori su richiesta tubazioni

var request = require('request'); 
app.all('/proxy/*', function(req, res){ 
    req.pipe(request({ 
     url: config.backendUrl + req.params[0], 
     qs: req.query, 
     method: req.method 
    })).pipe(res); 
}); 

Funziona bene se l'host remoto è disponibile, ma se host remoto non è disponibile l'intero server nodo si blocca con un'eccezione non gestita

stream.js:94            
     throw er; // Unhandled stream error in pipe.   
      ^            
Error: connect ECONNREFUSED         
    at errnoException (net.js:901:11)      
    at Object.afterConnect [as oncomplete] (net.js:892:19) 

Come posso gestire tali errori?

+0

[Risposte migliori qui] (http://stackoverflow.com/questions/7222982/node-request-how-to-determine-if-an-error-error-occured-the-request) – laggingreflex

risposta

28

Guardando la documentazione (https://github.com/mikeal/request) si dovrebbe essere in grado di fare qualcosa secondo le seguenti linee:

È possibile utilizzare l'argomento opzionale richiamata su richiesta, ad esempio:

app.all('/proxy/*', function(req, res){ 
    req.pipe(request({ 
     url: config.backendUrl + req.params[0], 
     qs: req.query, 
     method: req.method 
    }, function(error, response, body){ 
    if (error.code === 'ECONNREFUSED'){ 
     console.error('Refused connection'); 
    } else { 
     throw error; 
    } 
    })).pipe(res); 
}); 

In alternativa, è in grado di catturare un'eccezione non rilevata, con qualcosa come il seguente:

process.on('uncaughtException', function(err){ 
    console.error('uncaughtException: ' + err.message); 
    console.error(err.stack); 
    process.exit(1);    // exit with error 
}); 
+0

Grazie, it per me va bene. – ioncreature

2

Se si cattura l'eccezione non rilevata per ECONNREFUSED make sicuro di riavviare il processo. Ho visto in testing che il socket diventa instabile se si ignora l'eccezione e si tenta semplicemente di riconnettersi.

Ecco una grande panoramica: http://shapeshed.com/uncaught-exceptions-in-node/

ho finito per usare lo strumento "per sempre" per riavviare il processo di nodo, con il seguente codice:

process.on('uncaughtException', function(err){ 
//Is this our connection refused exception? 
    if(err.message.indexOf("ECONNREFUSED") > -1) 
    { 
    //Safer to shut down instead of ignoring 
    //See: http://shapeshed.com/uncaught-exceptions-in-node/ 
    console.error("Waiting for CLI connection to come up. Restarting in 2 second..."); 
    setTimeout(shutdownProcess, 2000); 
    } 
    else 
    { 
    //This is some other exception.. 
    console.error('uncaughtException: ' + err.message); 
    console.error(err.stack); 
    shutdownProcess(); 
    } 
}); 

//Desc: Restarts the process. Since forever is managing this process it's safe to shut down 
//  it will be restarted. If we ignore exceptions it could lead to unstable behavior. 
//  Exit and let the forever utility restart everything 
function shutdownProcess() 
{ 
    process.exit(1); //exit with error 
} 
2

si dovrebbe effettivamente cercare di evitare che l'eccezione ECONNREFUSED di diventare non rilevata:

var request = require('request'); 
app.all('/proxy/*', function(req, res){ 
    req.pipe(request({ 
     url: config.backendUrl + req.params[0], 
     qs: req.query, 
     method: req.method 
    })) 
    .on('error', err => { 
     const msg = 'Error on connecting to the webservice.'; 
     console.error(msg, err); 
     res.status(500).send(msg); 
    }) 
    .pipe(res); 
}); 

Se si ottiene un'eccezione reale non rilevata, allora si dovrebbe lasciare che il dado applicazione.