A simple reverse proxy example in Go
This example shows you a Go HTTP Server that forwards requests to an upstream Server using a HTTP client. Note that this example does notĀ stream the upstream server’s responses but downloads them to RAM and then serves them to the client (hence you might need to improve upon this example if you intend to serve large files).
Also, note that this example does not implement proper error handling for the upstream request since it’s only intended to serve as a basic starting point forĀ you to develop your own reverse proxy implementation.
package main
import (
"fmt"
"io/ioutil"
"log"
"net/http"
)
func main() {
client := &http.Client{}
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
// Perform request
url := "https://techoverflow.net" + r.URL.Path
req, _ := http.NewRequest(r.Method, url, r.Body)
req.Header = r.Header
resp, _ := client.Do(req)
// Cleanup when this function ends
defer resp.Body.Close()
// Copy headers from request to response
header := w.Header()
for name, headers := range resp.Header {
// Iterate all headers with one name (e.g. Content-Type)
for _, hdr := range headers {
header.Add(name, hdr)
}
}
// Read all the response data into a []byte
body, _ := ioutil.ReadAll(resp.Body)
// Write header & body
w.WriteHeader(resp.StatusCode)
w.Write(body)
})
// log.Fatal shows you if there is an error like the
// port already being used
fmt.Println("Listening on port 8080")
log.Fatal(http.ListenAndServe(":8080", nil))
}
Further reading:
- Go net/http package
- Iterating HTTP client response headers in Go (which we use as a basis to implement our header copying mechanism)