forked from Bose/minisentinel
/
sentinelCmds.go
130 lines (114 loc) · 2.94 KB
/
sentinelCmds.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
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
package minisentinel
import (
"fmt"
"reflect"
"strings"
"github.com/alicebob/miniredis/server"
)
const msgInvalidSentinelCommand = "ERR unknown command '%s'"
func commandsSentinel(s *Sentinel) {
s.srv.Register("SENTINEL", s.cmdsSentinel)
}
// cmdsSentinel - entry point for all commands that start with SENTINEL
func (s *Sentinel) cmdsSentinel(c *server.Peer, cmd string, args []string) {
if !isSentinelCmd(cmd) {
c.WriteError(fmt.Sprintf(msgInvalidSentinelCommand, cmd))
return
}
if len(args) > 2 {
c.WriteError(errWrongNumber(cmd))
return
}
if !s.handleAuth(c) {
return
}
subCmd := strings.ToUpper(args[0])
if subCmd == "MASTERS" {
err := s.mastersCommand(c, cmd, args)
if err != nil {
c.WriteError(err.Error())
}
return
}
if subCmd == "GET-MASTER-ADDR-BY-NAME" {
err := s.getMasterAddrByNameCommand(c, cmd, args)
if err != nil {
c.WriteError(err.Error())
}
return
}
if subCmd == "SLAVES" {
err := s.slavesCommand(c, cmd, args)
if err != nil {
c.WriteError(err.Error())
}
return
}
c.WriteError(fmt.Sprintf(msgInvalidSentinelCommand, subCmd))
return
}
func (s *Sentinel) getMasterAddrByNameCommand(c *server.Peer, cmd string, args []string) error {
if !isSentinelCmd(cmd) {
return fmt.Errorf(msgInvalidSentinelCommand, cmd)
}
subCmd := strings.ToUpper(args[0])
if subCmd != "GET-MASTER-ADDR-BY-NAME" {
return fmt.Errorf(msgInvalidSentinelCommand, subCmd)
}
if strings.ToUpper(s.masterInfo.Name) != strings.ToUpper(args[1]) {
c.WriteLen(-1)
return nil
}
c.WriteLen(2)
c.WriteBulk(s.master.Host())
c.WriteBulk(s.master.Port())
return nil
}
func (s *Sentinel) slavesCommand(c *server.Peer, cmd string, args []string) error {
if !isSentinelCmd(cmd) {
return fmt.Errorf(msgInvalidSentinelCommand, cmd)
}
subCmd := strings.ToUpper(args[0])
if subCmd != "SLAVES" {
return fmt.Errorf(msgInvalidSentinelCommand, subCmd)
}
c.WriteLen(1)
c.WriteLen(40)
t := reflect.TypeOf(s.replicaInfo)
v := reflect.ValueOf(s.replicaInfo)
// Iterate over all available fields and read the tag value
for i := 0; i < t.NumField(); i++ {
field := t.Field(i)
tag := field.Tag.Get("mapstructure")
c.WriteBulk(tag)
c.WriteBulk(v.Field(i).Interface().(string))
}
return nil
}
func (s *Sentinel) mastersCommand(c *server.Peer, cmd string, args []string) error {
if !isSentinelCmd(cmd) {
return fmt.Errorf(msgInvalidSentinelCommand, cmd)
}
subCmd := strings.ToUpper(args[0])
if subCmd != "MASTERS" {
return fmt.Errorf(msgInvalidSentinelCommand, subCmd)
}
c.WriteLen(1)
c.WriteLen(40)
t := reflect.TypeOf(s.masterInfo)
v := reflect.ValueOf(s.masterInfo)
// Iterate over all available fields and read the tag value
for i := 0; i < t.NumField(); i++ {
field := t.Field(i)
tag := field.Tag.Get("mapstructure")
c.WriteBulk(tag)
c.WriteBulk(v.Field(i).Interface().(string))
}
return nil
}
func isSentinelCmd(cmd string) bool {
if strings.ToUpper(cmd) != "SENTINEL" {
return false
}
return true
}