Go语言HTTP代理,将HTTP连接转发给另一个网站
网站没有使用NGINX之类的反射代理,例如只是纯粹使用golang搭建的http服务,在多个网站放在同一个服务器的情况下,管理起来就只能手工写代码了。
现有站点A和站点B,都是放在同一个IP下的主机里面,假如站点A监听80商品,站点B监听8080端口,则需要做特殊处理。因为这两个站点的域名不一样。
站点A代码:
// checkAndRedirect 检查是否要跳转以及一些非法操作的判断
func checkAndRedirect(w http.ResponseWriter, r *http.Request) {
// 如果是通过站点B的域名访问了站点A 通过下面代码转发即可
if strings.Replace(host, "www.", "", 1) == "站点B域名" {
u, _ := url.Parse("http://127.0.0.1:8080")
httputil.NewSingleHostReverseProxy(u).ServeHTTP(w, r)
}
}
有个非常坑的地方是,如果站点A使用的静态资源是通过下面这样的方式去指定的话,一定要特殊处理,例如站点A的CSS目录映射通过这种方式写的:
// 站点A首页
http.HandleFunc("/", handlerA)
// 站点A的CSS连接映射
http.Handle("/style/", http.StripPrefix("/style/", http.FileServer(http.Dir("./html/style"))))
func handlerA(w http.ResponseWriter, r *http.Request) {}
这样写会导致站点B也使用这一个目录下的CSS,也就是说,这里的请求也是需要单独做转发的。可以有多种方式做处理,例如:
一、将上面的代码全部放在 handlerA 函数内处理,通过检测 r.URL.Path 做跳转。
二、单独处理静态文件。
type Static struct{}
func (s *Static) ServeHTTP(w http.ResponseWriter, r *http.Request) {
path := strings.Trim(strings.ToLower(r.URL.Path), "/")
arr := strings.Split(path, ".")
if len(arr) != 2 {
http.NotFound(w, r)
return
}
if arr[1] == "css" {
path = "./html/style/" + path
// 载入文件
buf, err := os.OpenFile(path)
if err != nil {
http.NotFound(w, r)
return
}
w.Header().Set("Accept-Ranges", "bytes")
w.Header().Set("Content-Type", "text/css; charset=utf-8")
w.Write(buf)
return
}
if arr[1] == "js" {
path = "./html/js/" + path
// 载入文件
buf, err := os.OpenFile(path)
if err != nil {
index.HTTP404(w, r)
return
}
fname := strings.Split(path, ".")
w.Header().Set("Accept-Ranges", "bytes")
if fix := fname[len(fname)-1]; fix == "js" {
w.Header().Set("Content-Type", "application/javascript; charset=utf-8")
} else if fix == "css" {
w.Header().Set("Content-Type", "text/css; charset=utf-8")
}
w.Write(buf)
}
}
以上就是使用Go语言做HTTP转发的代码。
声明: 因编程语言版本更新较快,当前文章所涉及的语法或某些特性相关的信息并不一定完全适用于您当前所使用的版本,请仔细甄别。文章内容仅作为学习和参考,若有错误,欢迎指正。
开发者
专题·造轮子
Golang·热门
相关文章