@@ -36,13 +36,15 @@ function argumentsArray(args) {
36
36
function fail ( req , res , code , msg ) {
37
37
// log a failure, and finish the HTTP request with an error code
38
38
msg = msg || "" ;
39
+ res . _logMsg = msg ;
40
+
41
+ if ( res . writableEnded ) return ; // response already done
39
42
if ( res . writeHead ) res . writeHead ( code ) ;
40
43
if ( res . write ) {
41
44
if ( ! msg ) {
42
45
msg = http . STATUS_CODES [ code ] ;
43
46
}
44
47
res . write ( msg ) ;
45
- res . _logMsg = msg ;
46
48
}
47
49
if ( res . end ) res . end ( ) ;
48
50
}
@@ -410,6 +412,7 @@ class ConfigurableProxy extends EventEmitter {
410
412
_handleProxyErrorDefault ( code , kind , req , res ) {
411
413
// called when no custom error handler is registered,
412
414
// or is registered and doesn't work
415
+ if ( res . writableEnded ) return ; // response already done
413
416
if ( ! res . headersSent && res . writeHead ) res . writeHead ( code ) ;
414
417
if ( res . write ) res . write ( http . STATUS_CODES [ code ] ) ;
415
418
if ( res . end ) res . end ( ) ;
@@ -425,15 +428,20 @@ class ConfigurableProxy extends EventEmitter {
425
428
this . statsd . increment ( "requests." + code , 1 ) ;
426
429
if ( e ) {
427
430
// avoid stack traces on known not-our-problem errors:
428
- // ECONNREFUSED (backend isn't there)
429
- // ECONNRESET (backend is there, but didn't respond)
430
- if ( e . code === "ECONNRESET" || e . code === "ECONNREFUSED" ) {
431
- errMsg = e . message ;
432
- } else {
433
- // logging the error object shows a stack trace.
434
- // Anything that gets here is an unknown error,
435
- // so log more info.
436
- errMsg = e ;
431
+ // ECONNREFUSED, EHOSTUNREACH (backend isn't there)
432
+ // ECONNRESET, ETIMEDOUT (backend is there, but didn't respond)
433
+ switch ( e . code ) {
434
+ case "ECONNREFUSED" :
435
+ case "ECONNRESET" :
436
+ case "EHOSTUNREACH" :
437
+ case "ETIMEDOUT" :
438
+ errMsg = e . message ;
439
+ break ;
440
+ default :
441
+ // logging the error object shows a stack trace.
442
+ // Anything that gets here is an unknown error,
443
+ // so log more info.
444
+ errMsg = e ;
437
445
}
438
446
}
439
447
this . log . error ( "%s %s %s %s" , code , req . method , req . url , errMsg ) ;
@@ -463,13 +471,14 @@ class ConfigurableProxy extends EventEmitter {
463
471
}
464
472
465
473
var errorRequest = ( secure ? https : http ) . request ( target , function ( upstream ) {
474
+ if ( res . writableEnded ) return ; // response already done
466
475
[ "content-type" , "content-encoding" ] . map ( function ( key ) {
467
476
if ( ! upstream . headers [ key ] ) return ;
468
477
if ( res . setHeader ) res . setHeader ( key , upstream . headers [ key ] ) ;
469
478
} ) ;
470
479
if ( res . writeHead ) res . writeHead ( code ) ;
471
480
upstream . on ( "data" , ( data ) => {
472
- if ( res . write ) res . write ( data ) ;
481
+ if ( res . write && ! res . writableEnded ) res . write ( data ) ;
473
482
} ) ;
474
483
upstream . on ( "end" , ( ) => {
475
484
if ( res . end ) res . end ( ) ;
@@ -498,6 +507,7 @@ class ConfigurableProxy extends EventEmitter {
498
507
this . _handleProxyErrorDefault ( code , kind , req , res ) ;
499
508
return ;
500
509
}
510
+ if ( res . writableEnded ) return ; // response already done
501
511
if ( res . writeHead ) res . writeHead ( code , { "Content-Type" : "text/html" } ) ;
502
512
if ( res . write ) res . write ( data ) ;
503
513
if ( res . end ) res . end ( ) ;
0 commit comments