Thumbnail

rani/matterbridge.git

Clone URL: https://git.buni.party/rani/matterbridge.git

Viewing file on branch master

1package bmumble
2
3import (
4 "strconv"
5 "time"
6
7 "layeh.com/gumble/gumble"
8
9 "github.com/matterbridge-org/matterbridge/bridge/config"
10 "github.com/matterbridge-org/matterbridge/bridge/helper"
11)
12
13func (b *Bmumble) handleServerConfig(event *gumble.ServerConfigEvent) {
14 b.serverConfigUpdate <- *event
15}
16
17func (b *Bmumble) handleTextMessage(event *gumble.TextMessageEvent) {
18 sender := "unknown"
19 if event.TextMessage.Sender != nil {
20 sender = event.TextMessage.Sender.Name
21 }
22 // If the text message is received before receiving a ServerSync
23 // and UserState, Client.Self or Self.Channel are nil
24 if event.Client.Self == nil || event.Client.Self.Channel == nil {
25 b.Log.Warn("Connection bootstrap not finished, discarding text message")
26 return
27 }
28 // Convert Mumble HTML messages to markdown
29 parts, err := b.convertHTMLtoMarkdown(event.TextMessage.Message)
30 if err != nil {
31 b.Log.Error(err)
32 }
33 now := time.Now().UTC()
34 for i, part := range parts {
35 // Construct matterbridge message and pass on to the gateway
36 rmsg := config.Message{
37 Channel: strconv.FormatUint(uint64(event.Client.Self.Channel.ID), 10),
38 Username: sender,
39 UserID: sender + "@" + b.Host,
40 Account: b.Account,
41 }
42 if part.Image == nil {
43 rmsg.Text = part.Text
44 } else {
45 fileExt := part.FileExtension
46 if fileExt == ".jfif" {
47 fileExt = ".jpg"
48 }
49 if fileExt == ".jpe" {
50 fileExt = ".jpg"
51 }
52 fname := b.Account + "_" + strconv.FormatInt(now.UnixNano(), 10) + "_" + strconv.Itoa(i) + fileExt
53 rmsg.Extra = make(map[string][]interface{})
54 if err = helper.HandleDownloadSize(b.Log, &rmsg, fname, int64(len(part.Image)), b.General); err != nil {
55 b.Log.WithError(err).Warn("not including image in message")
56 continue
57 }
58 helper.HandleDownloadData(b.Log, &rmsg, fname, "", "", &part.Image, b.General)
59 }
60 b.Log.Debugf("Sending message to gateway: %+v", rmsg)
61 b.Remote <- rmsg
62 }
63}
64
65func (b *Bmumble) handleConnect(event *gumble.ConnectEvent) {
66 // Set the user's "bio"/comment
67 if comment := b.GetString("UserComment"); comment != "" && event.Client.Self != nil {
68 event.Client.Self.SetComment(comment)
69 }
70 // No need to talk or listen
71 event.Client.Self.SetSelfDeafened(true)
72 // if the Channel variable is set, this is a reconnect -> rejoin channel
73 if b.Channel != nil {
74 if err := b.doJoin(event.Client, *b.Channel); err != nil {
75 b.Log.Error(err)
76 }
77 b.Remote <- config.Message{
78 Username: "system",
79 Text: "rejoin",
80 Channel: "",
81 Account: b.Account,
82 Event: config.EventRejoinChannels,
83 }
84 }
85}
86
87func (b *Bmumble) handleJoinLeave(event *gumble.UserChangeEvent) {
88 // Ignore events happening before setup is done
89 if b.Channel == nil {
90 return
91 }
92 if b.GetBool("nosendjoinpart") {
93 return
94 }
95 b.Log.Debugf("Received gumble user change event: %+v", event)
96
97 text := ""
98 switch {
99 case event.Type&gumble.UserChangeKicked > 0:
100 text = " was kicked"
101 case event.Type&gumble.UserChangeBanned > 0:
102 text = " was banned"
103 case event.Type&gumble.UserChangeDisconnected > 0:
104 if event.User.Channel != nil && event.User.Channel.ID == *b.Channel {
105 text = " left"
106 }
107 case event.Type&gumble.UserChangeConnected > 0:
108 if event.User.Channel != nil && event.User.Channel.ID == *b.Channel {
109 text = " joined"
110 }
111 case event.Type&gumble.UserChangeChannel > 0:
112 // Treat Mumble channel changes the same as connects/disconnects; as far as matterbridge is concerned, they are identical
113 if event.User.Channel != nil && event.User.Channel.ID == *b.Channel {
114 text = " joined"
115 } else {
116 text = " left"
117 }
118 }
119
120 if text != "" {
121 b.Remote <- config.Message{
122 Username: "system",
123 Text: event.User.Name + text,
124 Channel: strconv.FormatUint(uint64(*b.Channel), 10),
125 Account: b.Account,
126 Event: config.EventJoinLeave,
127 }
128 }
129}
130
131func (b *Bmumble) handleUserModified(event *gumble.UserChangeEvent) {
132 // Ignore events happening before setup is done
133 if b.Channel == nil {
134 return
135 }
136
137 if event.Type&gumble.UserChangeChannel > 0 {
138 // Someone attempted to move the user out of the configured channel; attempt to join back
139 if err := b.doJoin(event.Client, *b.Channel); err != nil {
140 b.Log.Error(err)
141 }
142 }
143}
144
145func (b *Bmumble) handleUserChange(event *gumble.UserChangeEvent) {
146 // The UserChangeEvent is used for both the gumble client itself as well as other clients
147 if event.User != event.Client.Self {
148 // other users
149 b.handleJoinLeave(event)
150 } else {
151 // gumble user
152 b.handleUserModified(event)
153 }
154}
155
156func (b *Bmumble) handleDisconnect(event *gumble.DisconnectEvent) {
157 b.connected <- *event
158}
159