Skip to content

Commit 5bc8231

Browse files
committed
Add welcome message functionality
(Telegram and whatsapp for now)
1 parent 08692ee commit 5bc8231

File tree

7 files changed

+211
-26
lines changed

7 files changed

+211
-26
lines changed

bridge/config/config.go

+1
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import (
1515
)
1616

1717
const (
18+
EventWelcomeMsg = "welcome"
1819
EventJoinLeave = "join_leave"
1920
EventTopicChange = "topic_change"
2021
EventFailure = "failure"

bridge/telegram/handlers.go

+2
Original file line numberDiff line numberDiff line change
@@ -287,7 +287,9 @@ func (b *Btelegram) handleUserJoin(update tgbotapi.Update) {
287287
Event: config.EventJoinLeave,
288288
Text: "joined chat",
289289
}
290+
b.Remote <- rmsg
290291

292+
rmsg.Event = config.EventWelcomeMsg
291293
b.Remote <- rmsg
292294
}
293295
}

bridge/whatsappmulti/handlers.go

+2
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,9 @@ func (b *Bwhatsapp) handleUserJoin(event *events.GroupInfo) {
5353
Event: config.EventJoinLeave,
5454
Text: "joined chat",
5555
}
56+
b.Remote <- rmsg
5657

58+
rmsg.Event = config.EventWelcomeMsg
5759
b.Remote <- rmsg
5860
}
5961
}

gateway/channelstore.go

+68
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
package gateway
2+
3+
import (
4+
"encoding/gob"
5+
6+
"github.com/42wim/matterbridge/bridge/config"
7+
"github.com/philippgille/gokv"
8+
"github.com/philippgille/gokv/bbolt"
9+
"github.com/philippgille/gokv/encoding"
10+
)
11+
12+
type ChannelData struct {
13+
HasWelcomeMessage bool
14+
WelcomeMessage config.Message
15+
}
16+
17+
func (r *Router) getChannelStore(path string) gokv.Store {
18+
gob.Register(map[string]interface{}{})
19+
gob.Register(config.FileInfo{})
20+
21+
options := bbolt.Options{
22+
BucketName: "ChannelData",
23+
Path: path,
24+
Codec: encoding.Gob,
25+
}
26+
27+
gob.Register(map[string]interface{}{})
28+
29+
store, err := bbolt.NewStore(options)
30+
if err != nil {
31+
r.logger.Errorf("Could not connect to db: %s", path)
32+
}
33+
34+
return store
35+
}
36+
37+
func (r *Router) getWelcomeMessage(Channel string) *config.Message {
38+
channelData := new(ChannelData)
39+
found, err := r.ChannelStore.Get(Channel, channelData)
40+
if err != nil {
41+
r.logger.Error(err)
42+
}
43+
44+
if found && channelData.HasWelcomeMessage {
45+
return &channelData.WelcomeMessage
46+
}
47+
48+
return nil
49+
}
50+
51+
func (r *Router) setWelcomeMessage(Channel string, newWelcomeMessage *config.Message) error {
52+
channelData := new(ChannelData)
53+
r.ChannelStore.Get(Channel, channelData)
54+
55+
if newWelcomeMessage == nil {
56+
channelData.HasWelcomeMessage = false
57+
channelData.WelcomeMessage = config.Message{}
58+
} else {
59+
channelData.HasWelcomeMessage = true
60+
channelData.WelcomeMessage = *newWelcomeMessage
61+
}
62+
63+
err := r.ChannelStore.Set(Channel, channelData)
64+
if err != nil {
65+
r.logger.Errorf(err.Error())
66+
}
67+
return err
68+
}

gateway/command.go

+109-21
Original file line numberDiff line numberDiff line change
@@ -1,43 +1,82 @@
11
package gateway
22

33
import (
4+
"strings"
5+
46
"github.com/42wim/matterbridge/bridge/config"
57
)
68

