UNPKG

@rill/forwarded-from

Version:

Safe X-Forwarded-For header handling for Rill.

67 lines (57 loc) 1.69 kB
'use strict' var isLocal = require('is-local-ip') /** * Creates a middleware that will update `ctx.req.ip` with valid `X-Forwarded-For` * headers from trusted ips. * * @param {Object} options * @param {String|Array<String>} [options.from] - A list of allowed ip addresses. * @param {Boolean} [options.local=true] - Allow local ip addresses. * @return {Function} */ module.exports = function forwardedFrom (options) { options = options || {} var ips = options.from && [].concat(options.from) var local = 'local' in options ? options.local : true return function forwardedFromMiddleware (ctx, next) { var req = ctx.req var isAccepted = (ips && ips.indexOf(req.ip)) || (local && isLocal(req.ip)) if (isAccepted) { // Mark request as forwarded. req.forwarded = true // Check for forwarded ip address. var forwardIP = req.get('X-Forwarded-For') if (forwardIP) { req.ip = forwardIP } // Check for forwarded host. var forwardHost = req.get('X-Forwarded-Host') if (forwardHost) { // Parse the host into its parts. var parts = parseHost(forwardHost, req.port) req.host = parts.host req.hostname = parts.hostname req.port = parts.port } } return next() } } /** * Parses a host into host, hostname and port. * * @param {String} host * @param {Number} port */ function parseHost (host, port) { var result = { host: host } var index = host.indexOf(':') if (index) { result.hostname = host.slice(0, index) result.port = host.slice(index + 1) } else { result.hostname = host result.port = port } return result }