diff --git a/lib/handlers/cors-proxy.js b/lib/handlers/cors-proxy.js index 488b4a392..ed1719241 100644 --- a/lib/handlers/cors-proxy.js +++ b/lib/handlers/cors-proxy.js @@ -22,11 +22,35 @@ const PROXY_SETTINGS = { router: req => req.destination.target, pathRewrite: (path, req) => req.destination.path } -const LOCAL_IP_RANGES = [ - '10.0.0.0/8', - '127.0.0.0/8', - '172.16.0.0/12', - '192.168.0.0/16' +// https://en.wikipedia.org/wiki/Reserved_IP_addresses +const RESERVED_IP_RANGES = [ + '127.0.0.0/8', // loopback + '::1/128', // loopback + '0.0.0.0/8', // current network (only valid as source address) + '169.254.0.0/16', // link-local + '10.0.0.0/8', // private network + '100.64.0.0/10', // Shared Address Space + '172.16.0.0/12', // private network + '192.0.0.0/24', // IETF Protocol Assignments + '192.0.2.0/24', // TEST-NET-1, documentation and examples + '192.88.99.0/24', // IPv6 to IPv4 relay (includes 2002::/16) + '192.168.0.0/16', // private network + '198.18.0.0/15', // network benchmark tests + '198.51.100.0/24', // TEST-NET-2, documentation and examples + '203.0.113.0/24', // TEST-NET-3, documentation and examples + '224.0.0.0/4', // IP multicast (former Class D network) + '240.0.0.0/4', // reserved (former Class E network) + '255.255.255.255', // broadcast + '64:ff9b::/96', // IPv4/IPv6 translation (RFC 6052) + '100::/64', // discard prefix (RFC 6666) + '2001::/32', // Teredo tunneling + '2001:10::/28', // deprecated (previously ORCHID + '2001:20::/28', // ORCHIDv2 + '2001:db8::/32', // documentation and example source code + '2002::/16', // 6to4 + 'fc00::/7', // unique local address + 'fe80::/10', // link-local address + 'ff00::/8' // multicast ] // Adds a CORS proxy handler to the application on the given path @@ -58,7 +82,7 @@ function extractProxyConfig (req, res, next) { // Verifies and adds the proxy configuration to the request function addProxyConfig (error, hostAddress) { // Ensure the host is not a local IP - if (error || LOCAL_IP_RANGES.some(r => ipRange(hostAddress, r))) { + if (error || RESERVED_IP_RANGES.some(r => ipRange(hostAddress, r))) { return res.status(400).send(`Cannot proxy ${uri}`) } req.destination = { path, target: `${protocol}//${host}` } diff --git a/test/integration/cors-proxy-test.js b/test/integration/cors-proxy-test.js index 7191d7af6..9bcc9ee48 100644 --- a/test/integration/cors-proxy-test.js +++ b/test/integration/cors-proxy-test.js @@ -44,7 +44,13 @@ describe('CORS Proxy', () => { .end(done) }) - const LOCAL_IPS = ['127.0.0.0', '10.0.0.0', '172.16.0.0', '192.168.0.0'] + const LOCAL_IPS = [ + '127.0.0.0', + '10.0.0.0', + '172.16.0.0', + '192.168.0.0', + '[::1]' + ] LOCAL_IPS.forEach(ip => { it(`should return 400 for a ${ip} address`, (done) => { nock(`https://${ip}`).get('/').reply(200)