Thumbnail

rani/matterbridge.git

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

Viewing file on branch master

1package rockethook
2
3import (
4 "crypto/tls"
5 "encoding/json"
6 "io"
7 "log"
8 "net"
9 "net/http"
10 "regexp"
11)
12
13// Message for rocketchat outgoing webhook.
14type Message struct {
15 Token string `json:"token"`
16 ChannelID string `json:"channel_id"`
17 ChannelName string `json:"channel_name"`
18 Timestamp string `json:"timestamp"`
19 UserID string `json:"user_id"`
20 UserName string `json:"user_name"`
21 Text string `json:"text"`
22}
23
24// Client for Rocketchat.
25type Client struct {
26 In chan Message
27 httpclient *http.Client
28 Config
29}
30
31// Config for client.
32type Config struct {
33 BindAddress string // Address to listen on
34 Token string // Only allow this token from Rocketchat. (Allow everything when empty)
35 InsecureSkipVerify bool // disable certificate checking
36}
37
38// New Rocketchat client.
39func New(url string, config Config) *Client {
40 c := &Client{In: make(chan Message), Config: config}
41 tr := &http.Transport{
42 TLSClientConfig: &tls.Config{InsecureSkipVerify: config.InsecureSkipVerify}, //nolint:gosec
43 }
44 c.httpclient = &http.Client{Transport: tr}
45 _, _, err := net.SplitHostPort(c.BindAddress)
46 if err != nil {
47 log.Fatalf("incorrect bindaddress %s", c.BindAddress)
48 }
49 go c.StartServer()
50 return c
51}
52
53// StartServer starts a webserver listening for incoming mattermost POSTS.
54func (c *Client) StartServer() {
55 mux := http.NewServeMux()
56 mux.Handle("/", c)
57 log.Printf("Listening on http://%v...\n", c.BindAddress)
58 if err := http.ListenAndServe(c.BindAddress, mux); err != nil {
59 log.Fatal(err)
60 }
61}
62
63// ServeHTTP implementation.
64func (c *Client) ServeHTTP(w http.ResponseWriter, r *http.Request) {
65 if r.Method != "POST" {
66 log.Println("invalid " + r.Method + " connection from " + r.RemoteAddr)
67 http.NotFound(w, r)
68 return
69 }
70 msg := Message{}
71
72 body, err := io.ReadAll(r.Body)
73 if err != nil {
74 log.Println(err)
75 http.NotFound(w, r)
76 return
77 }
78 defer r.Body.Close()
79 err = json.Unmarshal(body, &msg)
80 if err != nil {
81 log.Println(err)
82 http.NotFound(w, r)
83 return
84 }
85 if msg.Token == "" {
86 log.Println("no token from " + r.RemoteAddr)
87 http.NotFound(w, r)
88 return
89 }
90 msg.ChannelName = "#" + msg.ChannelName
91 if c.Token != "" {
92 if msg.Token != c.Token {
93 if regexp.MustCompile(`[^a-zA-Z0-9]+`).MatchString(msg.Token) {
94 log.Println("invalid token " + msg.Token + " from " + r.RemoteAddr)
95 } else {
96 log.Println("invalid token from " + r.RemoteAddr)
97 }
98 http.NotFound(w, r)
99 return
100 }
101 }
102 c.In <- msg
103}
104
105// Receive returns an incoming message from mattermost outgoing webhooks URL.
106func (c *Client) Receive() Message {
107 var msg Message
108 for msg = range c.In {
109 return msg
110 }
111 return msg
112}
113