Dispatcher, Commands, Filters, Markdown escaping

This commit is contained in:
nefrace 2023-01-22 23:54:54 +03:00
parent 677f28182a
commit e2ba9565d5
8 changed files with 133 additions and 20 deletions

5
bot.go
View File

@ -30,11 +30,8 @@ func (b *bot) Update(u *echo.Update) {
b.lock.Lock()
defer b.lock.Unlock()
newState, err := b.state.Call(upd)
err := b.state.Call(upd)
if err != nil {
upd.LogError("", err, true)
}
if newState != nil {
b.state = newState
}
}

24
command.go Normal file
View File

@ -0,0 +1,24 @@
package nechotron
import "strings"
type Command struct {
Body string
IsAdminOnly bool
}
func NewCommand(body string, isAdminOnly bool) *Command {
return &Command{
Body: body,
IsAdminOnly: isAdminOnly,
}
}
func (c *Command) String() string {
return "/" + c.Body
}
func (c *Command) Param(text string) string {
return strings.TrimPrefix(text, "/"+c.Body+" ")
}
// func HandleCommand(command *Command, handler cmdFunc) (bool, error)

58
dispatcher.go Normal file
View File

@ -0,0 +1,58 @@
package nechotron
import (
"strings"
)
type dispatchHandler func(u *Update) (bool, error)
type updateHandler func(u *Update) error
type commandHandler func(u *UpdateCommand) error
type Dispatcher struct {
handlers []dispatchHandler
}
func NewDispatcher() *Dispatcher {
return &Dispatcher{}
}
func (d *Dispatcher) Run(u *Update) error {
for _, h := range d.handlers {
executed, err := h(u)
if executed {
return err
}
}
return nil
}
func (d *Dispatcher) HandleCommand(command *Command, handler commandHandler) *Dispatcher {
newHandler := func(u *Update) (bool, error) {
if !strings.HasPrefix(u.Text(), command.String()) {
return false, nil
}
if command.IsAdminOnly && !u.IsUserAdmin() {
return false, nil
}
upd := &UpdateCommand{
Update: *u,
Param: command.Param(u.Text()),
}
err := handler(upd)
return true, err
}
d.handlers = append(d.handlers, newHandler)
return d
}
func (d *Dispatcher) HandleFilter(filter FilterFn, handler updateHandler) *Dispatcher {
newHandler := func(u *Update) (bool, error) {
if !filter(u) {
return false, nil
}
err := handler(u)
return true, err
}
d.handlers = append(d.handlers, newHandler)
return d
}

17
filters.go Normal file
View File

@ -0,0 +1,17 @@
package nechotron
import "strings"
type FilterFn func(u *Update) bool
func TextStartsWith(text string) FilterFn {
return func(u *Update) bool {
return strings.HasPrefix(u.Text(), text)
}
}
func TextHas(text string) FilterFn {
return func(u *Update) bool {
return strings.Contains(u.Text(), text)
}
}

14
markdown.go Normal file
View File

@ -0,0 +1,14 @@
package nechotron
import (
"regexp"
"strings"
)
var chars = []string{"_", "*", "\\[", "\\]", "\\(", "\\)", "~", "`", ">", "#", "+", "-", "=", "|", "{", "}", ".", "!"}
var r = strings.Join(chars, "")
var reg = regexp.MustCompile("[" + r + "]+")
func EscapeMd2(s string) string {
return reg.ReplaceAllString(s, "\\$0")
}

View File

@ -24,7 +24,7 @@ func NewTron(token string, defaultState *State) *Nechotron {
}
func (n *Nechotron) newBot(chatID int64) echo.Bot {
a := echo.NewCustomAPI(n.Token, n.ApiServer)
a := echo.NewAPI(n.Token)
// a := echo.NewAPI(n.Token)
me, _ := a.GetMe()
// log.Println("New bot active: ", chatID, me.Result)

View File

@ -9,18 +9,18 @@ import (
type StateData map[string]interface{}
type Runnable interface {
Call(*Update) (Runnable, error)
Call(*Update) error
}
type State struct {
Fn stateFn
}
func (s *State) Call(u *Update) (Runnable, error) {
func (s *State) Call(u *Update) error {
return s.Fn(u)
}
type stateFn func(*Update) (Runnable, error)
type stateFn func(*Update) error
func (d StateData) Set(name string, data interface{}) {
d[name] = data
@ -49,7 +49,7 @@ var EchoState = State{
Fn: EchoFunc,
}
func EchoFunc(u *Update) (Runnable, error) {
func EchoFunc(u *Update) error {
u.AnswerText(u.Text(), &echotron.MessageOptions{})
return nil, nil
return nil
}

View File

@ -13,6 +13,10 @@ type U echotron.Update
var emptyOpts = echotron.MessageOptions{}
type Event interface {
Update
}
type Update struct {
U
Bot *bot
@ -20,6 +24,11 @@ type Update struct {
Ctx context.Context
}
type UpdateCommand struct {
Update
Param string
}
func (u *Update) Upd() *echotron.Update {
return (*echotron.Update)(&u.U)
}
@ -169,17 +178,11 @@ func (u *Update) Entities() []*echotron.MessageEntity {
}
func (u *Update) IsUserAdmin() bool {
ids := []int64{
60441930, // v.rud
327487258, // vika shet
member, err := u.Bot.GetChatMember(u.ChatID(), u.From().ID)
if err != nil {
return false
}
from := u.From()
for i := range ids {
if from.ID == ids[i] {
return true
}
}
return false
return member.Result.Status == "administrator" || member.Result.Status == "creator"
}
func (u *Update) LogError(text string, e error, send bool) {