Golinting
This commit is contained in:
parent
def74ddc09
commit
cfeaaad88f
22
client.go
22
client.go
@ -26,8 +26,8 @@ import (
|
||||
)
|
||||
|
||||
const (
|
||||
CRLF = "\x0d\x0a"
|
||||
BUF_SIZE = 1380
|
||||
CRLF = "\x0d\x0a"
|
||||
BufSize = 1380
|
||||
)
|
||||
|
||||
type Client struct {
|
||||
@ -40,7 +40,7 @@ type Client struct {
|
||||
}
|
||||
|
||||
type ClientAlivenessState struct {
|
||||
ping_sent bool
|
||||
pingSent bool
|
||||
timestamp time.Time
|
||||
}
|
||||
|
||||
@ -56,26 +56,26 @@ func NewClient(hostname string, conn net.Conn) *Client {
|
||||
// splits messages by CRLF and send them to Daemon gorouting for processing
|
||||
// it futher. Also it can signalize that client is unavailable (disconnected).
|
||||
func (client *Client) Processor(sink chan<- ClientEvent) {
|
||||
var buf_net []byte
|
||||
var bufNet []byte
|
||||
buf := make([]byte, 0)
|
||||
log.Println(client, "New client")
|
||||
sink <- ClientEvent{client, EVENT_NEW, ""}
|
||||
sink <- ClientEvent{client, EventNew, ""}
|
||||
for {
|
||||
buf_net = make([]byte, BUF_SIZE)
|
||||
_, err := client.conn.Read(buf_net)
|
||||
bufNet = make([]byte, BufSize)
|
||||
_, err := client.conn.Read(bufNet)
|
||||
if err != nil {
|
||||
log.Println(client, "connection lost", err)
|
||||
sink <- ClientEvent{client, EVENT_DEL, ""}
|
||||
sink <- ClientEvent{client, EventDel, ""}
|
||||
break
|
||||
}
|
||||
buf_net = bytes.TrimRight(buf_net, "\x00")
|
||||
buf = append(buf, buf_net...)
|
||||
bufNet = bytes.TrimRight(bufNet, "\x00")
|
||||
buf = append(buf, bufNet...)
|
||||
if !bytes.HasSuffix(buf, []byte(CRLF)) {
|
||||
continue
|
||||
}
|
||||
for _, msg := range bytes.Split(buf[:len(buf)-2], []byte(CRLF)) {
|
||||
if len(msg) > 0 {
|
||||
sink <- ClientEvent{client, EVENT_MSG, string(msg)}
|
||||
sink <- ClientEvent{client, EventMsg, string(msg)}
|
||||
}
|
||||
}
|
||||
buf = []byte{}
|
||||
|
@ -100,22 +100,22 @@ func TestNewClient(t *testing.T) {
|
||||
go client.Processor(sink)
|
||||
|
||||
event := <-sink
|
||||
if event.event_type != EVENT_NEW {
|
||||
if event.eventType != EventNew {
|
||||
t.Fatal("no NEW event", event)
|
||||
}
|
||||
conn.inbound <- "foo"
|
||||
event = <-sink
|
||||
if (event.event_type != EVENT_MSG) || (event.text != "foo") {
|
||||
if (event.eventType != EventMsg) || (event.text != "foo") {
|
||||
t.Fatal("no first MSG", event)
|
||||
}
|
||||
conn.inbound <- "bar"
|
||||
event = <-sink
|
||||
if (event.event_type != EVENT_MSG) || (event.text != "bar") {
|
||||
if (event.eventType != EventMsg) || (event.text != "bar") {
|
||||
t.Fatal("no second MSG", event)
|
||||
}
|
||||
conn.inbound <- ""
|
||||
event = <-sink
|
||||
if event.event_type != EVENT_DEL {
|
||||
if event.eventType != EventDel {
|
||||
t.Fatal("no client termination", event)
|
||||
}
|
||||
}
|
||||
|
120
daemon.go
120
daemon.go
@ -29,36 +29,36 @@ import (
|
||||
)
|
||||
|
||||
const (
|
||||
PING_TIMEOUT = time.Second * 180 // Max time deadline for client's unresponsiveness
|
||||
PING_THRESHOLD = time.Second * 90 // Max idle client's time before PING are sent
|
||||
ALIVENESS_CHECK = time.Second * 10 // Client's aliveness check period
|
||||
PingTimeout = time.Second * 180 // Max time deadline for client's unresponsiveness
|
||||
PingThreshold = time.Second * 90 // Max idle client's time before PING are sent
|
||||
AlivenessCheck = time.Second * 10 // Client's aliveness check period
|
||||
)
|
||||
|
||||
var (
|
||||
RE_NICKNAME = regexp.MustCompile("^[a-zA-Z0-9-]{1,9}$")
|
||||
RENickname = regexp.MustCompile("^[a-zA-Z0-9-]{1,9}$")
|
||||
)
|
||||
|
||||
type Daemon struct {
|
||||
Verbose bool
|
||||
hostname string
|
||||
motd string
|
||||
clients map[*Client]bool
|
||||
client_aliveness map[*Client]*ClientAlivenessState
|
||||
rooms map[string]*Room
|
||||
room_sinks map[*Room]chan ClientEvent
|
||||
last_aliveness_check time.Time
|
||||
log_sink chan<- LogEvent
|
||||
state_sink chan<- StateEvent
|
||||
Verbose bool
|
||||
hostname string
|
||||
motd string
|
||||
clients map[*Client]bool
|
||||
clientAliveness map[*Client]*ClientAlivenessState
|
||||
rooms map[string]*Room
|
||||
roomSinks map[*Room]chan ClientEvent
|
||||
lastAlivenessCheck time.Time
|
||||
logSink chan<- LogEvent
|
||||
stateSink chan<- StateEvent
|
||||
}
|
||||
|
||||
func NewDaemon(hostname, motd string, log_sink chan<- LogEvent, state_sink chan<- StateEvent) *Daemon {
|
||||
func NewDaemon(hostname, motd string, logSink chan<- LogEvent, stateSink chan<- StateEvent) *Daemon {
|
||||
daemon := Daemon{hostname: hostname, motd: motd}
|
||||
daemon.clients = make(map[*Client]bool)
|
||||
daemon.client_aliveness = make(map[*Client]*ClientAlivenessState)
|
||||
daemon.clientAliveness = make(map[*Client]*ClientAlivenessState)
|
||||
daemon.rooms = make(map[string]*Room)
|
||||
daemon.room_sinks = make(map[*Room]chan ClientEvent)
|
||||
daemon.log_sink = log_sink
|
||||
daemon.state_sink = state_sink
|
||||
daemon.roomSinks = make(map[*Room]chan ClientEvent)
|
||||
daemon.logSink = logSink
|
||||
daemon.stateSink = stateSink
|
||||
return &daemon
|
||||
}
|
||||
|
||||
@ -160,13 +160,13 @@ func (daemon *Daemon) ClientRegister(client *Client, command string, cols []stri
|
||||
return
|
||||
}
|
||||
nickname := cols[1]
|
||||
for existing_client := range daemon.clients {
|
||||
if existing_client.nickname == nickname {
|
||||
for existingClient := range daemon.clients {
|
||||
if existingClient.nickname == nickname {
|
||||
client.ReplyParts("433", "*", nickname, "Nickname is already in use")
|
||||
return
|
||||
}
|
||||
}
|
||||
if !RE_NICKNAME.MatchString(nickname) {
|
||||
if !RENickname.MatchString(nickname) {
|
||||
client.ReplyParts("432", "*", cols[1], "Erroneous nickname")
|
||||
return
|
||||
}
|
||||
@ -198,13 +198,13 @@ func (daemon *Daemon) ClientRegister(client *Client, command string, cols []stri
|
||||
// Register new room in Daemon. Create an object, events sink, save pointers
|
||||
// to corresponding daemon's places and start room's processor goroutine.
|
||||
func (daemon *Daemon) RoomRegister(name string) (*Room, chan<- ClientEvent) {
|
||||
room_new := NewRoom(daemon.hostname, name, daemon.log_sink, daemon.state_sink)
|
||||
room_new.Verbose = daemon.Verbose
|
||||
room_sink := make(chan ClientEvent)
|
||||
daemon.rooms[name] = room_new
|
||||
daemon.room_sinks[room_new] = room_sink
|
||||
go room_new.Processor(room_sink)
|
||||
return room_new, room_sink
|
||||
roomNew := NewRoom(daemon.hostname, name, daemon.logSink, daemon.stateSink)
|
||||
roomNew.Verbose = daemon.Verbose
|
||||
roomSink := make(chan ClientEvent)
|
||||
daemon.rooms[name] = roomNew
|
||||
daemon.roomSinks[roomNew] = roomSink
|
||||
go roomNew.Processor(roomSink)
|
||||
return roomNew, roomSink
|
||||
}
|
||||
|
||||
func (daemon *Daemon) HandlerJoin(client *Client, cmd string) {
|
||||
@ -229,12 +229,12 @@ func (daemon *Daemon) HandlerJoin(client *Client, cmd string) {
|
||||
}
|
||||
denied := false
|
||||
joined := false
|
||||
for room_existing, room_sink := range daemon.room_sinks {
|
||||
if room == room_existing.name {
|
||||
if (room_existing.key != "") && (room_existing.key != key) {
|
||||
for roomExisting, roomSink := range daemon.roomSinks {
|
||||
if room == roomExisting.name {
|
||||
if (roomExisting.key != "") && (roomExisting.key != key) {
|
||||
denied = true
|
||||
} else {
|
||||
room_sink <- ClientEvent{client, EVENT_NEW, ""}
|
||||
roomSink <- ClientEvent{client, EventNew, ""}
|
||||
joined = true
|
||||
}
|
||||
break
|
||||
@ -246,12 +246,12 @@ func (daemon *Daemon) HandlerJoin(client *Client, cmd string) {
|
||||
if denied || joined {
|
||||
continue
|
||||
}
|
||||
room_new, room_sink := daemon.RoomRegister(room)
|
||||
roomNew, roomSink := daemon.RoomRegister(room)
|
||||
if key != "" {
|
||||
room_new.key = key
|
||||
room_new.StateSave()
|
||||
roomNew.key = key
|
||||
roomNew.StateSave()
|
||||
}
|
||||
room_sink <- ClientEvent{client, EVENT_NEW, ""}
|
||||
roomSink <- ClientEvent{client, EventNew, ""}
|
||||
}
|
||||
}
|
||||
|
||||
@ -261,41 +261,41 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
client := event.client
|
||||
|
||||
// Check for clients aliveness
|
||||
if daemon.last_aliveness_check.Add(ALIVENESS_CHECK).Before(now) {
|
||||
if daemon.lastAlivenessCheck.Add(AlivenessCheck).Before(now) {
|
||||
for c := range daemon.clients {
|
||||
aliveness, alive := daemon.client_aliveness[c]
|
||||
aliveness, alive := daemon.clientAliveness[c]
|
||||
if !alive {
|
||||
continue
|
||||
}
|
||||
if aliveness.timestamp.Add(PING_TIMEOUT).Before(now) {
|
||||
if aliveness.timestamp.Add(PingTimeout).Before(now) {
|
||||
log.Println(c, "ping timeout")
|
||||
c.conn.Close()
|
||||
continue
|
||||
}
|
||||
if !aliveness.ping_sent && aliveness.timestamp.Add(PING_THRESHOLD).Before(now) {
|
||||
if !aliveness.pingSent && aliveness.timestamp.Add(PingThreshold).Before(now) {
|
||||
if c.registered {
|
||||
c.Msg("PING :" + daemon.hostname)
|
||||
aliveness.ping_sent = true
|
||||
aliveness.pingSent = true
|
||||
} else {
|
||||
log.Println(c, "ping timeout")
|
||||
c.conn.Close()
|
||||
}
|
||||
}
|
||||
}
|
||||
daemon.last_aliveness_check = now
|
||||
daemon.lastAlivenessCheck = now
|
||||
}
|
||||
|
||||
switch event.event_type {
|
||||
case EVENT_NEW:
|
||||
switch event.eventType {
|
||||
case EventNew:
|
||||
daemon.clients[client] = true
|
||||
daemon.client_aliveness[client] = &ClientAlivenessState{ping_sent: false, timestamp: now}
|
||||
case EVENT_DEL:
|
||||
daemon.clientAliveness[client] = &ClientAlivenessState{pingSent: false, timestamp: now}
|
||||
case EventDel:
|
||||
delete(daemon.clients, client)
|
||||
delete(daemon.client_aliveness, client)
|
||||
for _, room_sink := range daemon.room_sinks {
|
||||
room_sink <- event
|
||||
delete(daemon.clientAliveness, client)
|
||||
for _, roomSink := range daemon.roomSinks {
|
||||
roomSink <- event
|
||||
}
|
||||
case EVENT_MSG:
|
||||
case EventMsg:
|
||||
cols := strings.SplitN(event.text, " ", 2)
|
||||
command := strings.ToUpper(cols[0])
|
||||
if daemon.Verbose {
|
||||
@ -303,7 +303,7 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
}
|
||||
if command == "QUIT" {
|
||||
delete(daemon.clients, client)
|
||||
delete(daemon.client_aliveness, client)
|
||||
delete(daemon.clientAliveness, client)
|
||||
client.conn.Close()
|
||||
continue
|
||||
}
|
||||
@ -345,9 +345,9 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
continue
|
||||
}
|
||||
if len(cols) == 1 {
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_MODE, ""}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventMode, ""}
|
||||
} else {
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_MODE, cols[1]}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventMode, cols[1]}
|
||||
}
|
||||
case "MOTD":
|
||||
go daemon.SendMotd(client)
|
||||
@ -362,7 +362,7 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
client.ReplyNoChannel(room)
|
||||
continue
|
||||
}
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_DEL, ""}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventDel, ""}
|
||||
}
|
||||
case "PING":
|
||||
if len(cols) == 1 {
|
||||
@ -398,7 +398,7 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
if !found {
|
||||
client.ReplyNoNickChan(target)
|
||||
}
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_MSG, command + " " + strings.TrimLeft(cols[1], ":")}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventMsg, command + " " + strings.TrimLeft(cols[1], ":")}
|
||||
case "TOPIC":
|
||||
if len(cols) == 1 {
|
||||
client.ReplyNotEnoughParameters("TOPIC")
|
||||
@ -416,7 +416,7 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
} else {
|
||||
change = ""
|
||||
}
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_TOPIC, change}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventTopic, change}
|
||||
case "WHO":
|
||||
if len(cols) == 1 || len(cols[1]) < 1 {
|
||||
client.ReplyNotEnoughParameters("WHO")
|
||||
@ -428,7 +428,7 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
client.ReplyNoChannel(room)
|
||||
continue
|
||||
}
|
||||
daemon.room_sinks[r] <- ClientEvent{client, EVENT_WHO, ""}
|
||||
daemon.roomSinks[r] <- ClientEvent{client, EventWho, ""}
|
||||
case "WHOIS":
|
||||
if len(cols) == 1 || len(cols[1]) < 1 {
|
||||
client.ReplyNotEnoughParameters("WHOIS")
|
||||
@ -441,9 +441,9 @@ func (daemon *Daemon) Processor(events <-chan ClientEvent) {
|
||||
client.ReplyNicknamed("421", command, "Unknown command")
|
||||
}
|
||||
}
|
||||
if aliveness, alive := daemon.client_aliveness[client]; alive {
|
||||
if aliveness, alive := daemon.clientAliveness[client]; alive {
|
||||
aliveness.timestamp = now
|
||||
aliveness.ping_sent = false
|
||||
aliveness.pingSent = false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
28
events.go
28
events.go
@ -27,26 +27,26 @@ import (
|
||||
)
|
||||
|
||||
const (
|
||||
EVENT_NEW = iota
|
||||
EVENT_DEL = iota
|
||||
EVENT_MSG = iota
|
||||
EVENT_TOPIC = iota
|
||||
EVENT_WHO = iota
|
||||
EVENT_MODE = iota
|
||||
FORMAT_MSG = "[%s] <%s> %s\n"
|
||||
FORMAT_META = "[%s] * %s %s\n"
|
||||
EventNew = iota
|
||||
EventDel = iota
|
||||
EventMsg = iota
|
||||
EventTopic = iota
|
||||
EventWho = iota
|
||||
EventMode = iota
|
||||
FormatMsg = "[%s] <%s> %s\n"
|
||||
FormatMeta = "[%s] * %s %s\n"
|
||||
)
|
||||
|
||||
// Client events going from each of client
|
||||
// They can be either NEW, DEL or unparsed MSG
|
||||
type ClientEvent struct {
|
||||
client *Client
|
||||
event_type int
|
||||
text string
|
||||
client *Client
|
||||
eventType int
|
||||
text string
|
||||
}
|
||||
|
||||
func (m ClientEvent) String() string {
|
||||
return string(m.event_type) + ": " + m.client.String() + ": " + m.text
|
||||
return string(m.eventType) + ": " + m.client.String() + ": " + m.text
|
||||
}
|
||||
|
||||
// Logging in-room events
|
||||
@ -73,9 +73,9 @@ func Logger(logdir string, events <-chan LogEvent) {
|
||||
continue
|
||||
}
|
||||
if event.meta {
|
||||
format = FORMAT_META
|
||||
format = FormatMeta
|
||||
} else {
|
||||
format = FORMAT_MSG
|
||||
format = FormatMsg
|
||||
}
|
||||
_, err = fd.WriteString(fmt.Sprintf(format, time.Now(), event.who, event.what))
|
||||
fd.Close()
|
||||
|
14
goircd.go
14
goircd.go
@ -46,11 +46,11 @@ func Run() {
|
||||
events := make(chan ClientEvent)
|
||||
log.SetFlags(log.Ldate | log.Lmicroseconds | log.Lshortfile)
|
||||
|
||||
log_sink := make(chan LogEvent)
|
||||
logSink := make(chan LogEvent)
|
||||
if *logdir == "" {
|
||||
// Dummy logger
|
||||
go func() {
|
||||
for _ = range log_sink {
|
||||
for _ = range logSink {
|
||||
}
|
||||
}()
|
||||
} else {
|
||||
@ -58,17 +58,17 @@ func Run() {
|
||||
log.Fatalln("Need absolute path for logdir")
|
||||
return
|
||||
}
|
||||
go Logger(*logdir, log_sink)
|
||||
go Logger(*logdir, logSink)
|
||||
log.Println(*logdir, "logger initialized")
|
||||
}
|
||||
|
||||
state_sink := make(chan StateEvent)
|
||||
daemon := NewDaemon(*hostname, *motd, log_sink, state_sink)
|
||||
stateSink := make(chan StateEvent)
|
||||
daemon := NewDaemon(*hostname, *motd, logSink, stateSink)
|
||||
daemon.Verbose = *verbose
|
||||
if *statedir == "" {
|
||||
// Dummy statekeeper
|
||||
go func() {
|
||||
for _ = range state_sink {
|
||||
for _ = range stateSink {
|
||||
}
|
||||
}()
|
||||
} else {
|
||||
@ -94,7 +94,7 @@ func Run() {
|
||||
log.Println("Loaded state for room", room.name)
|
||||
}
|
||||
}
|
||||
go StateKeeper(*statedir, state_sink)
|
||||
go StateKeeper(*statedir, stateSink)
|
||||
log.Println(*statedir, "statekeeper initialized")
|
||||
}
|
||||
|
||||
|
62
room.go
62
room.go
@ -26,34 +26,34 @@ import (
|
||||
)
|
||||
|
||||
var (
|
||||
RE_ROOM = regexp.MustCompile("^#[^\x00\x07\x0a\x0d ,:/]{1,200}$")
|
||||
RERoom = regexp.MustCompile("^#[^\x00\x07\x0a\x0d ,:/]{1,200}$")
|
||||
)
|
||||
|
||||
// Sanitize room's name. It can consist of 1 to 50 ASCII symbols
|
||||
// with some exclusions. All room names will have "#" prefix.
|
||||
func RoomNameValid(name string) bool {
|
||||
return RE_ROOM.MatchString(name)
|
||||
return RERoom.MatchString(name)
|
||||
}
|
||||
|
||||
type Room struct {
|
||||
Verbose bool
|
||||
name string
|
||||
topic string
|
||||
key string
|
||||
members map[*Client]bool
|
||||
hostname string
|
||||
log_sink chan<- LogEvent
|
||||
state_sink chan<- StateEvent
|
||||
Verbose bool
|
||||
name string
|
||||
topic string
|
||||
key string
|
||||
members map[*Client]bool
|
||||
hostname string
|
||||
logSink chan<- LogEvent
|
||||
stateSink chan<- StateEvent
|
||||
}
|
||||
|
||||
func NewRoom(hostname, name string, log_sink chan<- LogEvent, state_sink chan<- StateEvent) *Room {
|
||||
func NewRoom(hostname, name string, logSink chan<- LogEvent, stateSink chan<- StateEvent) *Room {
|
||||
room := Room{name: name}
|
||||
room.members = make(map[*Client]bool)
|
||||
room.topic = ""
|
||||
room.key = ""
|
||||
room.hostname = hostname
|
||||
room.log_sink = log_sink
|
||||
room.state_sink = state_sink
|
||||
room.logSink = logSink
|
||||
room.stateSink = stateSink
|
||||
return &room
|
||||
}
|
||||
|
||||
@ -66,9 +66,9 @@ func (room *Room) SendTopic(client *Client) {
|
||||
}
|
||||
|
||||
// Send message to all room's subscribers, possibly excluding someone
|
||||
func (room *Room) Broadcast(msg string, client_to_ignore ...*Client) {
|
||||
func (room *Room) Broadcast(msg string, clientToIgnore ...*Client) {
|
||||
for member := range room.members {
|
||||
if (len(client_to_ignore) > 0) && member == client_to_ignore[0] {
|
||||
if (len(clientToIgnore) > 0) && member == clientToIgnore[0] {
|
||||
continue
|
||||
}
|
||||
member.Msg(msg)
|
||||
@ -76,22 +76,22 @@ func (room *Room) Broadcast(msg string, client_to_ignore ...*Client) {
|
||||
}
|
||||
|
||||
func (room *Room) StateSave() {
|
||||
room.state_sink <- StateEvent{room.name, room.topic, room.key}
|
||||
room.stateSink <- StateEvent{room.name, room.topic, room.key}
|
||||
}
|
||||
|
||||
func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
var client *Client
|
||||
for event := range events {
|
||||
client = event.client
|
||||
switch event.event_type {
|
||||
case EVENT_NEW:
|
||||
switch event.eventType {
|
||||
case EventNew:
|
||||
room.members[client] = true
|
||||
if room.Verbose {
|
||||
log.Println(client, "joined", room.name)
|
||||
}
|
||||
room.SendTopic(client)
|
||||
room.Broadcast(fmt.Sprintf(":%s JOIN %s", client, room.name))
|
||||
room.log_sink <- LogEvent{room.name, client.nickname, "joined", true}
|
||||
room.logSink <- LogEvent{room.name, client.nickname, "joined", true}
|
||||
nicknames := []string{}
|
||||
for member := range room.members {
|
||||
nicknames = append(nicknames, member.nickname)
|
||||
@ -99,7 +99,7 @@ func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
sort.Strings(nicknames)
|
||||
client.ReplyNicknamed("353", "=", room.name, strings.Join(nicknames, " "))
|
||||
client.ReplyNicknamed("366", room.name, "End of NAMES list")
|
||||
case EVENT_DEL:
|
||||
case EventDel:
|
||||
if _, subscribed := room.members[client]; !subscribed {
|
||||
client.ReplyNicknamed("442", room.name, "You are not on that channel")
|
||||
continue
|
||||
@ -107,8 +107,8 @@ func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
delete(room.members, client)
|
||||
msg := fmt.Sprintf(":%s PART %s :%s", client, room.name, client.nickname)
|
||||
room.Broadcast(msg)
|
||||
room.log_sink <- LogEvent{room.name, client.nickname, "left", true}
|
||||
case EVENT_TOPIC:
|
||||
room.logSink <- LogEvent{room.name, client.nickname, "left", true}
|
||||
case EventTopic:
|
||||
if _, subscribed := room.members[client]; !subscribed {
|
||||
client.ReplyParts("442", room.name, "You are not on that channel")
|
||||
continue
|
||||
@ -120,14 +120,14 @@ func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
room.topic = strings.TrimLeft(event.text, ":")
|
||||
msg := fmt.Sprintf(":%s TOPIC %s :%s", client, room.name, room.topic)
|
||||
go room.Broadcast(msg)
|
||||
room.log_sink <- LogEvent{room.name, client.nickname, "set topic to " + room.topic, true}
|
||||
room.logSink <- LogEvent{room.name, client.nickname, "set topic to " + room.topic, true}
|
||||
room.StateSave()
|
||||
case EVENT_WHO:
|
||||
case EventWho:
|
||||
for m := range room.members {
|
||||
client.ReplyNicknamed("352", room.name, m.username, m.conn.RemoteAddr().String(), room.hostname, m.nickname, "H", "0 "+m.realname)
|
||||
}
|
||||
client.ReplyNicknamed("315", room.name, "End of /WHO list")
|
||||
case EVENT_MODE:
|
||||
case EventMode:
|
||||
if event.text == "" {
|
||||
mode := "+"
|
||||
if room.key != "" {
|
||||
@ -146,7 +146,7 @@ func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
continue
|
||||
}
|
||||
var msg string
|
||||
var msg_log string
|
||||
var msgLog string
|
||||
if strings.HasPrefix(event.text, "+k") {
|
||||
cols := strings.Split(event.text, " ")
|
||||
if len(cols) == 1 {
|
||||
@ -155,19 +155,19 @@ func (room *Room) Processor(events <-chan ClientEvent) {
|
||||
}
|
||||
room.key = cols[1]
|
||||
msg = fmt.Sprintf(":%s MODE %s +k %s", client, room.name, room.key)
|
||||
msg_log = "set channel key to " + room.key
|
||||
msgLog = "set channel key to " + room.key
|
||||
} else if strings.HasPrefix(event.text, "-k") {
|
||||
room.key = ""
|
||||
msg = fmt.Sprintf(":%s MODE %s -k", client, room.name)
|
||||
msg_log = "removed channel key"
|
||||
msgLog = "removed channel key"
|
||||
}
|
||||
go room.Broadcast(msg)
|
||||
room.log_sink <- LogEvent{room.name, client.nickname, msg_log, true}
|
||||
room.logSink <- LogEvent{room.name, client.nickname, msgLog, true}
|
||||
room.StateSave()
|
||||
case EVENT_MSG:
|
||||
case EventMsg:
|
||||
sep := strings.Index(event.text, " ")
|
||||
room.Broadcast(fmt.Sprintf(":%s %s %s :%s", client, event.text[:sep], room.name, event.text[sep+1:]), client)
|
||||
room.log_sink <- LogEvent{room.name, client.nickname, event.text[sep+1:], false}
|
||||
room.logSink <- LogEvent{room.name, client.nickname, event.text[sep+1:], false}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
60
room_test.go
60
room_test.go
@ -5,28 +5,28 @@ import (
|
||||
"testing"
|
||||
)
|
||||
|
||||
func no_nickchan(t *testing.T, c *TestingConn) {
|
||||
func noNickchan(t *testing.T, c *TestingConn) {
|
||||
if r := <-c.outbound; !strings.HasPrefix(r, ":foohost 401") {
|
||||
t.Fatal("no nick/channel", r)
|
||||
}
|
||||
}
|
||||
|
||||
func no_chan(t *testing.T, c *TestingConn) {
|
||||
func noChan(t *testing.T, c *TestingConn) {
|
||||
if r := <-c.outbound; !strings.HasPrefix(r, ":foohost 403") {
|
||||
t.Fatal("no channel", r)
|
||||
}
|
||||
}
|
||||
|
||||
func not_enough_params(t *testing.T, c *TestingConn) {
|
||||
func notEnoughParams(t *testing.T, c *TestingConn) {
|
||||
if r := <-c.outbound; !strings.HasPrefix(r, ":foohost 461") {
|
||||
t.Fatal("not enough params", r)
|
||||
}
|
||||
}
|
||||
|
||||
func TestTwoUsers(t *testing.T) {
|
||||
log_sink := make(chan LogEvent, 8)
|
||||
state_sink := make(chan StateEvent, 8)
|
||||
daemon := NewDaemon("foohost", "", log_sink, state_sink)
|
||||
logSink := make(chan LogEvent, 8)
|
||||
stateSink := make(chan StateEvent, 8)
|
||||
daemon := NewDaemon("foohost", "", logSink, stateSink)
|
||||
events := make(chan ClientEvent)
|
||||
go daemon.Processor(events)
|
||||
|
||||
@ -50,9 +50,9 @@ func TestTwoUsers(t *testing.T) {
|
||||
}
|
||||
|
||||
conn1.inbound <- "WHOIS"
|
||||
not_enough_params(t, conn1)
|
||||
notEnoughParams(t, conn1)
|
||||
conn1.inbound <- "WHOIS nick3"
|
||||
no_nickchan(t, conn1)
|
||||
noNickchan(t, conn1)
|
||||
conn1.inbound <- "WHOIS nick2"
|
||||
if r := <-conn1.outbound; r != ":foohost 311 nick1 nick2 foo2 Unknown * :Long name2\r\n" {
|
||||
t.Fatal("first WHOIS 311", r)
|
||||
@ -73,9 +73,9 @@ func TestTwoUsers(t *testing.T) {
|
||||
}
|
||||
|
||||
conn1.inbound <- "WHO"
|
||||
not_enough_params(t, conn1)
|
||||
notEnoughParams(t, conn1)
|
||||
conn1.inbound <- "WHO #fooroom"
|
||||
no_chan(t, conn1)
|
||||
noChan(t, conn1)
|
||||
|
||||
conn1.inbound <- "JOIN #foo"
|
||||
conn2.inbound <- "JOIN #foo"
|
||||
@ -98,9 +98,9 @@ func TestTwoUsers(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestJoin(t *testing.T) {
|
||||
log_sink := make(chan LogEvent, 8)
|
||||
state_sink := make(chan StateEvent, 8)
|
||||
daemon := NewDaemon("foohost", "", log_sink, state_sink)
|
||||
logSink := make(chan LogEvent, 8)
|
||||
stateSink := make(chan StateEvent, 8)
|
||||
daemon := NewDaemon("foohost", "", logSink, stateSink)
|
||||
events := make(chan ClientEvent)
|
||||
go daemon.Processor(events)
|
||||
conn := NewTestingConn()
|
||||
@ -113,11 +113,11 @@ func TestJoin(t *testing.T) {
|
||||
}
|
||||
|
||||
conn.inbound <- "JOIN"
|
||||
not_enough_params(t, conn)
|
||||
notEnoughParams(t, conn)
|
||||
conn.inbound <- "JOIN bla/bla/bla"
|
||||
no_chan(t, conn)
|
||||
noChan(t, conn)
|
||||
conn.inbound <- "JOIN bla:bla:bla"
|
||||
no_chan(t, conn)
|
||||
noChan(t, conn)
|
||||
|
||||
conn.inbound <- "JOIN #foo"
|
||||
if r := <-conn.outbound; r != ":foohost 331 nick2 #foo :No topic is set\r\n" {
|
||||
@ -132,7 +132,7 @@ func TestJoin(t *testing.T) {
|
||||
if r := <-conn.outbound; r != ":foohost 366 nick2 #foo :End of NAMES list\r\n" {
|
||||
t.Fatal("no end of NAMES list", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "joined") || (r.where != "#foo") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "joined") || (r.where != "#foo") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("invalid join log event", r)
|
||||
}
|
||||
|
||||
@ -146,10 +146,10 @@ func TestJoin(t *testing.T) {
|
||||
if _, ok := daemon.rooms["#baz"]; !ok {
|
||||
t.Fatal("#baz does not exist")
|
||||
}
|
||||
if r := <-log_sink; (r.what != "joined") || (r.where != "#bar") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "joined") || (r.where != "#bar") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("invalid join log event #bar", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "joined") || (r.where != "#baz") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "joined") || (r.where != "#baz") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("invalid join log event #baz", r)
|
||||
}
|
||||
|
||||
@ -163,16 +163,16 @@ func TestJoin(t *testing.T) {
|
||||
if daemon.rooms["#bazenc"].key != "key2" {
|
||||
t.Fatal("no room with key2")
|
||||
}
|
||||
if r := <-log_sink; (r.what != "joined") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "joined") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("invalid join log event #barenc", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "joined") || (r.where != "#bazenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "joined") || (r.where != "#bazenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("invalid join log event #bazenc", r)
|
||||
}
|
||||
if r := <-state_sink; (r.topic != "") || (r.where != "#barenc") || (r.key != "key1") {
|
||||
if r := <-stateSink; (r.topic != "") || (r.where != "#barenc") || (r.key != "key1") {
|
||||
t.Fatal("set channel key1 state", r)
|
||||
}
|
||||
if r := <-state_sink; (r.topic != "") || (r.where != "#bazenc") || (r.key != "key2") {
|
||||
if r := <-stateSink; (r.topic != "") || (r.where != "#bazenc") || (r.key != "key2") {
|
||||
t.Fatal("set channel key2 state", r)
|
||||
}
|
||||
|
||||
@ -183,10 +183,10 @@ func TestJoin(t *testing.T) {
|
||||
if daemon.rooms["#barenc"].key != "" {
|
||||
t.Fatal("removing key from #barenc")
|
||||
}
|
||||
if r := <-log_sink; (r.what != "removed channel key") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "removed channel key") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("removed channel key log", r)
|
||||
}
|
||||
if r := <-state_sink; (r.topic != "") || (r.where != "#barenc") || (r.key != "") {
|
||||
if r := <-stateSink; (r.topic != "") || (r.where != "#barenc") || (r.key != "") {
|
||||
t.Fatal("removed channel key state", r)
|
||||
}
|
||||
|
||||
@ -194,7 +194,7 @@ func TestJoin(t *testing.T) {
|
||||
if r := <-conn.outbound; r != ":foohost 442 #bazenc :You are not on that channel\r\n" {
|
||||
t.Fatal("not on that channel", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "left") || (r.where != "#bazenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "left") || (r.where != "#bazenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("left #bazenc log", r)
|
||||
}
|
||||
|
||||
@ -207,10 +207,10 @@ func TestJoin(t *testing.T) {
|
||||
if r := <-conn.outbound; r != ":nick2!foo2@someclient MODE #barenc +k newkey\r\n" {
|
||||
t.Fatal("+k MODE setting", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "set channel key to newkey") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "set channel key to newkey") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("set channel key", r)
|
||||
}
|
||||
if r := <-state_sink; (r.topic != "") || (r.where != "#barenc") || (r.key != "newkey") {
|
||||
if r := <-stateSink; (r.topic != "") || (r.where != "#barenc") || (r.key != "newkey") {
|
||||
t.Fatal("set channel newkey state", r)
|
||||
}
|
||||
|
||||
@ -218,10 +218,10 @@ func TestJoin(t *testing.T) {
|
||||
if r := <-conn.outbound; r != ":nick2!foo2@someclient TOPIC #barenc :New topic\r\n" {
|
||||
t.Fatal("set TOPIC", r)
|
||||
}
|
||||
if r := <-log_sink; (r.what != "set topic to New topic") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
if r := <-logSink; (r.what != "set topic to New topic") || (r.where != "#barenc") || (r.who != "nick2") || (r.meta != true) {
|
||||
t.Fatal("set TOPIC log", r)
|
||||
}
|
||||
if r := <-state_sink; (r.topic != "New topic") || (r.where != "#barenc") || (r.key != "newkey") {
|
||||
if r := <-stateSink; (r.topic != "New topic") || (r.where != "#barenc") || (r.key != "newkey") {
|
||||
t.Fatal("set channel TOPIC state", r)
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user