Files
mayfly-go/server/internal/machine/mcm/client_cache.go

123 lines
3.2 KiB
Go
Raw Normal View History

2023-10-30 17:34:56 +08:00
package mcm
import (
"errors"
2023-10-30 17:34:56 +08:00
"mayfly-go/internal/common/consts"
tagentity "mayfly-go/internal/tag/domain/entity"
2023-10-30 17:34:56 +08:00
"mayfly-go/pkg/cache"
2024-02-23 22:53:17 +08:00
"mayfly-go/pkg/logx"
2023-10-30 17:34:56 +08:00
"time"
)
// 机器客户端连接缓存,指定时间内没有访问则会被关闭
var cliCache = cache.NewTimedCache(consts.MachineConnExpireTime, 5*time.Second).
WithUpdateAccessTime(true).
OnEvicted(func(_, value any) {
value.(*Cli).Close()
})
func init() {
AddCheckSshTunnelMachineUseFunc(func(machineId int) bool {
// 遍历所有机器连接实例若存在机器连接实例使用该ssh隧道机器则返回true表示还在使用中...
items := cliCache.Items()
for _, v := range items {
sshTunnelMachine := v.Value.(*Cli).Info.SshTunnelMachine
if sshTunnelMachine != nil && int(sshTunnelMachine.Id) == machineId {
return true
}
}
return false
})
2024-02-23 22:53:17 +08:00
go checkClientAvailability(3 * time.Minute)
2023-10-30 17:34:56 +08:00
}
// 从缓存中获取客户端信息,不存在则回调获取机器信息函数,并新建。
// @param 机器的授权凭证名
func GetMachineCli(authCertName string, getMachine func(string) (*MachineInfo, error)) (*Cli, error) {
if load, ok := cliCache.Get(authCertName); ok {
2023-10-30 17:34:56 +08:00
return load.(*Cli), nil
}
mi, err := getMachine(authCertName)
2023-10-30 17:34:56 +08:00
if err != nil {
return nil, err
}
mi.Key = authCertName
c, err := mi.Conn()
2023-10-30 17:34:56 +08:00
if err != nil {
return nil, err
}
cliCache.Put(authCertName, c)
2023-10-30 17:34:56 +08:00
return c, nil
}
// 根据机器id从已连接的机器客户端中获取特权账号连接, 若不存在特权账号,则随机返回一个
func GetMachineCliById(machineId uint64) (*Cli, error) {
// 遍历所有机器连接实例删除指定机器id关联的连接...
items := cliCache.Items()
var machineCli *Cli
for _, v := range items {
cli := v.Value.(*Cli)
mi := cli.Info
if mi.Id != machineId {
continue
}
machineCli = cli
// 如果是特权账号,则跳出
if mi.AuthCertType == tagentity.AuthCertTypePrivileged {
break
}
}
if machineCli != nil {
return machineCli, nil
}
return nil, errors.New("不存在该机器id的连接")
}
2024-02-23 22:53:17 +08:00
// 删除指定机器缓存客户端,并关闭客户端连接
2023-10-30 17:34:56 +08:00
func DeleteCli(id uint64) {
// 遍历所有机器连接实例删除指定机器id关联的连接...
items := cliCache.Items()
for _, v := range items {
mi := v.Value.(*Cli).Info
if mi.Id == id {
cliCache.Delete(mi.Key)
}
}
2023-10-30 17:34:56 +08:00
}
2024-02-23 22:53:17 +08:00
// 检查缓存中的客户端是否可用,不可用则关闭客户端连接
func checkClientAvailability(interval time.Duration) {
ticker := time.NewTicker(interval)
defer ticker.Stop()
for range ticker.C {
// 遍历所有机器连接实例若存在机器连接实例使用该ssh隧道机器则返回true表示还在使用中...
items := cliCache.Items()
for _, v := range items {
if v == nil {
continue
}
2024-02-23 22:53:17 +08:00
cli := v.Value.(*Cli)
if cli.Info == nil {
continue
}
2024-03-02 19:08:19 +08:00
if cli.sshClient == nil {
continue
}
if cli.sshClient.Conn == nil {
continue
}
2024-02-23 22:53:17 +08:00
if _, _, err := cli.sshClient.Conn.SendRequest("ping", true, nil); err != nil {
logx.Errorf("machine[%s] cache client is not available: %s", cli.Info.Name, err.Error())
DeleteCli(cli.Info.Id)
}
logx.Debugf("machine[%s] cache client is available", cli.Info.Name)
}
}
}