I have a HTTP web server and I'm trying to set it up behind a HTTPS proxy server.
I've tried the example that's in the repository: https://github.com/http-party/node-http-proxy/blob/master/examples/http/proxy-https-to-http.js but I'm always getting ERR_EMPTY_RESPONSE in browser.
Example code
var https = require('https'),
http = require('http'),
util = require('util'),
path = require('path'),
fs = require('fs'),
colors = require('colors'),
httpProxy = require('../../lib/http-proxy'),
fixturesDir = path.join(__dirname, '..', '..', 'test', 'fixtures');
//
// Create the target HTTP server
//
http.createServer(function (req, res) {
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.write('hello http over https\n');
res.end();
}).listen(9009);
//
// Create the HTTPS proxy server listening on port 8000
//
httpProxy.createServer({
target: {
host: 'localhost',
port: 9009
},
ssl: {
key: fs.readFileSync(path.join(fixturesDir, 'agent2-key.pem'), 'utf8'),
cert: fs.readFileSync(path.join(fixturesDir, 'agent2-cert.pem'), 'utf8')
}
}).listen(8009);
console.log('https proxy server'.blue + ' started '.green.bold + 'on port '.blue + '8009'.yellow);
console.log('http server '.blue + 'started '.green.bold + 'on port '.blue + '9009 '.yellow);
Error
Screenshot
Browser is pointed to use 127.0.0.1:8009 proxy.
Does anybody know what's wrong ?
Any suggestion is appreciated.
Related
I'm trying to setup an HTTPS server that proxies requests to changing targets that also enforce HTTPS. this is because I want to setup an intercepting https proxy, terminate ssl, modify data and send encrypted modifications to target server (or backwards through the response).
Example:
Browser --> myHTTPSProxy(modify request) --> https://targethost.com --> myHTTPSProxy(modify response) --> Browser
This is sample implementation for the task from the node-http-proxy library:
const https = require('https'),
fs = require('fs'),
colors = require('colors'),
httpProxy = require('http-proxy'),
httpsOpts = {
key: fs.readFileSync('agent2-key.pem', 'utf8'),
cert: fs.readFileSync('agent2-cert.pem', 'utf8')
};
// Create DUMMY HTTPS SRV
https.createServer(httpsOpts, function (req, res) {
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.write('hello https\n');
res.end();
}).listen(3000);
// PROXY
httpProxy.createServer({
ssl: httpsOpts,
target: 'https://localhost:3000',
secure: false
}).listen(8080);
console.log('https proxy server'.blue + ' started '.green.bold + 'on port '.blue + '8080'.yellow);
console.log('https server '.blue + 'started '.green.bold + 'on port '.blue + '3000 '.yellow);
Certificates are also taken from the library, and I tried using valid ones as well that works on a straight https server but no as a proxy.
as a proxy - I get Secure Connection Failed.
TL;DR Question
Does anyone know how to implement a HTTPS proxy server using nodejs?
Similar unresolved posts:
Https proxy server(secure proxy server) in Nodejs with http-proxy is not working
https://github.com/http-party/node-http-proxy/issues/1456
https://github.com/http-party/node-http-proxy/issues/1506
I have a requirement to set up an https proxy server(Secure Web Proxy-http://dev.chromium.org/developers/design-documents/secure-web-proxy) to test one of my application with the proxy environment.
Steps followed:
1.Created an https proxy server with the help of http-proxy. code,
var https = require('https'),
http = require('http'),
util = require('util'),
fs = require('fs'),
path = require('path'),
colors = require('colors'),
httpProxy = require('http-proxy'),
// fixturesDir = path.join(__dirname, '..', '..', 'test', 'fixtures'),
httpsOpts = {
key: fs.readFileSync('server.key', 'utf8'),
cert: fs.readFileSync('server.crt', 'utf8')
};
//
// Create the target HTTPS server
//
https.createServer(httpsOpts, function (req, res) {
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.write('hello https\n');
res.end();
}).listen(9010);
//
// Create the proxy server listening on port 8010
//
httpProxy.createServer({
ssl: httpsOpts,
target: 'https://localhost:9010',
secure: false
}).listen(8010);
console.log('https proxy server'.blue + ' started '.green.bold + 'on port '.blue + '8010'.yellow);
console.log('https server '.blue + 'started '.green.bold + 'on port '.blue + '9010 '.yellow);
Created a PAC file with https proxy server details
function FindProxyForURL(url, host) {
return "HTTPS 127.0.0.1:8010";
}
And point the pac file in my application to test application with proxy environment, sample code pasted here.
var url = require('url');
var https = require('https');
var PacProxyAgent = require('pac-proxy-agent');
// URI to a PAC proxy file to use (the "pac+" prefix is stripped)
var proxy = 'pac+http://localhost:123/hosted/pac.pac';
//console.log('using PAC proxy proxy file at %j', proxy);
// HTTP endpoint for the proxy to connect to
var endpoint = 'https://nodejs.org/api/';
//console.log('attempting to GET %j', endpoint);
var opts = url.parse(endpoint);
// create an instance of the `PacProxyAgent` class with the PAC file location
var agent = new PacProxyAgent(proxy,opts);
opts.agent = agent;
https.get(opts, function (res) {
console.log('"response" event!', res.headers);
res.pipe(process.stdout);
});
But it's not working, it throws the error
Chrome behavior:
I configured the PAC file in windows proxy settings
After that I am not getting any response from any sites
ex: when I enter https://gmail.com/ it ends up with
any suggestions?
I'm using http-proxy module and I'm trying to send the request to port 1234 and gets its reply back.
But in the apache logs I can see that request is only to /. The documentation says to use toProxy: true in order to pass the URL but it isn't working.
https://github.com/http-party/node-http-proxy
toProxy: true/false, passes the absolute URL as the path (useful for proxying to proxies)
Here is the code:
var http = require('http');
var httpProxy = require('http-proxy');
var proxy = httpProxy.createProxyServer();
var fs = require('fs');
http.createServer(function(req, res) {
return proxy.web(req, res, { target: {host: 'localhost', port: 1234},
ssl: {
key: fs.readFileSync('/root/test.pem', 'utf8'),
cert: fs.readFileSync('/root/test_cert.pem', 'utf8')
},
toProxy: true
});
}).listen(3000);
I'm using curl to test and checking the apache logs which is listening on port 1234.
curl -v http://localhost:3000/getsomething.html
Figured it out. I had to include protocol.
return proxy.web(req, res, { target: { protocol: 'https:', host: 'localhost', port: 1234},
I do have the following configuration for my hapi server
const server = new Hapi.Server();
const tls = {
cert: fs.readFileSync(path.join(__dirname, '../certificates/cert.crt')),
key: fs.readFileSync(path.join(__dirname, '../certificates/cert.key')),
};
server.connection({
port: process.env.PORT_HTTP || 80,
host: process.env.HOST || 'localhost',
});
server.connection({
port: process.env.PORT_HTTPS || 443,
host: process.env.HOST || 'localhost',
tls,
});
The server is working ok on both, http and https, but I would like to redirect all the traffic from the http to https.
How should I proceed, tried already to register the hapi-require-https npm module but the traffic still remain the same, nothing happens.
Create an extra server for http requests and bind them to redirect function.
var Hapi = require('hapi');
var http = new Hapi.Server(80);
var server = new Hapi.Server(443, { tls: {} });
var redirect = function () {
this.reply.redirect('https://your.site/' + this.params.path);
});
http.route({ method: '*', path: '/{path*}', handler: redirect });
Update(other option)
server.route({
method: 'GET',
path: '/',
handler: function (request, reply) {
if(request.headers.referer.split(':')[0] == "http"){
this.reply.redirect('https://your.site' + this.params.path);
}
}
});
How about this? Binding them both
var http = new Hapi.Server(80); // our extra server
http.route({
method: '*',
path: '/{path*}',
handler:
function (request, reply) {
// if(request.headers.referer.split(':')[0] == "http"){
this.reply.redirect('https://your.site' + this.params.path);
// }
}
});
Create two server instances to handle http & https traffic seperately.
var Hapi = require('hapi');
var server = new Hapi.Server(80);
var httpsServer = new Hapi.Server(443, { tls: { // your certificates here} });
Now register the hapi-gate plugin to the base server so that it redirects the traffic to https.
server.register({
register: require('hapi-gate'),
options: {https: true} // will force https on all requests
});
You can also use the hapi-require-https plugin instead.
I have a Node.js Express 3.0 application which listens on port 3000 locally and 80 online, that's fine. What I need to do now however is introduce an SSL certificate.
I've looked at many sources online however they're all dated, or only work on port 443 or nothing. What I need to do however is listen on both 443 and 80 and re-direct any requests to 80 back to 443.
Are they any up to date examples of this?
I would do this with 2 distinct processes: an insecure proxy server and a secure server.
The insecure proxy listens on port 80 and responds to all requests with a 302 redirect to the secure server
Insecure Proxy
var http = require('http')
var port = 80
var server = http.createServer(function (req, res) {
// change this to your secure sever url
var redirectURL = 'https://www.google.com'
res.writeHead(302, {
Location: redirectURL
});
res.end();
}).listen(port, function () {
console.log('insecure proxy listening on port: ' + port)
})
Secure Server
var https = require('https')
var express = require('express')
var fs = require('fs')
var keyFilePath = '/path/to/key.pem'
var certFilePath = '/path/to/cert.pem'
var app = express()
// put your express app config here
// app.use(...) etc.
var port = 443 // standard https port
var options = {
key: fs.readFileSync(keyFilePath, 'utf8'),
cert: fs.readFileSync(certFilePath, 'utf8')
}
var server = https.createServer(options, app)
server.listen(port, function () {
console.log('secure server listening on port: ' + port)
})
Note that you could run both of these servers within a single process but it is more maintainable to separate the concerns into distinct processes.