forked from pubnative/mysqlproto-go
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathconn.go
90 lines (72 loc) · 1.53 KB
/
conn.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
package mysqlproto
import (
"errors"
"io"
)
type Conn struct {
*Stream
CapabilityFlags uint32
}
var ErrNoStream = errors.New("mysqlproto: stream is not set")
func ConnectPlainHandshake(rw io.ReadWriteCloser, capabilityFlags uint32,
username, password, database string,
connectAttrs map[string]string) (Conn, error) {
stream := NewStream(rw)
handshakeV10, err := ReadHandshakeV10(stream)
if err != nil {
return Conn{}, err
}
flags := handshakeV10.CapabilityFlags & capabilityFlags
res := HandshakeResponse41(
flags,
handshakeV10.CharacterSet,
username,
password,
handshakeV10.AuthPluginData,
database,
handshakeV10.AuthPluginName,
connectAttrs,
)
conn := Conn{
stream,
uint32(res[4]) | uint32(res[5])<<8 | uint32(res[6])<<16 | uint32(res[7])<<24,
}
if _, err = conn.Write(res); err != nil {
return conn, err
}
packet, err := conn.NextPacket()
if err != nil {
return conn, err
}
if packet.Payload[0] == OK_PACKET {
return conn, nil
}
return conn, parseError(packet.Payload, conn.CapabilityFlags)
}
func (c Conn) Close() error {
if c.Stream == nil {
return ErrNoStream
}
_, err := c.Write(CommandPacket(COM_QUIT, nil))
if err != nil {
c.Stream.Close()
return err
}
pkt, err := c.NextPacket()
if err != nil {
if err != io.EOF {
c.Stream.Close()
return err
}
return c.Stream.Close()
}
if pkt.Payload[0] == OK_PACKET {
return c.Stream.Close()
}
err = parseError(pkt.Payload, c.CapabilityFlags)
if err != nil {
c.Stream.Close()
return err
}
return c.Stream.Close()
}