package discord import ( "context" "fmt" "gitea.dwysokinski.me/twhelp/dcbot/internal/domain" "gitea.dwysokinski.me/twhelp/dcbot/internal/twhelp" "github.com/bwmarrin/discordgo" ) type GroupService interface { Create(ctx context.Context, params domain.CreateGroupParams) (domain.Group, error) SetTWServer(ctx context.Context, id, versionCode, serverKey string) (domain.Group, error) SetChannelGains(ctx context.Context, id, channel string) (domain.Group, error) SetChannelLosses(ctx context.Context, id, channel string) (domain.Group, error) List(ctx context.Context, params domain.ListGroupsParams) ([]domain.Group, error) } type TWHelpClient interface { ListVersions(ctx context.Context) ([]twhelp.Version, error) } type Bot struct { s *discordgo.Session groupSvc GroupService client TWHelpClient } func NewBot(token string, groupSvc GroupService, client TWHelpClient) (*Bot, error) { s, err := discordgo.New("Bot " + token) if err != nil { return nil, fmt.Errorf("discordgo.New: %w", err) } if err = s.Open(); err != nil { return nil, fmt.Errorf("s.Open: %w", err) } b := &Bot{s: s, groupSvc: groupSvc, client: client} if err = b.registerCommands(); err != nil { _ = s.Close() return nil, fmt.Errorf("couldn't register commands: %w", err) } return b, nil } func (b *Bot) registerCommands() error { if err := b.registerCommand(&groupCommand{svc: b.groupSvc, client: b.client}); err != nil { return err } return nil } type command interface { name() string register(s *discordgo.Session) error } func (b *Bot) registerCommand(cmd command) error { if err := cmd.register(b.s); err != nil { return fmt.Errorf("couldn't register command '%s': %w", cmd.name(), err) } return nil } func (b *Bot) Close() error { return b.s.Close() }