blob: b578f0d54675b340eebabb3b6fd178309bc35bad [file] [log] [blame]
package irc
import (
"context"
"fmt"
"time"
"github.com/golang/glog"
)
var (
errBanned = fmt.Errorf("user is shitlisted")
)
// getconn either gets a connection by username, or creates a new one (after
// evicting the least recently used connection).
func (m *Manager) getconn(ctx context.Context, userTelegram string) (*ircconn, error) {
// Is the user shitlisted?
if t, ok := m.shitlist[userTelegram]; ok && time.Now().Before(t) {
return nil, errBanned
}
// Do we already have a connection?
c, ok := m.conns[userTelegram]
if ok {
// Bump and return.
c.last = time.Now()
return c, nil
}
// Are we at the limit of allowed connections?
if len(m.conns) >= m.max {
// Evict least recently used
evict := ""
lru := time.Now()
for _, c := range m.conns {
if c.last.Before(lru) {
evict = c.user
lru = c.last
}
}
if evict == "" {
glog.Exitf("could not find connection to evict, %v", m.conns)
}
m.conns[evict].Evict()
delete(m.conns, evict)
}
// Allocate new connection
return m.newconn(ctx, userTelegram, false)
}
// newconn creates a new IRC connection as a given user, and saves it to the
// conns map.
func (m *Manager) newconn(ctx context.Context, userTelegram string, backup bool) (*ircconn, error) {
c, err := NewConn(m.server, m.channel, userTelegram, backup, m.Event)
if err != nil {
return nil, err
}
m.conns[userTelegram] = c
go c.Run(m.runctx)
return c, nil
}