Browse Source

Handling of message with buttons with blocks to allow for more than 5

pull/1/head
rodley82 1 year ago
parent
commit
156c11fb7e
  1. 33
      config/app.go
  2. BIN
      internal/.DS_Store
  3. 77
      internal/slack/handler.go

33
config/app.go

@ -1,12 +1,13 @@
package config package config
import ( import (
"encoding/csv"
"fmt" "fmt"
"io"
"log" "log"
"os" "os"
"encoding/csv"
"strings" "strings"
"io"
"github.com/joho/godotenv" "github.com/joho/godotenv"
) )
@ -23,6 +24,7 @@ type ActionScript struct {
} }
var Config ConfigEntries var Config ConfigEntries
// var Actions []ActionScript // var Actions []ActionScript
func init() { func init() {
@ -38,6 +40,10 @@ func init() {
Config.SlackAuthToken = os.Getenv("SLACK_AUTH_TOKEN") Config.SlackAuthToken = os.Getenv("SLACK_AUTH_TOKEN")
Config.SlackAppToken = os.Getenv("SLACK_APP_TOKEN") Config.SlackAppToken = os.Getenv("SLACK_APP_TOKEN")
actionsLoaded := initalizeDefinedActions() actionsLoaded := initalizeDefinedActions()
if actionsLoaded == 0 {
log.Println("No actions found in the environment variables")
os.Exit(1)
}
log.Println("Finished loading config. Actions found:", actionsLoaded) log.Println("Finished loading config. Actions found:", actionsLoaded)
log.Println("Actions:", Config.Actions) log.Println("Actions:", Config.Actions)
} }
@ -47,13 +53,17 @@ func init() {
// `Name,Display Name,Path` // `Name,Display Name,Path`
// For example: // For example:
// `poweron,Encender Server,/some/script.sh` // `poweron,Encender Server,/some/script.sh`
//
// Each action name must be unique
func initalizeDefinedActions() int { func initalizeDefinedActions() int {
log.Println("initalizeDefinedActions") log.Println("initalizeDefinedActions")
var count = 1 var count = 0
var value string var value string
var exists bool var exists bool
actionNames := make(map[string]bool)
for { for {
envVarName := fmt.Sprintf("BOT_ACTION_%d", count) envVarName := fmt.Sprintf("BOT_ACTION_%d", count+1)
log.Println("Checking for env var:", envVarName) log.Println("Checking for env var:", envVarName)
value, exists = os.LookupEnv(envVarName) value, exists = os.LookupEnv(envVarName)
if !exists { if !exists {
@ -61,6 +71,21 @@ func initalizeDefinedActions() int {
} }
log.Println("Action found:", value) log.Println("Action found:", value)
action := actionStringToActionScript(value) action := actionStringToActionScript(value)
exists = actionNames[action.Name]
if exists {
log.Println("The action", action.Name, "is already defined.")
os.Exit(1)
} else {
actionNames[action.Name] = true
}
_, err := os.Stat(action.Path)
if err != nil {
log.Println("The specified path", action.Path, " does not exist.", err)
os.Exit(1)
}
// Actions = append(Actions, action) // Actions = append(Actions, action)
Config.Actions = append(Config.Actions, action) Config.Actions = append(Config.Actions, action)
count++ count++

BIN
internal/.DS_Store

Binary file not shown.

77
internal/slack/handler.go

@ -6,9 +6,10 @@ import (
"fmt" "fmt"
"log" "log"
"os" "os"
"time"
"os/exec" "os/exec"
"rodleyserverbot/slack-bot/config" "rodleyserverbot/slack-bot/config"
"time"
"github.com/slack-go/slack" "github.com/slack-go/slack"
"github.com/slack-go/slack/slackevents" "github.com/slack-go/slack/slackevents"
"github.com/slack-go/slack/socketmode" "github.com/slack-go/slack/socketmode"
@ -58,7 +59,9 @@ func Start() {
socketClient.Ack(*event.Request) socketClient.Ack(*event.Request)
switch callback.Type { switch callback.Type {
case slack.InteractionTypeInteractionMessage: case slack.InteractionTypeInteractionMessage:
action := *callback.ActionCallback.AttachmentActions[0] case slack.InteractionTypeMessageAction:
case slack.InteractionTypeBlockActions:
action := *callback.ActionCallback.BlockActions[0]
var output string var output string
var err error var err error
@ -68,12 +71,13 @@ func Start() {
finalMessage := fmt.Sprintf("Resultado*\n```\n%s\n```", output) finalMessage := fmt.Sprintf("Resultado*\n```\n%s\n```", output)
replyToAction(callback.Channel.ID, finalMessage, client) replyToAction(callback.Channel.ID, finalMessage, client)
handleAppMessagedEvent(nil, callback.Channel.ID, client) err := handleAppMessagedEvent(nil, callback.Channel.ID, client)
if err != nil {
log.Println("Error handling event:", err)
}
} else {
log.Println("Error executing action", err)
} }
case slack.InteractionTypeMessageAction:
case slack.InteractionTypeBlockActions:
// See https://api.slack.com/apis/connections/socket-implement#button
case slack.InteractionTypeShortcut: case slack.InteractionTypeShortcut:
case slack.InteractionTypeViewSubmission: case slack.InteractionTypeViewSubmission:
@ -97,6 +101,7 @@ func Start() {
if err != nil { if err != nil {
// Replace with actual err handeling // Replace with actual err handeling
// log.Fatal(err) // log.Fatal(err)
log.Println("Error handling event:", err)
} }
default: default:
} }
@ -120,10 +125,16 @@ func handleEventMessage(event slackevents.EventsAPIEvent, client *slack.Client)
case *slackevents.AppMentionEvent: case *slackevents.AppMentionEvent:
// The application has been mentioned since this Event is a Mention event // The application has been mentioned since this Event is a Mention event
//log.Println("App Mentioned!", ev) //log.Println("App Mentioned!", ev)
handleAppMentionEvent(ev, client) err := handleAppMentionEvent(ev, client)
if err != nil {
return fmt.Errorf("failed to handle app mention event: %w", err)
}
case *slackevents.MessageEvent: case *slackevents.MessageEvent:
//log.Println("MessageEvent!", ev) //log.Println("MessageEvent!", ev)
handleAppMessagedEvent(ev, ev.Channel, client) err := handleAppMessagedEvent(ev, ev.Channel, client)
if err != nil {
return fmt.Errorf("failed to handle app message event: %w", err)
}
default: default:
} }
default: default:
@ -201,24 +212,52 @@ func getAttachmentButtons() []slack.AttachmentAction{
return actions return actions
} }
func buildResponseMessage() (slack.MsgOption, error) {
var blocks []slack.Block
sectionBlock := slack.NewSectionBlock(
slack.NewTextBlockObject("mrkdwn", "Esto es lo que se hacer:", false, false),
nil,
nil,
)
blocks = append(blocks, sectionBlock)
var buttons []slack.BlockElement
// Slack only allows 5 buttons per action block
for i, action := range config.Config.Actions {
if i > 0 && i%5 == 0 {
actionBlock := slack.NewActionBlock("", buttons...)
blocks = append(blocks, actionBlock)
buttons = []slack.BlockElement{}
}
buttonElement := slack.NewButtonBlockElement(action.Name, action.Name, slack.NewTextBlockObject("plain_text", action.DisplayName, false, false))
buttons = append(buttons, buttonElement)
}
if len(buttons) > 0 {
actionBlock := slack.NewActionBlock("", buttons...)
blocks = append(blocks, actionBlock)
}
message := slack.MsgOptionBlocks(blocks...)
return message, nil
}
func handleAppMessagedEvent(event *slackevents.MessageEvent, channel string, client *slack.Client) error { func handleAppMessagedEvent(event *slackevents.MessageEvent, channel string, client *slack.Client) error {
if event != nil && event.BotID != "" { if event != nil && event.BotID != "" {
// We're not interested in messages from ourselves or other bots // We're not interested in messages from ourselves or other bots
return nil return nil
} }
attachment := slack.Attachment{}
var err error var err error
attachment.CallbackID = "server_action" message, err := buildResponseMessage()
// Send a message to the user if err != nil {
attachment.Text = "Por el momento esto es lo que se hacer" return fmt.Errorf("failed to build response message: %w", err)
attachment.Pretext = fmt.Sprintf("Como te puedo ayudar?") }
attachment.Color = "#3d3d3d"
actions := getAttachmentButtons()
attachment.Actions = actions
// Send the message to the channel // Send the message to the channel
// The Channel is available in the event message // The Channel is available in the event message
_, _, err = client.PostMessage(channel, slack.MsgOptionAttachments(attachment)) _, _, err = client.PostMessage(channel, message)
if err != nil { if err != nil {
return fmt.Errorf("failed to post message: %w", err) return fmt.Errorf("failed to post message: %w", err)
} }
@ -234,7 +273,7 @@ func handleAppMentionEvent(event *slackevents.AppMentionEvent, client *slack.Cli
// Send a message to the user // Send a message to the user
attachment.Text = "Por el momento esto es lo que se hacer" attachment.Text = "Por el momento esto es lo que se hacer"
attachment.Pretext = fmt.Sprintf("Como te puedo ayudar?") attachment.Pretext = "Como te puedo ayudar?"
attachment.Color = "#3d3d3d" attachment.Color = "#3d3d3d"
actions := getAttachmentButtons() actions := getAttachmentButtons()
attachment.Actions = actions attachment.Actions = actions

Loading…
Cancel
Save