1
0

reverseproxy.go 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233
  1. package main
  2. import (
  3. "encoding/json"
  4. "log"
  5. "net/http"
  6. "path/filepath"
  7. "strconv"
  8. "imuslab.com/arozos/ReverseProxy/mod/dynamicproxy"
  9. )
  10. var (
  11. dynamicProxyRouter *dynamicproxy.Router
  12. )
  13. //Add user customizable reverse proxy
  14. func ReverseProxtInit() {
  15. inboundPort := 80
  16. if sysdb.KeyExists("settings", "inbound") {
  17. sysdb.Read("settings", "inbound", &inboundPort)
  18. log.Println("Serving inbound port ", inboundPort)
  19. } else {
  20. log.Println("Inbound port not set. Using default (80)")
  21. }
  22. dprouter, err := dynamicproxy.NewDynamicProxy(inboundPort)
  23. if err != nil {
  24. log.Println(err.Error())
  25. return
  26. }
  27. dynamicProxyRouter = dprouter
  28. http.HandleFunc("/enable", ReverseProxyHandleOnOff)
  29. http.HandleFunc("/add", ReverseProxyHandleAddEndpoint)
  30. http.HandleFunc("/status", ReverseProxyStatus)
  31. http.HandleFunc("/list", ReverseProxyList)
  32. http.HandleFunc("/del", DeleteProxyEndpoint)
  33. http.HandleFunc("/setIncoming", HandleIncomingPortSet)
  34. //Load all conf from files
  35. confs, _ := filepath.Glob("./conf/*.config")
  36. for _, conf := range confs {
  37. record, err := LoadReverseProxyConfig(conf)
  38. if err != nil {
  39. log.Println("Failed to load "+filepath.Base(conf), err.Error())
  40. return
  41. }
  42. if record.ProxyType == "root" {
  43. dynamicProxyRouter.SetRootProxy(record.ProxyTarget, record.UseTLS)
  44. } else if record.ProxyType == "subd" {
  45. dynamicProxyRouter.AddSubdomainRoutingService(record.Rootname, record.ProxyTarget, record.UseTLS)
  46. } else if record.ProxyType == "vdir" {
  47. dynamicProxyRouter.AddVirtualDirectoryProxyService(record.Rootname, record.ProxyTarget, record.UseTLS)
  48. } else {
  49. log.Println("Unsupported endpoint type: " + record.ProxyType + ". Skipping " + filepath.Base(conf))
  50. }
  51. }
  52. /*
  53. dynamicProxyRouter.SetRootProxy("192.168.0.107:8080", false)
  54. dynamicProxyRouter.AddSubdomainRoutingService("aroz.localhost", "192.168.0.107:8080/private/AOB/", false)
  55. dynamicProxyRouter.AddSubdomainRoutingService("loopback.localhost", "localhost:8080", false)
  56. dynamicProxyRouter.AddSubdomainRoutingService("git.localhost", "mc.alanyeung.co:3000", false)
  57. dynamicProxyRouter.AddVirtualDirectoryProxyService("/git/server/", "mc.alanyeung.co:3000", false)
  58. */
  59. //Start Service
  60. dynamicProxyRouter.StartProxyService()
  61. log.Println("Dynamic Reverse Proxy service started")
  62. }
  63. func ReverseProxyHandleOnOff(w http.ResponseWriter, r *http.Request) {
  64. enable, _ := mv(r, "enable", true) //Support root, vdir and subd
  65. if enable == "true" {
  66. err := dynamicProxyRouter.StartProxyService()
  67. if err != nil {
  68. sendErrorResponse(w, err.Error())
  69. return
  70. }
  71. } else {
  72. err := dynamicProxyRouter.StopProxyService()
  73. if err != nil {
  74. sendErrorResponse(w, err.Error())
  75. return
  76. }
  77. }
  78. sendOK(w)
  79. }
  80. func ReverseProxyHandleAddEndpoint(w http.ResponseWriter, r *http.Request) {
  81. eptype, err := mv(r, "type", true) //Support root, vdir and subd
  82. if err != nil {
  83. sendErrorResponse(w, "type not defined")
  84. return
  85. }
  86. endpoint, err := mv(r, "ep", true)
  87. if err != nil {
  88. sendErrorResponse(w, "endpoint not defined")
  89. return
  90. }
  91. tls, _ := mv(r, "tls", true)
  92. if tls == "" {
  93. tls = "false"
  94. }
  95. useTLS := (tls == "true")
  96. rootname := ""
  97. if eptype == "vdir" {
  98. vdir, err := mv(r, "rootname", true)
  99. if err != nil {
  100. sendErrorResponse(w, "vdir not defined")
  101. return
  102. }
  103. rootname = vdir
  104. dynamicProxyRouter.AddVirtualDirectoryProxyService(vdir, endpoint, useTLS)
  105. } else if eptype == "subd" {
  106. subdomain, err := mv(r, "rootname", true)
  107. if err != nil {
  108. sendErrorResponse(w, "subdomain not defined")
  109. return
  110. }
  111. rootname = subdomain
  112. dynamicProxyRouter.AddSubdomainRoutingService(subdomain, endpoint, useTLS)
  113. } else if eptype == "root" {
  114. rootname = "root"
  115. dynamicProxyRouter.SetRootProxy(endpoint, useTLS)
  116. } else {
  117. //Invalid eptype
  118. sendErrorResponse(w, "Invalid endpoint type")
  119. return
  120. }
  121. //Save it
  122. SaveReverseProxyConfig(eptype, rootname, endpoint, useTLS)
  123. sendOK(w)
  124. }
  125. func DeleteProxyEndpoint(w http.ResponseWriter, r *http.Request) {
  126. ep, err := mv(r, "ep", true)
  127. if err != nil {
  128. sendErrorResponse(w, "Invalid ep given")
  129. }
  130. ptype, err := mv(r, "ptype", true)
  131. if err != nil {
  132. sendErrorResponse(w, "Invalid ptype given")
  133. }
  134. err = dynamicProxyRouter.RemoveProxy(ptype, ep)
  135. if err != nil {
  136. sendErrorResponse(w, err.Error())
  137. }
  138. RemoveReverseProxyConfig(ep)
  139. sendOK(w)
  140. }
  141. func ReverseProxyStatus(w http.ResponseWriter, r *http.Request) {
  142. js, _ := json.Marshal(dynamicProxyRouter)
  143. sendJSONResponse(w, string(js))
  144. }
  145. func ReverseProxyList(w http.ResponseWriter, r *http.Request) {
  146. eptype, err := mv(r, "type", true) //Support root, vdir and subd
  147. if err != nil {
  148. sendErrorResponse(w, "type not defined")
  149. return
  150. }
  151. if eptype == "vdir" {
  152. results := []*dynamicproxy.ProxyEndpoint{}
  153. dynamicProxyRouter.ProxyEndpoints.Range(func(key, value interface{}) bool {
  154. results = append(results, value.(*dynamicproxy.ProxyEndpoint))
  155. return true
  156. })
  157. js, _ := json.Marshal(results)
  158. sendJSONResponse(w, string(js))
  159. } else if eptype == "subd" {
  160. results := []*dynamicproxy.SubdomainEndpoint{}
  161. dynamicProxyRouter.SubdomainEndpoint.Range(func(key, value interface{}) bool {
  162. results = append(results, value.(*dynamicproxy.SubdomainEndpoint))
  163. return true
  164. })
  165. js, _ := json.Marshal(results)
  166. sendJSONResponse(w, string(js))
  167. } else if eptype == "root" {
  168. js, _ := json.Marshal(dynamicProxyRouter.Root)
  169. sendJSONResponse(w, string(js))
  170. } else {
  171. sendErrorResponse(w, "Invalid type given")
  172. }
  173. }
  174. //Handle incoming port set. Change the current proxy incoming port
  175. func HandleIncomingPortSet(w http.ResponseWriter, r *http.Request) {
  176. newIncomingPort, err := mv(r, "incoming", true)
  177. if err != nil {
  178. sendErrorResponse(w, "invalid incoming port given")
  179. return
  180. }
  181. newIncomingPortInt, err := strconv.Atoi(newIncomingPort)
  182. if err != nil {
  183. sendErrorResponse(w, "invalid incoming port given")
  184. return
  185. }
  186. //Stop and change the setting of the reverse proxy service
  187. if dynamicProxyRouter.Running {
  188. dynamicProxyRouter.StopProxyService()
  189. dynamicProxyRouter.ListenPort = newIncomingPortInt
  190. dynamicProxyRouter.StartProxyService()
  191. } else {
  192. //Only change setting but not starting the proxy service
  193. dynamicProxyRouter.ListenPort = newIncomingPortInt
  194. }
  195. sysdb.Write("settings", "inbound", newIncomingPortInt)
  196. sendOK((w))
  197. }