package proxy import ( "crypto/rand" "encoding/hex" "sync" "time" ) type ProxySession struct { Token string TargetURL string Created time.Time Expires time.Time } type ProxySessionManager struct { sessions sync.Map ttl time.Duration } func NewProxySessionManager(ttl time.Duration) *ProxySessionManager { sm := &ProxySessionManager{ttl: ttl} go sm.cleanup() return sm } func (sm *ProxySessionManager) Create(targetURL string) string { token := generateToken() sm.sessions.Store(token, &ProxySession{ Token: token, TargetURL: targetURL, Created: time.Now(), Expires: time.Now().Add(sm.ttl), }) return token } func (sm *ProxySessionManager) Get(token string) *ProxySession { val, ok := sm.sessions.Load(token) if !ok { return nil } session := val.(*ProxySession) if time.Now().After(session.Expires) { sm.sessions.Delete(token) return nil } return session } func (sm *ProxySessionManager) cleanup() { ticker := time.NewTicker(5 * time.Minute) for range ticker.C { now := time.Now() sm.sessions.Range(func(key, value interface{}) bool { session := value.(*ProxySession) if now.After(session.Expires) { sm.sessions.Delete(key) } return true }) } } func generateToken() string { b := make([]byte, 16) rand.Read(b) return hex.EncodeToString(b) }