Skip to content

Instantly share code, notes, and snippets.

@MarkTiedemann
Last active March 13, 2017 17:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save MarkTiedemann/664910a2c5f635ba0bb3a749d117168c to your computer and use it in GitHub Desktop.
Save MarkTiedemann/664910a2c5f635ba0bb3a749d117168c to your computer and use it in GitHub Desktop.
Bare Bones Node.js HTTP Proxy
const http = require('http')
const url = require('url')
const apiPort = 3000
const proxyPort = 3001
const apiResStatus = 200
const apiResBody = `"Hi, I'm the API!"`
const clientReqMethod = 'GET'
const clientReqPath = '/'
// Create API server
const api = http.createServer((apiReq, apiRes) => {
apiReq.on('error', err => console.error('API Error:', err))
const apiReqUrl = url.parse(apiReq.url)
console.log('API Req:', apiPort, apiReq.method, apiReqUrl.path)
apiRes.writeHead(apiResStatus)
apiRes.end(apiResBody)
console.log('API Res:', apiResStatus, apiResBody)
})
api.listen(apiPort, apiErr => {
if (apiErr) throw apiErr
console.log(`API listening on 'localhost:${apiPort}'`)
// Create proxy server
const proxy = http.createServer((proxyReq, proxyRes) => {
proxyReq.on('error', err => console.error('Proxy Error:', err))
const proxyReqUrl = url.parse(proxyReq.url)
console.log('Proxy Req:', proxyPort, '->', apiPort, proxyReq.method, proxyReqUrl.path)
const tunnelReq = http.request({
method: proxyReq.method,
path: proxyReqUrl.path,
port: apiPort
}, tunnelRes => {
console.log('Proxy Res:', tunnelRes.statusCode, '(pipe)')
proxyRes.writeHead(tunnelRes.statusCode)
tunnelRes.pipe(proxyRes)
})
tunnelReq.on('error', err => console.error('Tunnel Error:', err))
tunnelReq.end()
})
proxy.listen(proxyPort, proxyErr => {
if (proxyErr) throw proxyErr
console.log(`Proxy listening on 'localhost:${proxyPort}'`)
// Make client request
console.log('Client Req:', proxyPort, clientReqMethod, clientReqPath)
const clientReq = http.request({
port: proxyPort,
path: clientReqPath,
method: clientReqMethod
}, clientRes => {
const clientResBuffer = []
clientRes.on('data', chunk => clientResBuffer.push(chunk))
clientRes.on('end', () => {
const clientResBody = Buffer.concat(clientResBuffer).toString()
console.log('Client Res:', clientRes.statusCode, clientResBody)
})
})
clientReq.on('error', err => console.error('Client Error:', err))
clientReq.end()
})
proxy.unref()
})
api.unref()
@MarkTiedemann
Copy link
Author

$ node .
API listening on 'localhost:3000'
Proxy listening on 'localhost:3001'
Client Req: 3001 GET /
Proxy Req: 3001 -> 3000 GET /
API Req: 3000 GET /
API Res: 200 "Hi, I'm the API!"
Proxy Res: 200 (pipe)
Client Res: 200 "Hi, I'm the API!"

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment