From cf1e03ef0e7a0192b9f3687fa9aed4ba68fa4e86 Mon Sep 17 00:00:00 2001 From: Alphyron Date: Sun, 14 Mar 2021 00:22:49 +0100 Subject: [PATCH] :sparkles: Implement the admin groups and broadcast commands --- cli/commands/admingroup.go | 178 ++++++++++++++++++++++++++ cli/commands/broadcast.go | 70 ++++++++++ cli/commands/chatinfo.go | 59 +++++++++ cli/commands/help.go | 18 +-- cli/commands/info.go | 2 +- logic/grouphelperservice.go | 4 + logic/service.go | 1 + main.go | 3 + models/group.go | 20 +-- repository/sql/grouphelprepository.go | 17 ++- 10 files changed, 352 insertions(+), 20 deletions(-) create mode 100644 cli/commands/admingroup.go create mode 100644 cli/commands/broadcast.go create mode 100644 cli/commands/chatinfo.go diff --git a/cli/commands/admingroup.go b/cli/commands/admingroup.go new file mode 100644 index 0000000..c3588fb --- /dev/null +++ b/cli/commands/admingroup.go @@ -0,0 +1,178 @@ +package commands + +import ( + "encoding/json" + "fmt" + "git.dragon-labs.de/alphyron/group_helper/cli" + "git.dragon-labs.de/alphyron/group_helper/logic" + "git.dragon-labs.de/alphyron/group_helper/models" + tgbotapi "github.com/go-telegram-bot-api/telegram-bot-api" + "log" + "strconv" + "strings" +) + +type adminGroupCommand struct { + groupHelperService logic.GroupHelperService +} + +func NewAdminGroupCommand(groupHelperService logic.GroupHelperService) cli.Command { + return &adminGroupCommand{ + groupHelperService: groupHelperService, + } +} + +func (i adminGroupCommand) GetUsage() string { + return "/admin (add/del/list) [groupid]" +} + +func (i adminGroupCommand) GetCommand() string { + return "/admin" +} + +func (i adminGroupCommand) GetDescription() string { + return "Add, Remove or List Admin-Groups" +} + +func (i adminGroupCommand) ExecuteCommand(bot *tgbotapi.BotAPI, update *tgbotapi.Update, group *models.Group) (bool, error) { + message := update.Message.Text + parts := strings.Split(message, " ") + + if len(parts) == 1 { + _, err := bot.Send(tgbotapi.NewMessage(update.Message.Chat.ID, "Wrong usage of this Command:\n"+i.GetUsage())) + return err != nil, err + } + + args := strings.Split(message, " ") + + switch args[1] { + case "list": + + message := fmt.Sprintf("Groups is managed by:\n") + + if group.AdminGroupID != 0 { + adminGroup, err := i.groupHelperService.GetGroupByDBID(group.AdminGroupID) + + if err != nil { + return false, err + } + + chat, err := bot.GetChat(tgbotapi.ChatConfig{ + ChatID: adminGroup.GroupID, + }) + + nameBytes, _ := json.Marshal(chat) + log.Println(string(nameBytes)) + + if err == nil { + message += fmt.Sprintf(" - %d: %s\n", adminGroup.AdminGroupID, chat.Title) + } else { + message += fmt.Sprintf(" - %d: %d\n", adminGroup.AdminGroupID, adminGroup.GroupID) + } + + } else { + message += fmt.Sprintf("There is no Admin Group\n") + } + + message += "\n\nGroups to manage:\n" + + if len(group.ControlledGroups) == 0 { + message += fmt.Sprintf("There are no Groups to Manage") + } else { + for i, controlled := range group.ControlledGroups { + message += fmt.Sprintf("%d.) %v ", i+1, controlled.GroupID) + } + } + + msg := tgbotapi.NewMessage(update.Message.Chat.ID, message) + _, err := bot.Send(msg) + return err != nil, err + case "add": + if len(parts) <= 2 { + _, err := bot.Send(tgbotapi.NewMessage(update.Message.Chat.ID, "Wrong usage of this Command:\n"+i.GetUsage())) + return err != nil, err + } + + groupID := parts[2] + groupIDInt, err := strconv.ParseInt(groupID, 10, 64) + + if err != nil { + return false, err + } + + newGroup, err := i.groupHelperService.GetGroupByID(groupIDInt) + + if err != nil { + return false, err + } + + newGroup.ControlledGroups = append(newGroup.ControlledGroups, group) + + newGroup, err = i.groupHelperService.UpdateGroup(newGroup) + + if err != nil { + return false, err + } + + msg := tgbotapi.NewMessage(update.Message.Chat.ID, "The group is now maintained by the given Group") + _, err = bot.Send(msg) + + if err != nil { + return false, err + } + + msg = tgbotapi.NewMessage(newGroup.GroupID, fmt.Sprintf("This group can now control the following Group:\n"+ + "- %s", update.Message.Chat.Type)) + _, err = bot.Send(msg) + + return err != nil, err + case "del": + + if len(parts) <= 2 { + _, err := bot.Send(tgbotapi.NewMessage(update.Message.Chat.ID, "Wrong usage of this Command:\n"+i.GetUsage())) + return err != nil, err + } + + groupID := parts[2] + groupIDInt, err := strconv.ParseInt(groupID, 10, 64) + + if err != nil { + return false, err + } + + group, err := i.groupHelperService.GetGroupByID(groupIDInt) + + if err != nil { + return false, err + } + + group.AdminGroupID = 0 + newGroup, err := i.groupHelperService.UpdateGroup(group) + + if err != nil { + return false, err + } + + msg := tgbotapi.NewMessage(newGroup.GroupID, "This group is now Maintained by no other Group") + _, err = bot.Send(msg) + + return err != nil, err + + default: + _, err := bot.Send(tgbotapi.NewMessage(update.Message.Chat.ID, "Wrong usage of this Command:\n"+i.GetUsage())) + return err != nil, err + } + return true, nil +} + +func (i adminGroupCommand) AllowChatType(chat *tgbotapi.Chat) bool { + return chat.IsGroup() || chat.IsSuperGroup() +} + +func (i adminGroupCommand) AllowMember(member *tgbotapi.ChatMember) bool { + return member.IsAdministrator() || member.IsCreator() +} + +func (i adminGroupCommand) AllowEveryMember() bool { + return false +} diff --git a/cli/commands/broadcast.go b/cli/commands/broadcast.go new file mode 100644 index 0000000..6136765 --- /dev/null +++ b/cli/commands/broadcast.go @@ -0,0 +1,70 @@ +package commands + +import ( + "fmt" + "git.dragon-labs.de/alphyron/group_helper/cli" + "git.dragon-labs.de/alphyron/group_helper/models" + tgbotapi "github.com/go-telegram-bot-api/telegram-bot-api" + "strconv" + "strings" +) + +type broadcastCommand struct { +} + +func NewBroadcastCommand() cli.Command { + return &broadcastCommand{} +} + +func (b broadcastCommand) GetUsage() string { + return "/broadcast [groupid] [message]" +} + +func (b broadcastCommand) GetCommand() string { + return "/broadcast" +} + +func (b broadcastCommand) GetDescription() string { + return "Send a message to the given group from the bot" +} + +func (b broadcastCommand) ExecuteCommand(bot *tgbotapi.BotAPI, update *tgbotapi.Update, group *models.Group) (bool, error) { + message := update.Message.Text + parts := strings.Split(message, " ") + + if len(parts) <= 2 { + _, err := bot.Send(tgbotapi.NewMessage(update.Message.Chat.ID, "Wrong usage of this Command:\n"+b.GetUsage())) + return err != nil, err + } + + var currentGroup *models.Group + + for _, controlledGroup := range group.ControlledGroups { + if strconv.FormatInt(controlledGroup.GroupID, 10) == parts[1] { + currentGroup = controlledGroup + } + } + + if currentGroup == nil { + message := fmt.Sprintf("There are no Groups to Manage") + msg := tgbotapi.NewMessage(update.Message.Chat.ID, message) + _, err := bot.Send(msg) + return false, err + } + + msg := tgbotapi.NewMessage(currentGroup.GroupID, strings.Join(parts[2:], "")) + _, err := bot.Send(msg) + return err == nil, err +} + +func (b broadcastCommand) AllowChatType(_ *tgbotapi.Chat) bool { + return true +} + +func (b broadcastCommand) AllowMember(member *tgbotapi.ChatMember) bool { + return member.IsAdministrator() || member.IsCreator() +} + +func (b broadcastCommand) AllowEveryMember() bool { + return false +} diff --git a/cli/commands/chatinfo.go b/cli/commands/chatinfo.go new file mode 100644 index 0000000..edf7b3c --- /dev/null +++ b/cli/commands/chatinfo.go @@ -0,0 +1,59 @@ +package commands + +import ( + "fmt" + "git.dragon-labs.de/alphyron/group_helper/cli" + "git.dragon-labs.de/alphyron/group_helper/models" + tgbotapi "github.com/go-telegram-bot-api/telegram-bot-api" +) + +type chatInfoCommand struct { +} + +func NewChatInfoCommand() cli.Command { + return &chatInfoCommand{} +} + +func (i chatInfoCommand) GetUsage() string { + return "/chat\\_info" +} + +func (i chatInfoCommand) GetCommand() string { + return "/chat_info" +} + +func (i chatInfoCommand) GetDescription() string { + return "Return just some simple Telegram Information about this group" +} + +func (i chatInfoCommand) ExecuteCommand(bot *tgbotapi.BotAPI, update *tgbotapi.Update, group *models.Group) (bool, error) { + infoMessage := fmt.Sprintf("General Information to this Group\n"+ + "Group ID: %d\n"+ + "Group Name: %s\n"+ + "Description: %s\n"+ + "Group Type: %s\n"+ + "===============================\n", + update.Message.Chat.ID, + update.Message.Chat.Title, + update.Message.Chat.Description, + update.Message.Chat.Type) + + msg := tgbotapi.NewMessage(update.Message.Chat.ID, infoMessage) + msg.ParseMode = "Markdown" + + _, err := bot.Send(msg) + + return err == nil, nil +} + +func (i chatInfoCommand) AllowChatType(*tgbotapi.Chat) bool { + return true +} + +func (i chatInfoCommand) AllowMember(*tgbotapi.ChatMember) bool { + return i.AllowEveryMember() +} + +func (i chatInfoCommand) AllowEveryMember() bool { + return true +} diff --git a/cli/commands/help.go b/cli/commands/help.go index 50af5c7..790e19f 100644 --- a/cli/commands/help.go +++ b/cli/commands/help.go @@ -5,7 +5,7 @@ import ( "git.dragon-labs.de/alphyron/group_helper/cli" "git.dragon-labs.de/alphyron/group_helper/models" tgbotapi "github.com/go-telegram-bot-api/telegram-bot-api" - "strings" + "log" ) type helpCommand struct { @@ -29,26 +29,26 @@ func (h helpCommand) GetDescription() string { } func (h helpCommand) ExecuteCommand(bot *tgbotapi.BotAPI, update *tgbotapi.Update, group *models.Group) (bool, error) { - var builder strings.Builder - builder.WriteString("All supported Commands:\n") + log.Println("test1") + + messages := "All supported Commands:" for _, cmd := range h.commandManager.Commands { - builder.WriteString(fmt.Sprintf("%s - %s\n", cmd.GetUsage(), cmd.GetDescription())) + messages += fmt.Sprintf("\n%s - %s", cmd.GetUsage(), cmd.GetDescription()) } - - msg := tgbotapi.NewMessage(update.Message.Chat.ID, builder.String()) + msg := tgbotapi.NewMessage(update.Message.Chat.ID, messages) msg.ParseMode = "Markdown" _, err := bot.Send(msg) - return err == nil, nil + return err == nil, err } -func (h helpCommand) AllowChatType(chat *tgbotapi.Chat) bool { +func (h helpCommand) AllowChatType(_ *tgbotapi.Chat) bool { return true } -func (h helpCommand) AllowMember(member *tgbotapi.ChatMember) bool { +func (h helpCommand) AllowMember(_ *tgbotapi.ChatMember) bool { return true } diff --git a/cli/commands/info.go b/cli/commands/info.go index a3f817c..ee247e7 100644 --- a/cli/commands/info.go +++ b/cli/commands/info.go @@ -30,7 +30,7 @@ func (i infoCommand) ExecuteCommand(bot *tgbotapi.BotAPI, update *tgbotapi.Updat "General Information to this Bot\n" + "===============================\n" + "Developer: @Alphyron\n" + - "Version: 2.0.0\n" + + "Version: 2.1.0\n" + "Git: [Gitea Repository](https://git.dragon-labs.de/alphyron/group_assistant)\n" + "===============================" diff --git a/logic/grouphelperservice.go b/logic/grouphelperservice.go index fb2b010..721bb3d 100644 --- a/logic/grouphelperservice.go +++ b/logic/grouphelperservice.go @@ -106,3 +106,7 @@ func (g groupHelperService) ListGroupUsers(group *models.Group) ([]*models.User, func (g groupHelperService) ListUsers() ([]*models.User, error) { return g.groupHelperRepo.ListUsers() } + +func (g groupHelperService) GetGroupByDBID(i uint64) (*models.Group, error) { + return g.groupHelperRepo.GetGroupByDBID(i) +} diff --git a/logic/service.go b/logic/service.go index 7ae3057..e6798c5 100644 --- a/logic/service.go +++ b/logic/service.go @@ -9,6 +9,7 @@ type GroupHelperService interface { UpdateGroup(*models.Group) (*models.Group, error) GetGroupByID(int64) (*models.Group, error) + GetGroupByDBID(uint64) (*models.Group, error) GetGroupDatabaseSize(*models.Group) (int, error) CreateUser(*models.User) (*models.User, error) diff --git a/main.go b/main.go index 2d7910e..f2049ae 100644 --- a/main.go +++ b/main.go @@ -103,6 +103,9 @@ func InitialCommandManager(bot *tgbotapi.BotAPI, service logic.GroupHelperServic cm.RegisterCommand(commands.NewVerifiedMessage(service)) cm.RegisterCommand(commands.NewToggleOnlineCheckCommand(service)) cm.RegisterCommand(commands.NewToggleWritingForbidCommand(service)) + cm.RegisterCommand(commands.NewChatInfoCommand()) + cm.RegisterCommand(commands.NewAdminGroupCommand(service)) + cm.RegisterCommand(commands.NewBroadcastCommand()) return cm } diff --git a/models/group.go b/models/group.go index 333d66e..fbf636c 100644 --- a/models/group.go +++ b/models/group.go @@ -1,17 +1,19 @@ package models type Group struct { - ID uint `gorm:"primary_key"` + ID uint64 `gorm:"primary_key"` GroupID int64 Size int - UserJoinMessage string `gorm:"column:msg_user_join;type:text"` - UserVerifiedMessage string `gorm:"column:msg_user_verified;type:text"` - UserLeaveMessage string `gorm:"column:msg_user_leave;type:text"` - UserKickMessage string `gorm:"column:msg_user_kick;type:text"` - ForbidWriting bool `gorm:"column:forbid_writing"` - OnlineCheck bool `gorm:"column:online_check"` - KickCooldown int `gorm:"column:kick_cooldown"` - Users []*User `gorm:"many2many:GroupUser;"` + UserJoinMessage string `gorm:"column:msg_user_join;type:text"` + UserVerifiedMessage string `gorm:"column:msg_user_verified;type:text"` + UserLeaveMessage string `gorm:"column:msg_user_leave;type:text"` + UserKickMessage string `gorm:"column:msg_user_kick;type:text"` + ForbidWriting bool `gorm:"column:forbid_writing"` + OnlineCheck bool `gorm:"column:online_check"` + KickCooldown int `gorm:"column:kick_cooldown"` + Users []*User `gorm:"many2many:GroupUser;"` + AdminGroupID uint64 `gorm:"column:admin_group_id"` + ControlledGroups []*Group `gorm:"foreignkey:admin_group_id"` } func (Group) TableName() string { diff --git a/repository/sql/grouphelprepository.go b/repository/sql/grouphelprepository.go index ad47e9a..01acbfd 100644 --- a/repository/sql/grouphelprepository.go +++ b/repository/sql/grouphelprepository.go @@ -94,7 +94,7 @@ func (g groupHelperRepository) GetGroupByID(id int64) (*models.Group, error) { defaultGroup.FillDefaultValues() defaultGroup.GroupID = id - err := g.Conn.Where("group_id = ?", id).First(&group) + err := g.Conn.Set("gorm:auto_preload", true).Where("group_id = ?", id).First(&group) if err.RecordNotFound() { return g.CreateGroup(defaultGroup) @@ -206,3 +206,18 @@ func (g groupHelperRepository) ListUsers() ([]*models.User, error) { func (g groupHelperRepository) InitRepository() error { return g.Conn.AutoMigrate(models.Group{}, models.User{}).Error } + +func (g groupHelperRepository) GetGroupByDBID(id uint64) (*models.Group, error) { + var group models.Group + + defaultGroup := &models.Group{} + defaultGroup.FillDefaultValues() + defaultGroup.ID = id + + err := g.Conn.Set("gorm:auto_preload", true).Where("id = ?", id).First(&group) + + if err.RecordNotFound() { + return g.CreateGroup(defaultGroup) + } + return &group, err.Error +}