-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathconnection.go
92 lines (81 loc) · 1.85 KB
/
connection.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
package main
import (
"bufio"
"encoding/json"
"io"
"log"
"golang.org/x/net/websocket"
)
// Connection holds state of a connection with a player.
type Connection struct {
Chan chan Message
ws *websocket.Conn
currentID int
}
// Message is a message that is sent between the player and the server.
type Message struct {
ID int `json:"id"`
Type string `json:"type"`
Arguments []string `json:"args"`
}
func makeConnection(ws *websocket.Conn) *Connection {
conn := &Connection{
Chan: make(chan Message),
ws: ws,
}
reader := bufio.NewReader(ws)
go func() {
for {
raw, err := reader.ReadBytes('\n')
if err != nil {
if err != io.EOF {
log.Printf("error while reading from connection: %#v\n", err)
}
close(conn.Chan)
return
}
var msg Message
if json.Unmarshal(raw, &msg) != nil {
log.Printf("invalid message received: %s\n", raw)
continue
}
if msg.ID > conn.currentID {
conn.currentID = msg.ID
}
conn.Chan <- msg
}
}()
return conn
}
// Send sends a message with the given type and args to the current connection.
func (conn *Connection) Send(typ string, args ...string) (n int, err error) {
if args == nil {
args = make([]string, 0)
}
conn.currentID++
return conn.write(Message{
ID: conn.currentID,
Type: typ,
Arguments: args,
})
}
// Reply sends a reply to the given id with the given type and args to the
// current connection.
func (conn *Connection) Reply(id int, typ string, args ...string) (n int, err error) {
if args == nil {
args = make([]string, 0)
}
return conn.write(Message{
ID: id,
Type: typ,
Arguments: args,
})
}
func (conn *Connection) write(msg Message) (n int, err error) {
bytes, err := json.Marshal(msg)
if err != nil {
return -1, err
}
withlf := append(bytes, '\n')
return conn.ws.Write(withlf)
}