79
// returns true if a command was registered (therefore a should not be relayed
810
func (r *Router) handleCommand(msg *config.Message) bool {
9-
switch text := msg.Text; text {
10-
case "!chatId":
11+
help := `!optout - opt out from all message relaying
12+
!optoutmedia - only opt out from relaying attachments
13+
!optin - opt back into chat relaying
14+
!setwelcome - set channel welcome message (admin)
15+
!unsetwelcome - clear channel welcome message (admin)
16+
!help - display this message`
17+
18+
isAdmin := r.isAdmin(msg)
19+
addTextFromCaptions(msg)
20+
cmd := msg.Text
21+
22+
switch {
23+
case cmd == "!help":
24+
r.logger.Debug("!help")
25+
r.replyCmd(msg, help)
26+
case cmd == "!chatId":
1127
r.logger.Infof("!chatId: %s", msg.Channel)
12-
case "!optin":
28+
case cmd == "!userId":
29+
r.logger.Infof("!userId: %s", msg.UserID)
30+
case cmd == "!ping":
31+
r.logger.Debug("!pong: %s,%s", msg.Channel, msg.UserID)
32+
r.replyCmd(msg, "pong!")
33+
case cmd == "!pingdm":
34+
r.logger.Debug("!pongdm: %s,%s", msg.Channel, msg.UserID)
35+
r.replyDM(msg, "pong!")
36+
case cmd == "!optin":
1337
r.logger.Debugf("!optin: %s", msg.UserID)
1438
r.handleOptOutCmd(msg, OptIn)
15-
case "!optout":
39+
case cmd == "!optout":
1640
r.logger.Debugf("!optout: %s", msg.UserID)
1741
r.handleOptOutCmd(msg, OptOut)
18-
case "!optoutmedia":
42+
case cmd == "!optoutmedia":
1943
r.logger.Debugf("!optoutmedia: %s", msg.UserID)
2044
r.handleOptOutCmd(msg, OptOutMediaOnly)
21-
case "!help":
22-
r.logger.Debug("!help")
23-
help := `!optout - opt out from all message relaying
24-
!optoutmedia - only opt out from relaying attachments
25-
!optin - opt back into chat relaying
26-
!help - display this message`
27-
28-
r.replyCmd(msg, help)
29-
case "!ping":
30-
r.logger.Debug("!pong")
31-
r.replyCmd(msg, "pong!")
32-
case "!pingdm":
33-
r.logger.Debug("!pongdm")
34-
r.replyDM(msg, "pong!")
45+
case isAdmin && strings.HasPrefix(cmd, "!setwelcome"):
46+
r.logger.Debugf("!setwelcome: %s - %+v", msg.Channel, msg)
47+
r.handleWelcomeCmd(msg, msg)
48+
case isAdmin && strings.HasPrefix(cmd, "!unsetwelcome"):
49+
r.logger.Debugf("!unsetwelcome: %s", msg.Channel)
50+
r.handleWelcomeCmd(msg, nil)
51+
case cmd == "!echowelcome":
52+
r.logger.Debugf("!echowelcome: %s,%s", msg.Channel, msg.UserID)
53+
r.handleEchoWelcomeCmd(msg)
3554
default:
3655
return false
3756
}
57+
3858
return true
3959
}
4060

61+
func (r *Router) isAdmin(msg *config.Message) bool {
62+
admins, _ := r.GetStringSlice("Admins")
63+
64+
for _, ID := range admins {
65+
if msg.UserID == ID {
66+
return true
67+
}
68+
}
69+
return false
70+
}
71+
72+
func addTextFromCaptions(msg *config.Message) {
73+
for _, f := range msg.Extra["file"] {
74+
fi := f.(config.FileInfo)
75+
76+
msg.Text += fi.Comment
77+
}
78+
}
79+
4180
func (r *Router) replyCmd(msg *config.Message, str string) {
4281
srcBridge := r.getBridge(msg.Account)
4382

@@ -71,8 +110,20 @@ func (r *Router) replyDM(msg *config.Message, str string) {
71110
srcBridge.Send(reply)
72111
}
73112

74-
func (r *Router) handleOptOutCmd(msg *config.Message, newStaus OptOutStatus) {
75-
err := r.setOptOutStatus(msg.UserID, newStaus)
113+
func (r *Router) sendDM(msg *config.Message, dmChannel string) {
114+
srcBridge := r.getBridge(msg.Account)
115+
116+
msg.Channel = dmChannel
117+
msg.Username = ""
118+
msg.UserID = ""
119+
msg.ID = ""
120+
msg.Event = ""
121+
122+
srcBridge.Send(*msg)
123+
}
124+
125+
func (r *Router) handleOptOutCmd(msg *config.Message, newStatus OptOutStatus) {
126+
err := r.setOptOutStatus(msg.UserID, newStatus)
76127

77128
reply := "Successfully set message relay preferences."
78129
if err != nil {
@@ -81,3 +132,40 @@ func (r *Router) handleOptOutCmd(msg *config.Message, newStaus OptOutStatus) {
81132

82133
r.replyCmd(msg, reply)
83134
}
135+
136+
func (r *Router) handleWelcomeCmd(msg *config.Message, welcomeMsg *config.Message) {
137+
138+
if welcomeMsg != nil {
139+
welcomeMsg.Text = strings.Replace(welcomeMsg.Text, "!setwelcome ", "", 1)
140+
141+
for i, f := range welcomeMsg.Extra["file"] {
142+
fi := f.(config.FileInfo)
143+
fi.Comment = strings.Replace(fi.Comment, "!setwelcome ", "", 1)
144+
145+
welcomeMsg.Extra["file"][i] = fi
146+
}
147+
}
148+
149+
err := r.setWelcomeMessage(msg.Channel, welcomeMsg)
150+
151+
reply := "Successfully set welcome message for channel."
152+
if welcomeMsg == nil {
153+
reply = "Successfully removed welcome message for channel."
154+
}
155+
if err != nil {
156+
reply = "Error setting channel welcome message, try again later or contact the moderators."
157+
}
158+
159+
r.replyCmd(msg, reply)
160+
}
161+
162+
func (r *Router) handleEchoWelcomeCmd(msg *config.Message) {
163+
msg.Event = config.EventWelcomeMsg
164+
165+
if r.getWelcomeMessage(msg.Channel) == nil {
166+
r.replyCmd(msg, "No welcome message configured, set with !setwelcome")
167+
return
168+
}
169+
170+
r.handleEventWelcome(msg)
171+
}

gateway/handlers.go

+14
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,20 @@ func (r *Router) handleEventGetChannelMembers(msg *config.Message) {
4949
}
5050
}
5151

52+
func (r *Router) handleEventWelcome(msg *config.Message) bool {
53+
if msg.Event != config.EventWelcomeMsg {
54+
return false
55+
}
56+
57+
welcomeMsg := r.getWelcomeMessage(msg.Channel)
58+
59+
if welcomeMsg != nil {
60+
r.sendDM(welcomeMsg, msg.UserID)
61+
}
62+
63+
return true
64+
}
65+
5266
// handleEventRejoinChannels handles rejoining of channels.
5367
func (r *Router) handleEventRejoinChannels(msg *config.Message) {
5468
if msg.Event != config.EventRejoinChannels {

gateway/router.go

+15-5
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ type Router struct {
2121
Message chan config.Message
2222
MattermostPlugin chan config.Message
2323
UserStore gokv.Store
24+
ChannelStore gokv.Store
2425

2526
logger *logrus.Entry
2627
}
@@ -101,9 +102,13 @@ func (r *Router) Start() error {
101102
}
102103
}
103104
}
104-
userStorePath, exists := r.Config.GetString("UserStorePath")
105+
dataStorePath, exists := r.Config.GetString("UserStore")
105106
if exists {
106-
r.UserStore = r.getUserStore(userStorePath)
107+
r.UserStore = r.getUserStore(dataStorePath)
108+
}
109+
dataStorePath, exists = r.Config.GetString("ChannelStore")
110+
if exists {
111+
r.ChannelStore = r.getChannelStore(dataStorePath)
107112
}
108113

109114
go r.handleReceive()
@@ -137,14 +142,19 @@ func (r *Router) getBridge(account string) *bridge.Bridge {
137142
func (r *Router) handleReceive() {
138143
for msg := range r.Message {
139144
msg := msg // scopelint
140-
if r.handleCommand(&msg) {
141-
continue
142-
}
145+
146+
skipMsg := false
147+
skipMsg = skipMsg || r.handleCommand(&msg)
148+
skipMsg = skipMsg || r.handleEventWelcome(&msg)
143149
r.handleEventGetChannelMembers(&msg)
144150
r.handleEventFailure(&msg)
145151
r.handleEventRejoinChannels(&msg)
146152
r.handleOptOutUser(&msg)
147153

154+
if skipMsg {
155+
continue
156+
}
157+
148158
// Set message protocol based on the account it came from
149159
msg.Protocol = r.getBridge(msg.Account).Protocol
150160

0 commit comments

Comments
 (0)