添加 空闲链接超时自动断开

This commit is contained in:
bjdgyc 2023-12-29 15:51:49 +08:00
parent 42142d95b7
commit ef1e20a558
13 changed files with 42 additions and 15 deletions

View File

@ -25,6 +25,7 @@ func StartAdmin() {
r.Use(func(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {
utils.SetSecureHeader(w)
w.Header().Set("Server", "AnyLinkAdminOpenSource")
next.ServeHTTP(w, req)
})
})

View File

@ -70,6 +70,7 @@ type ServerConfig struct {
Mtu int `json:"mtu"`
DefaultDomain string `json:"default_domain"`
IdleTimeout int `json:"idle_timeout"` // in seconds
SessionTimeout int `json:"session_timeout"` // in seconds
// AuthTimeout int `json:"auth_timeout"` // in seconds
AuditInterval int `json:"audit_interval"` // in seconds

View File

@ -57,6 +57,7 @@ var configs = []config{
{Typ: cfgInt, Name: "mobile_keepalive", Usage: "移动端keepalive接检测时间(秒)", ValInt: 7},
{Typ: cfgInt, Name: "mobile_dpd", Usage: "移动端死链接检测时间(秒)", ValInt: 15},
{Typ: cfgInt, Name: "mtu", Usage: "最大传输单元MTU", ValInt: 1460},
{Typ: cfgInt, Name: "idle_timeout", Usage: "空闲链接超时时间(秒)-超时后断开链接0关闭此功能", ValInt: 7200},
{Typ: cfgInt, Name: "session_timeout", Usage: "session过期时间(秒)-用于断线重连0永不过期", ValInt: 3600},
// {Typ: cfgInt, Name: "auth_timeout", Usage: "auth_timeout", ValInt: 0},
{Typ: cfgInt, Name: "audit_interval", Usage: "审计去重间隔(秒),-1关闭", ValInt: -1},

View File

@ -71,6 +71,7 @@ mtu = 1460
default_domain = "example.com"
#default_domain = "example.com abc.example.com"
idle_timeout = 7200
#session过期时间用于断线重连0永不过期
session_timeout = 3600
auth_timeout = 0

View File

@ -22,6 +22,7 @@ const (
UserLogoutTimeout = 3 // 用户超时登出
UserLogoutAdmin = 4 // 账号被管理员踢下线
UserLogoutExpire = 5 // 账号过期被踢下线
UserIdleTimeout = 6 // 用户空闲链接超时
)
type UserActLogProcess struct {
@ -62,6 +63,7 @@ var (
UserLogoutTimeout: "Session过期被踢下线",
UserLogoutAdmin: "账号被管理员踢下线",
UserLogoutExpire: "账号过期被踢下线",
UserIdleTimeout: "用户空闲链接超时",
},
}
)

View File

@ -33,7 +33,7 @@ require (
github.com/xhit/go-simple-mail/v2 v2.10.0
github.com/xlzd/gotp v0.0.0-20181030022105-c8557ba2c119
github.com/xuri/excelize/v2 v2.6.1
go.uber.org/atomic v1.10.0
go.uber.org/atomic v1.11.0
golang.org/x/crypto v0.8.0
golang.org/x/net v0.9.0
golang.org/x/text v0.9.0

View File

@ -631,8 +631,8 @@ go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
go.uber.org/atomic v1.5.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ=
go.uber.org/atomic v1.6.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ=
go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
go.uber.org/atomic v1.10.0 h1:9qC72Qh0+3MqyJbAn8YU5xVq1frD8bn3JtD2oXtafVQ=
go.uber.org/atomic v1.10.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0=
go.uber.org/atomic v1.11.0 h1:ZvwS0R+56ePWxUNi+Atn9dWONBPp/AUETXlHW0DxSjE=
go.uber.org/atomic v1.11.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0=
go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0=
go.uber.org/multierr v1.3.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4=
go.uber.org/multierr v1.5.0/go.mod h1:FeouvMocqHpRaaGuG9EjoKcStLC43Zu/fmqdUMPcKYU=

View File

@ -157,7 +157,7 @@ func tplRequest(typ int, w io.Writer, data RequestData) {
if data.Banner != "" {
buf := new(bytes.Buffer)
xml.EscapeText(buf, []byte(data.Banner))
_ = xml.EscapeText(buf, []byte(data.Banner))
data.Banner = buf.String()
}

View File

@ -21,10 +21,13 @@ func LinkCstp(conn net.Conn, bufRW *bufio.ReadWriter, cSess *sessdata.ConnSessio
}()
var (
err error
n int
dataLen uint16
dead = time.Duration(cSess.CstpDpd+5) * time.Second
err error
n int
dataLen uint16
dead = time.Second * time.Duration(cSess.CstpDpd+5)
idle = time.Second * time.Duration(base.Cfg.IdleTimeout)
checkIdle = base.Cfg.IdleTimeout > 0
lastTime time.Time
)
go cstpWrite(conn, bufRW, cSess)
@ -55,9 +58,19 @@ func LinkCstp(conn net.Conn, bufRW *bufio.ReadWriter, cSess *sessdata.ConnSessio
case 0x07: // KEEPALIVE
// do nothing
// base.Debug("recv keepalive", cSess.IpAddr)
// 判断超时时间
if checkIdle {
lastTime = cSess.LastDataTime.Load()
if lastTime.Before(utils.NowSec().Add(-idle)) {
base.Warn("IdleTimeout", cSess.Username, cSess.IpAddr, "lastTime", lastTime)
sessdata.CloseSess(cSess.Sess.Token, dbdata.UserIdleTimeout)
return
}
}
case 0x05: // DISCONNECT
cSess.UserLogoutCode = dbdata.UserLogoutClient
base.Debug("DISCONNECT", cSess.Username, cSess.IpAddr)
sessdata.CloseSess(cSess.Sess.Token, dbdata.UserLogoutClient)
return
case 0x03: // DPD-REQ
// base.Debug("recv DPD-REQ", cSess.IpAddr)
@ -98,6 +111,8 @@ func LinkCstp(conn net.Conn, bufRW *bufio.ReadWriter, cSess *sessdata.ConnSessio
if payloadIn(cSess, pl) {
return
}
// 只记录返回正确的数据时间
cSess.LastDataTime.Store(utils.NowSec())
}
}
}

View File

@ -93,6 +93,8 @@ func LinkDtls(conn net.Conn, cSess *sessdata.ConnSession) {
if payloadIn(cSess, pl) {
return
}
// 只记录返回正确的数据时间
cSess.LastDataTime.Store(utils.NowSec())
}
}

View File

@ -136,7 +136,7 @@ func LinkTunnel(w http.ResponseWriter, r *http.Request) {
}
HttpAddHeader(w, "X-CSTP-Split-Include", v.IpMask)
}
// 不允许的路由
// 不允许的路由 X-Cstp-Remote-Address-Ip4:
for _, v := range cSess.Group.RouteExclude {
HttpAddHeader(w, "X-CSTP-Split-Exclude", v.IpMask)
}
@ -184,10 +184,9 @@ func LinkTunnel(w http.ResponseWriter, r *http.Request) {
w.WriteHeader(http.StatusOK)
hClone := w.Header().Clone()
headers := make([]byte, 0)
buf := bytes.NewBuffer(headers)
buf := &bytes.Buffer{}
_ = hClone.Write(buf)
base.Debug(buf.String())
base.Trace("LinkTunnel Response Header:", buf.String())
hj := w.(http.Hijacker)
conn, bufRW, err := hj.Hijack()

View File

@ -89,10 +89,13 @@ func initIpPool() {
// }
// AcquireIp 获取动态ip
func AcquireIp(username, macAddr string, uniqueMac bool) net.IP {
base.Trace("AcquireIp:", username, macAddr, uniqueMac)
func AcquireIp(username, macAddr string, uniqueMac bool) (newIp net.IP) {
base.Trace("AcquireIp start:", username, macAddr, uniqueMac)
ipPoolMux.Lock()
defer ipPoolMux.Unlock()
defer func() {
ipPoolMux.Unlock()
base.Trace("AcquireIp end:", username, macAddr, uniqueMac, newIp)
}()
var (
err error

View File

@ -49,6 +49,7 @@ type ConnSession struct {
BandwidthDownAll atomic2.Uint64 // 使用下行带宽总量
closeOnce sync.Once
CloseChan chan struct{}
LastDataTime atomic2.Time // 最后数据传输时间
PayloadIn chan *Payload
PayloadOutCstp chan *Payload // Cstp的数据
PayloadOutDtls chan *Payload // Dtls的数据
@ -219,6 +220,7 @@ func (s *Session) NewConn() *ConnSession {
PayloadOutDtls: make(chan *Payload, 64),
dSess: &atomic.Value{},
}
cSess.LastDataTime.Store(time.Now())
dSess := &DtlsSession{
isActive: -1,