all repos — paprika @ 25de5b6c6af4b418eb4cb6ef74eb26540f50ddd6

go rewrite of taigabot

plugins/plugins.go (view raw)

 1package plugins
 2
 3import (
 4	"errors"
 5	"fmt"
 6	"strings"
 7
 8	"gopkg.in/irc.v3"
 9)
10
11type Plugin interface {
12	Triggers() []string
13	Execute(m *irc.Message) (string, error)
14}
15
16var Plugins = make(map[string]Plugin)
17
18func Register(p Plugin) {
19	for _, t := range p.Triggers() {
20		Plugins[t] = p
21	}
22}
23
24// This Error is used to signal a NAK so other plugins
25// can attempt to parse the result
26// This is useful for broad prefix matching or future regexp
27// functions, other special errors may need defining
28// to determin priority or to "concatenate" output.
29var NoReply = errors.New("No Reply")
30
31type Flag int
32
33type ReplyT struct {
34	Flags Flag
35}
36
37const (
38	Notice Flag = 1 << iota
39	DirectMessage
40)
41
42var AllFlags = [...]Flag{Notice, DirectMessage}
43
44func (f Flag) String() string {
45	switch f {
46	case Notice:
47		return "Notice"
48	case DirectMessage:
49		return "DM"
50	default:
51		return fmt.Sprintf("Invalid:%d", f)
52	}
53}
54
55func NewReplyT(flags Flag) *ReplyT {
56	return &ReplyT{Flags: flags}
57}
58
59func (r *ReplyT) ApplyFlags(m *irc.Message) {
60	for _, flag := range AllFlags {
61		if r.Flags & flag != 0 {
62			switch flag {
63			case Notice:
64				m.Command = "NOTICE"
65			case DirectMessage:
66				m.Params[0] = m.Name
67			}
68		}
69	}
70}
71
72func (r *ReplyT) Error() string {
73	var reply strings.Builder
74	for _, flag := range AllFlags {
75		if r.Flags & flag != 0 {
76			reply.WriteString(flag.String())
77		}
78	}
79	return reply.String()
80}
81
82func IsReplyT(e error) bool {
83	r := &ReplyT{}
84	return errors.As(e, &r)
85}
86
87// Checks for triggers in a message and executes its
88// corresponding plugin, returning the response/error.
89func ProcessTrigger(m *irc.Message) (string, error) {
90	for trigger, plugin := range Plugins {
91		if strings.HasPrefix(m.Trailing(), trigger) {
92			response, err := plugin.Execute(m)
93			if !errors.Is(err, NoReply) {
94				return response, err
95			}
96		}
97	}
98	return "", NoReply // No plugin matched, so we need to Ignore.
99}