From 2d9b230f6ff54d11df3e6eb269f555fb59b6f88d Mon Sep 17 00:00:00 2001 From: Ken Kaizu Date: Sat, 3 Aug 2024 09:52:49 +0900 Subject: [PATCH] feat: skip comment when no change flag (#24) --- pkg/cli/app.go | 4 ++++ pkg/cli/var.go | 4 ++++ pkg/config/config.go | 5 +++-- pkg/controller/controller.go | 1 + pkg/notifier/gitlab/client.go | 1 + pkg/notifier/gitlab/notify.go | 5 +++++ pkg/notifier/gitlab/notify_test.go | 27 +++++++++++++++++++++++++++ 7 files changed, 45 insertions(+), 2 deletions(-) diff --git a/pkg/cli/app.go b/pkg/cli/app.go index 51319ae..d466478 100644 --- a/pkg/cli/app.go +++ b/pkg/cli/app.go @@ -39,6 +39,10 @@ func New(flags *LDFlags) *cli.App { Name: "patch", Usage: "update an existing comment instead of creating a new comment. If there is no existing comment, a new comment is created.", }, + &cli.BoolFlag{ + Name: "skip-no-changes", + Usage: "If there is no change tfcmt updates a label but doesn't post a comment", + }, }, }, { diff --git a/pkg/cli/var.go b/pkg/cli/var.go index 19c08e9..4bed1f0 100644 --- a/pkg/cli/var.go +++ b/pkg/cli/var.go @@ -44,6 +44,10 @@ func parseOpts(ctx *cli.Context, cfg *config.Config) error { cfg.CI.Link = buildURL } + if ctx.IsSet("skip-no-changes") { + cfg.Terraform.Plan.WhenNoChanges.DisableComment = ctx.Bool("skip-no-changes") + } + vars := ctx.StringSlice("var") vm := make(map[string]string, len(vars)) if err := parseVarOpts(vars, vm); err != nil { diff --git a/pkg/config/config.go b/pkg/config/config.go index a7f6d5e..5348c97 100644 --- a/pkg/config/config.go +++ b/pkg/config/config.go @@ -70,8 +70,9 @@ type WhenDestroy struct { // WhenNoChanges is a configuration to add a label when the plan result contains no change type WhenNoChanges struct { - Label string - Color string `yaml:"label_color"` + Label string + Color string `yaml:"label_color"` + DisableComment bool `yaml:"disable_comment"` } // WhenPlanError is a configuration to notify the plan result returns an error diff --git a/pkg/controller/controller.go b/pkg/controller/controller.go index 3dc4eed..5b76951 100644 --- a/pkg/controller/controller.go +++ b/pkg/controller/controller.go @@ -188,6 +188,7 @@ func (ctrl *Controller) getNotifier(ctx context.Context) (notifier.Notifier, err EmbeddedVarNames: ctrl.Config.EmbeddedVarNames, Templates: ctrl.Config.Templates, Patch: ctrl.Config.PlanPatch, + SkipNoChanges: ctrl.Config.Terraform.Plan.WhenNoChanges.DisableComment, }) if err != nil { return nil, err diff --git a/pkg/notifier/gitlab/client.go b/pkg/notifier/gitlab/client.go index 66da861..c874254 100644 --- a/pkg/notifier/gitlab/client.go +++ b/pkg/notifier/gitlab/client.go @@ -49,6 +49,7 @@ type Config struct { Templates map[string]string UseRawOutput bool Patch bool + SkipNoChanges bool } // MergeRequest represents GitLab Merge Request metadata diff --git a/pkg/notifier/gitlab/notify.go b/pkg/notifier/gitlab/notify.go index e066c59..f2e3e31 100644 --- a/pkg/notifier/gitlab/notify.go +++ b/pkg/notifier/gitlab/notify.go @@ -89,6 +89,11 @@ func (g *NotifyService) Notify(param notifier.ParamExec) (int, error) { //nolint logE.WithField("size", len(comments)).Debug("list comments") } + if result.HasNoChanges && result.Warning == "" && len(errMsgs) == 0 && cfg.SkipNoChanges { + logE.Debug("skip posting a comment because there is no change") + return result.ExitCode, nil + } + logE.Debug("create a comment") if err := g.client.Comment.Post(body, PostOptions{ diff --git a/pkg/notifier/gitlab/notify_test.go b/pkg/notifier/gitlab/notify_test.go index e93d35d..86fccbf 100644 --- a/pkg/notifier/gitlab/notify_test.go +++ b/pkg/notifier/gitlab/notify_test.go @@ -207,6 +207,33 @@ func TestNotifyNotify(t *testing.T) { //nolint:maintidx ok: true, exitCode: 0, }, + { + name: "valid with no change, then skip comment", + createMockGitLabAPI: func(ctrl *gomock.Controller) *gitlabmock.MockAPI { + api := gitlabmock.NewMockAPI(ctrl) + api.EXPECT().CreateMergeRequestNote(gomock.Any(), gomock.Any()).Times(0) + return api + }, + config: Config{ + Token: "token", + NameSpace: "namespace", + Project: "project", + MR: MergeRequest{ + Revision: "", + Number: 1, + }, + Parser: terraform.NewPlanParser(), + Template: terraform.NewPlanTemplate(terraform.DefaultPlanTemplate), + ParseErrorTemplate: terraform.NewPlanParseErrorTemplate(terraform.DefaultPlanTemplate), + SkipNoChanges: true, + }, + paramExec: notifier.ParamExec{ + CombinedOutput: "No changes. Infrastructure is up-to-date.", + ExitCode: 0, + }, + ok: true, + exitCode: 0, + }, { name: "valid, contains destroy, but not to notify", createMockGitLabAPI: func(ctrl *gomock.Controller) *gitlabmock.MockAPI {