Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use an EventEmitter to replay failed proxy connect HTTP requests #77

Merged
merged 2 commits into from Oct 7, 2019
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
18 changes: 15 additions & 3 deletions index.js
Expand Up @@ -5,6 +5,7 @@
var net = require('net');
var tls = require('tls');
var url = require('url');
var events = require('events');
var Agent = require('agent-base');
var inherits = require('util').inherits;
var debug = require('debug')('https-proxy-agent');
Expand Down Expand Up @@ -154,20 +155,32 @@ HttpsProxyAgent.prototype.callback = function connect(req, opts, fn) {
fn(null, sock);
} else {
// some other status code that's not 200... need to re-play the HTTP header
// "data" events onto the socket once the HTTP machinery is attached so that
// the user can parse and handle the error status code
// "data" events onto the socket once the HTTP machinery is attached so
// that the node core `http` can parse and handle the error status code
cleanup();

// the original socket is closed, and a "fake socket" EventEmitter is
// returned instead, so that the proxy doesn't get the HTTP request
// written to it (which may contain `Authorization` headers or other
// sensitive data).
//
// See: https://hackerone.com/reports/541502
socket.destroy();
socket = new events.EventEmitter();

// save a reference to the concat'd Buffer for the `onsocket` callback
buffers = buffered;

// need to wait for the "socket" event to re-play the "data" events
req.once('socket', onsocket);

fn(null, socket);
}
}

function onsocket(socket) {
debug('replaying proxy buffer for failed request');

// replay the "buffers" Buffer onto the `socket`, since at this point
// the HTTP module machinery has been hooked up for the user
if (socket.listenerCount('data') > 0) {
Expand All @@ -177,7 +190,6 @@ HttpsProxyAgent.prototype.callback = function connect(req, opts, fn) {
throw new Error('should not happen...');
}

socket.resume();
// nullify the cached Buffer instance
buffers = null;
}
Expand Down