mirror of
https://github.com/yusing/godoxy.git
synced 2026-04-21 16:31:43 +02:00
v0.26.0
This commit is contained in:
@@ -1,12 +1,14 @@
|
||||
package route
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"net/http"
|
||||
"sync"
|
||||
|
||||
"github.com/rs/zerolog/log"
|
||||
"github.com/yusing/godoxy/agent/pkg/agent"
|
||||
"github.com/yusing/godoxy/agent/pkg/agentproxy"
|
||||
config "github.com/yusing/godoxy/internal/config/types"
|
||||
entrypoint "github.com/yusing/godoxy/internal/entrypoint/types"
|
||||
"github.com/yusing/godoxy/internal/health/monitor"
|
||||
"github.com/yusing/godoxy/internal/idlewatcher"
|
||||
"github.com/yusing/godoxy/internal/logging/accesslog"
|
||||
@@ -14,16 +16,14 @@ import (
|
||||
"github.com/yusing/godoxy/internal/net/gphttp/loadbalancer"
|
||||
"github.com/yusing/godoxy/internal/net/gphttp/middleware"
|
||||
nettypes "github.com/yusing/godoxy/internal/net/types"
|
||||
"github.com/yusing/godoxy/internal/route/routes"
|
||||
route "github.com/yusing/godoxy/internal/route/types"
|
||||
"github.com/yusing/godoxy/internal/types"
|
||||
gperr "github.com/yusing/goutils/errs"
|
||||
"github.com/yusing/goutils/http/reverseproxy"
|
||||
"github.com/yusing/goutils/task"
|
||||
"github.com/yusing/goutils/version"
|
||||
)
|
||||
|
||||
type ReveseProxyRoute struct {
|
||||
type ReverseProxyRoute struct {
|
||||
*Route
|
||||
|
||||
loadBalancer *loadbalancer.LoadBalancer
|
||||
@@ -31,11 +31,11 @@ type ReveseProxyRoute struct {
|
||||
rp *reverseproxy.ReverseProxy
|
||||
}
|
||||
|
||||
var _ types.ReverseProxyRoute = (*ReveseProxyRoute)(nil)
|
||||
var _ types.ReverseProxyRoute = (*ReverseProxyRoute)(nil)
|
||||
|
||||
// var globalMux = http.NewServeMux() // TODO: support regex subdomain matching.
|
||||
|
||||
func NewReverseProxyRoute(base *Route) (*ReveseProxyRoute, gperr.Error) {
|
||||
func NewReverseProxyRoute(base *Route) (*ReverseProxyRoute, error) {
|
||||
httpConfig := base.HTTPConfig
|
||||
proxyURL := base.ProxyURL
|
||||
|
||||
@@ -111,7 +111,7 @@ func NewReverseProxyRoute(base *Route) (*ReveseProxyRoute, gperr.Error) {
|
||||
}
|
||||
}
|
||||
|
||||
r := &ReveseProxyRoute{
|
||||
r := &ReverseProxyRoute{
|
||||
Route: base,
|
||||
rp: rp,
|
||||
}
|
||||
@@ -119,20 +119,21 @@ func NewReverseProxyRoute(base *Route) (*ReveseProxyRoute, gperr.Error) {
|
||||
}
|
||||
|
||||
// ReverseProxy implements routes.ReverseProxyRoute.
|
||||
func (r *ReveseProxyRoute) ReverseProxy() *reverseproxy.ReverseProxy {
|
||||
func (r *ReverseProxyRoute) ReverseProxy() *reverseproxy.ReverseProxy {
|
||||
return r.rp
|
||||
}
|
||||
|
||||
// Start implements task.TaskStarter.
|
||||
func (r *ReveseProxyRoute) Start(parent task.Parent) gperr.Error {
|
||||
func (r *ReverseProxyRoute) Start(parent task.Parent) error {
|
||||
r.task = parent.Subtask("http."+r.Name(), false)
|
||||
r.task.SetValue(monitor.DisplayNameKey{}, r.DisplayName())
|
||||
|
||||
switch {
|
||||
case r.UseIdleWatcher():
|
||||
waker, err := idlewatcher.NewWatcher(parent, r, r.IdlewatcherConfig())
|
||||
if err != nil {
|
||||
r.task.Finish(err)
|
||||
return gperr.Wrap(err)
|
||||
return err
|
||||
}
|
||||
r.handler = waker
|
||||
r.HealthMon = waker
|
||||
@@ -149,7 +150,7 @@ func (r *ReveseProxyRoute) Start(parent task.Parent) gperr.Error {
|
||||
r.rp.AccessLogger, err = accesslog.NewAccessLogger(r.task, r.AccessLog)
|
||||
if err != nil {
|
||||
r.task.Finish(err)
|
||||
return gperr.Wrap(err)
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
@@ -159,44 +160,50 @@ func (r *ReveseProxyRoute) Start(parent task.Parent) gperr.Error {
|
||||
|
||||
if r.HealthMon != nil {
|
||||
if err := r.HealthMon.Start(r.task); err != nil {
|
||||
return err
|
||||
// TODO: add to event history
|
||||
log.Warn().Err(err).Msg("health monitor error")
|
||||
r.HealthMon = nil
|
||||
}
|
||||
}
|
||||
|
||||
ep := entrypoint.FromCtx(parent.Context())
|
||||
if ep == nil {
|
||||
err := errors.New("entrypoint not initialized")
|
||||
r.task.Finish(err)
|
||||
return err
|
||||
}
|
||||
|
||||
if r.UseLoadBalance() {
|
||||
r.addToLoadBalancer(parent)
|
||||
} else {
|
||||
routes.HTTP.Add(r)
|
||||
if state := config.WorkingState.Load(); state != nil {
|
||||
state.ShortLinkMatcher().AddRoute(r.Alias)
|
||||
if err := r.addToLoadBalancer(parent, ep); err != nil {
|
||||
r.task.Finish(err)
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
if err := ep.StartAddRoute(r); err != nil {
|
||||
r.task.Finish(err)
|
||||
return err
|
||||
}
|
||||
r.task.OnCancel("remove_route", func() {
|
||||
routes.HTTP.Del(r)
|
||||
if state := config.WorkingState.Load(); state != nil {
|
||||
state.ShortLinkMatcher().DelRoute(r.Alias)
|
||||
}
|
||||
})
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (r *ReveseProxyRoute) ServeHTTP(w http.ResponseWriter, req *http.Request) {
|
||||
func (r *ReverseProxyRoute) ServeHTTP(w http.ResponseWriter, req *http.Request) {
|
||||
// req.Header.Set("Accept-Encoding", "identity")
|
||||
r.handler.ServeHTTP(w, req)
|
||||
}
|
||||
|
||||
var lbLock sync.Mutex
|
||||
|
||||
func (r *ReveseProxyRoute) addToLoadBalancer(parent task.Parent) {
|
||||
func (r *ReverseProxyRoute) addToLoadBalancer(parent task.Parent, ep entrypoint.Entrypoint) error {
|
||||
var lb *loadbalancer.LoadBalancer
|
||||
cfg := r.LoadBalance
|
||||
lbLock.Lock()
|
||||
defer lbLock.Unlock()
|
||||
|
||||
l, ok := routes.HTTP.Get(cfg.Link)
|
||||
var linked *ReveseProxyRoute
|
||||
l, ok := ep.HTTPRoutes().Get(cfg.Link)
|
||||
var linked *ReverseProxyRoute
|
||||
if ok {
|
||||
lbLock.Unlock()
|
||||
linked = l.(*ReveseProxyRoute)
|
||||
linked = l.(*ReverseProxyRoute) // it must be a reverse proxy route
|
||||
lb = linked.loadBalancer
|
||||
lb.UpdateConfigIfNeeded(cfg)
|
||||
if linked.Homepage.Name == "" {
|
||||
@@ -205,26 +212,24 @@ func (r *ReveseProxyRoute) addToLoadBalancer(parent task.Parent) {
|
||||
} else {
|
||||
lb = loadbalancer.New(cfg)
|
||||
_ = lb.Start(parent) // always return nil
|
||||
linked = &ReveseProxyRoute{
|
||||
linked = &ReverseProxyRoute{
|
||||
Route: &Route{
|
||||
Alias: cfg.Link,
|
||||
Homepage: r.Homepage,
|
||||
Bind: r.Bind,
|
||||
Metadata: Metadata{
|
||||
LisURL: r.ListenURL(),
|
||||
task: lb.Task(),
|
||||
},
|
||||
},
|
||||
loadBalancer: lb,
|
||||
handler: lb,
|
||||
}
|
||||
linked.SetHealthMonitor(lb)
|
||||
routes.HTTP.AddKey(cfg.Link, linked)
|
||||
if state := config.WorkingState.Load(); state != nil {
|
||||
state.ShortLinkMatcher().AddRoute(cfg.Link)
|
||||
if err := ep.StartAddRoute(linked); err != nil {
|
||||
lb.Finish(err)
|
||||
return err
|
||||
}
|
||||
r.task.OnFinished("remove_loadbalancer_route", func() {
|
||||
routes.HTTP.DelKey(cfg.Link)
|
||||
if state := config.WorkingState.Load(); state != nil {
|
||||
state.ShortLinkMatcher().DelRoute(cfg.Link)
|
||||
}
|
||||
})
|
||||
lbLock.Unlock()
|
||||
}
|
||||
r.loadBalancer = lb
|
||||
|
||||
@@ -233,4 +238,5 @@ func (r *ReveseProxyRoute) addToLoadBalancer(parent task.Parent) {
|
||||
r.task.OnCancel("lb_remove_server", func() {
|
||||
lb.RemoveServer(server)
|
||||
})
|
||||
return nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user