From 45f4fa6466b73fd93e9d2a61bb2b13cfa111d022 Mon Sep 17 00:00:00 2001 From: Huseyin BABAL Date: Tue, 18 Jul 2023 10:59:42 +0300 Subject: [PATCH 1/4] add human friendly error messages --- cmd/botkube-agent/main.go | 27 ++++++++++++++++++++++++--- 1 file changed, 24 insertions(+), 3 deletions(-) diff --git a/cmd/botkube-agent/main.go b/cmd/botkube-agent/main.go index 37a431ffe..51aec9a89 100644 --- a/cmd/botkube-agent/main.go +++ b/cmd/botkube-agent/main.go @@ -5,6 +5,7 @@ import ( "errors" "fmt" "net/http" + "strings" "time" "github.com/google/go-github/v44/github" @@ -19,7 +20,7 @@ import ( "k8s.io/client-go/discovery/cached/memory" "k8s.io/client-go/kubernetes" "k8s.io/client-go/rest" - "k8s.io/utils/strings" + k8sStrings "k8s.io/utils/strings" "sigs.k8s.io/controller-runtime/pkg/manager/signals" "github.com/kubeshop/botkube/internal/analytics" @@ -60,6 +61,13 @@ const ( reportHeartbeatMaxRetries = 30 ) +var humanizedErrorMessages = map[string]string{ + "not_in_channel": "BotKube is not invited to channel", + "invalid_auth": "Invalid Slack credentials", + "HTTP 401 Unauthorized": "Invalid Discord credentials", + "HTTP 404 Not Found": "Discord channel not found", +} + func main() { // Set up context ctx := signals.SetupSignalHandler() @@ -469,7 +477,7 @@ func getAnalyticsReporter(disableAnalytics bool, logger logrus.FieldLogger) (ana } wrappedLogger := logger.WithField(componentLogFieldKey, "Analytics reporter") - wrappedLogger.Infof("Using API Key starting with %q...", strings.ShortenString(analytics.APIKey, printAPIKeyCharCount)) + wrappedLogger.Infof("Using API Key starting with %q...", k8sStrings.ShortenString(analytics.APIKey, printAPIKeyCharCount)) segmentCli, err := segment.NewWithConfig(analytics.APIKey, segment.Config{ Logger: analytics.NewSegmentLoggerAdapter(wrappedLogger), Verbose: false, @@ -515,7 +523,7 @@ func reportFatalErrFn(logger logrus.FieldLogger, reporter analytics.Reporter, st logger.Errorf("while reporting fatal error: %s", err.Error()) } - if err := status.ReportDeploymentFailure(ctxTimeout, err.Error()); err != nil { + if err := status.ReportDeploymentFailure(ctxTimeout, humanFriendlyError(err)); err != nil { logger.Errorf("while reporting deployment failure: %s", err.Error()) } @@ -561,3 +569,16 @@ func findVersions(cli *kubernetes.Clientset) (string, error) { return fmt.Sprintf("K8s Server Version: %s\nBotkube version: %s", k8sVer.String(), botkubeVersion), nil } + +func humanFriendlyError(err error) string { + if err == nil { + return "" + } + for k, v := range humanizedErrorMessages { + if strings.Contains(err.Error(), k) { + return v + } + } + + return err.Error() +} From 02bd2fb0fdfbb652cb4bda446b7f53ea08533fcc Mon Sep 17 00:00:00 2001 From: Huseyin BABAL Date: Wed, 19 Jul 2023 14:49:01 +0300 Subject: [PATCH 2/4] added more messages for discord and mm --- cmd/botkube-agent/main.go | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/cmd/botkube-agent/main.go b/cmd/botkube-agent/main.go index 51aec9a89..61b45f1e7 100644 --- a/cmd/botkube-agent/main.go +++ b/cmd/botkube-agent/main.go @@ -61,11 +61,16 @@ const ( reportHeartbeatMaxRetries = 30 ) -var humanizedErrorMessages = map[string]string{ +var humanFriendlyErrorMessages = map[string]string{ "not_in_channel": "BotKube is not invited to channel", "invalid_auth": "Invalid Slack credentials", + "channel_not_found": "Slack channel not found", "HTTP 401 Unauthorized": "Invalid Discord credentials", "HTTP 404 Not Found": "Discord channel not found", + "Invalid or expired session, please login again": "Invalid Mattermost token", + "while getting bot user ID: user with name": "Mattermost bot user not found", + "while creating Mattermost bot: team:": "Mattermost team not found", + "while creating Mattermost bot: while producing channels configuration map by ID: while getting channel by name": "Mattermost channel not found", } func main() { @@ -523,7 +528,7 @@ func reportFatalErrFn(logger logrus.FieldLogger, reporter analytics.Reporter, st logger.Errorf("while reporting fatal error: %s", err.Error()) } - if err := status.ReportDeploymentFailure(ctxTimeout, humanFriendlyError(err)); err != nil { + if err := status.ReportDeploymentFailure(ctxTimeout, humanFriendlyError(wrappedErr, err)); err != nil { logger.Errorf("while reporting deployment failure: %s", err.Error()) } @@ -570,12 +575,9 @@ func findVersions(cli *kubernetes.Clientset) (string, error) { return fmt.Sprintf("K8s Server Version: %s\nBotkube version: %s", k8sVer.String(), botkubeVersion), nil } -func humanFriendlyError(err error) string { - if err == nil { - return "" - } - for k, v := range humanizedErrorMessages { - if strings.Contains(err.Error(), k) { +func humanFriendlyError(wrappedErr, err error) string { + for k, v := range humanFriendlyErrorMessages { + if strings.Contains(wrappedErr.Error(), k) { return v } } From d42a591d7b118ee17e9987c04c838df03c92fed6 Mon Sep 17 00:00:00 2001 From: Huseyin BABAL Date: Fri, 21 Jul 2023 13:49:06 +0300 Subject: [PATCH 3/4] detailed error messages added to bots --- cmd/botkube-agent/main.go | 29 +++-------------------------- pkg/bot/discord.go | 19 +++++++++++++++++-- pkg/bot/slack_shared.go | 12 ++++++++++++ pkg/bot/slack_socket.go | 4 ++-- 4 files changed, 34 insertions(+), 30 deletions(-) diff --git a/cmd/botkube-agent/main.go b/cmd/botkube-agent/main.go index 61b45f1e7..37a431ffe 100644 --- a/cmd/botkube-agent/main.go +++ b/cmd/botkube-agent/main.go @@ -5,7 +5,6 @@ import ( "errors" "fmt" "net/http" - "strings" "time" "github.com/google/go-github/v44/github" @@ -20,7 +19,7 @@ import ( "k8s.io/client-go/discovery/cached/memory" "k8s.io/client-go/kubernetes" "k8s.io/client-go/rest" - k8sStrings "k8s.io/utils/strings" + "k8s.io/utils/strings" "sigs.k8s.io/controller-runtime/pkg/manager/signals" "github.com/kubeshop/botkube/internal/analytics" @@ -61,18 +60,6 @@ const ( reportHeartbeatMaxRetries = 30 ) -var humanFriendlyErrorMessages = map[string]string{ - "not_in_channel": "BotKube is not invited to channel", - "invalid_auth": "Invalid Slack credentials", - "channel_not_found": "Slack channel not found", - "HTTP 401 Unauthorized": "Invalid Discord credentials", - "HTTP 404 Not Found": "Discord channel not found", - "Invalid or expired session, please login again": "Invalid Mattermost token", - "while getting bot user ID: user with name": "Mattermost bot user not found", - "while creating Mattermost bot: team:": "Mattermost team not found", - "while creating Mattermost bot: while producing channels configuration map by ID: while getting channel by name": "Mattermost channel not found", -} - func main() { // Set up context ctx := signals.SetupSignalHandler() @@ -482,7 +469,7 @@ func getAnalyticsReporter(disableAnalytics bool, logger logrus.FieldLogger) (ana } wrappedLogger := logger.WithField(componentLogFieldKey, "Analytics reporter") - wrappedLogger.Infof("Using API Key starting with %q...", k8sStrings.ShortenString(analytics.APIKey, printAPIKeyCharCount)) + wrappedLogger.Infof("Using API Key starting with %q...", strings.ShortenString(analytics.APIKey, printAPIKeyCharCount)) segmentCli, err := segment.NewWithConfig(analytics.APIKey, segment.Config{ Logger: analytics.NewSegmentLoggerAdapter(wrappedLogger), Verbose: false, @@ -528,7 +515,7 @@ func reportFatalErrFn(logger logrus.FieldLogger, reporter analytics.Reporter, st logger.Errorf("while reporting fatal error: %s", err.Error()) } - if err := status.ReportDeploymentFailure(ctxTimeout, humanFriendlyError(wrappedErr, err)); err != nil { + if err := status.ReportDeploymentFailure(ctxTimeout, err.Error()); err != nil { logger.Errorf("while reporting deployment failure: %s", err.Error()) } @@ -574,13 +561,3 @@ func findVersions(cli *kubernetes.Clientset) (string, error) { return fmt.Sprintf("K8s Server Version: %s\nBotkube version: %s", k8sVer.String(), botkubeVersion), nil } - -func humanFriendlyError(wrappedErr, err error) string { - for k, v := range humanFriendlyErrorMessages { - if strings.Contains(wrappedErr.Error(), k) { - return v - } - } - - return err.Error() -} diff --git a/pkg/bot/discord.go b/pkg/bot/discord.go index 89c81717e..c81eee060 100644 --- a/pkg/bot/discord.go +++ b/pkg/bot/discord.go @@ -4,6 +4,7 @@ import ( "context" "errors" "fmt" + "net/http" "regexp" "strings" "sync" @@ -269,7 +270,7 @@ func (b *Discord) send(channelID string, resp interactive.CoreMessage) error { return fmt.Errorf("while formatting message: %w", err) } if _, err := b.api.ChannelMessageSendComplex(channelID, discordMsg); err != nil { - return fmt.Errorf("while sending message: %w", err) + return fmt.Errorf("while sending message: %w", discordError(err, channelID)) } b.log.Debugf("Message successfully sent to channel %q", channelID) @@ -355,7 +356,7 @@ func discordChannelsConfigFrom(log logrus.FieldLogger, api *discordgo.Session, c channelData, err := api.Channel(channCfg.Identifier()) if err != nil { - return nil, fmt.Errorf("while getting channel name for ID %q: %w", channCfg.Identifier(), err) + return nil, fmt.Errorf("while getting channel name for ID %q: %w", channCfg.Identifier(), discordError(err, channCfg.Identifier())) } res[channCfg.Identifier()] = channelConfigByID{ @@ -377,3 +378,17 @@ func discordBotMentionRegex(botID string) (*regexp.Regexp, error) { return botMentionRegex, nil } + +func discordError(err error, channel string) error { + switch err.(type) { + case *discordgo.RESTError: + restErr := err.(*discordgo.RESTError) + switch restErr.Response.StatusCode { + case http.StatusUnauthorized: + err = errors.New("invalid discord credentials") + case http.StatusNotFound: + err = fmt.Errorf("channel %q not found", channel) + } + } + return err +} diff --git a/pkg/bot/slack_shared.go b/pkg/bot/slack_shared.go index d98432715..51c5006db 100644 --- a/pkg/bot/slack_shared.go +++ b/pkg/bot/slack_shared.go @@ -42,6 +42,18 @@ func slackBotMentionRegex(botID string) (*regexp.Regexp, error) { return botMentionRegex, nil } +func slackError(err error, channel string) error { + switch err.Error() { + case "channel_not_found": + err = fmt.Errorf("channel %q not found", channel) + case "not_in_channel": + err = fmt.Errorf("botkube is not in channel %q", channel) + case "invalid_auth": + err = fmt.Errorf("invalid slack credentials") + } + return err +} + // slackMessage contains message details to execute command and send back the result type slackMessage struct { Text string diff --git a/pkg/bot/slack_socket.go b/pkg/bot/slack_socket.go index 0bc37b8c0..8355139de 100644 --- a/pkg/bot/slack_socket.go +++ b/pkg/bot/slack_socket.go @@ -60,7 +60,7 @@ func NewSocketSlack(log logrus.FieldLogger, commGroupName string, cfg config.Soc authResp, err := client.AuthTest() if err != nil { - return nil, fmt.Errorf("while testing the ability to do auth Slack request: %w", err) + return nil, fmt.Errorf("while testing the ability to do auth Slack request: %w", slackError(err, "")) } botID := authResp.UserID @@ -422,7 +422,7 @@ func (b *SocketSlack) send(ctx context.Context, event slackMessage, resp interac } } else { if _, _, err := b.client.PostMessageContext(ctx, event.Channel, options...); err != nil { - return fmt.Errorf("while posting Slack message: %w", err) + return fmt.Errorf("while posting Slack message: %w", slackError(err, event.Channel)) } } From b7f7bc3c4ae48305b76903f6e8d2c81d91b5ff49 Mon Sep 17 00:00:00 2001 From: Huseyin BABAL Date: Tue, 25 Jul 2023 18:52:13 +0300 Subject: [PATCH 4/4] lint fix --- pkg/bot/discord.go | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/pkg/bot/discord.go b/pkg/bot/discord.go index c81eee060..e6dfdeec5 100644 --- a/pkg/bot/discord.go +++ b/pkg/bot/discord.go @@ -380,14 +380,13 @@ func discordBotMentionRegex(botID string) (*regexp.Regexp, error) { } func discordError(err error, channel string) error { - switch err.(type) { + switch err := err.(type) { case *discordgo.RESTError: - restErr := err.(*discordgo.RESTError) - switch restErr.Response.StatusCode { + switch err.Response.StatusCode { case http.StatusUnauthorized: - err = errors.New("invalid discord credentials") + return errors.New("invalid discord credentials") case http.StatusNotFound: - err = fmt.Errorf("channel %q not found", channel) + return fmt.Errorf("channel %q not found", channel) } } return err