diff --git a/eventsources/sources/bitbucketserver/start.go b/eventsources/sources/bitbucketserver/start.go index 404db7904c..be3bc986a5 100644 --- a/eventsources/sources/bitbucketserver/start.go +++ b/eventsources/sources/bitbucketserver/start.go @@ -184,67 +184,71 @@ func (el *EventListener) StartListening(ctx context.Context, dispatch func([]byt hookIDs: make(map[string]int), } - logger.Info("retrieving the access token credentials...") - bitbucketToken, err := common.GetSecretFromVolume(bitbucketserverEventSource.AccessToken) - if err != nil { - return errors.Errorf("failed to get bitbucketserver token. err: %+v", err) - } - - if bitbucketserverEventSource.WebhookSecret != nil { - logger.Info("retrieving the webhook secret...") - webhookSecret, err := common.GetSecretFromVolume(bitbucketserverEventSource.WebhookSecret) + if bitbucketserverEventSource.ShouldCreateWebhooks() { + logger.Info("retrieving the access token credentials...") + bitbucketToken, err := common.GetSecretFromVolume(bitbucketserverEventSource.AccessToken) if err != nil { - return errors.Errorf("failed to get bitbucketserver webhook secret. err: %+v", err) + return errors.Errorf("failed to get bitbucketserver token. err: %+v", err) } - router.hookSecret = webhookSecret - } + if bitbucketserverEventSource.WebhookSecret != nil { + logger.Info("retrieving the webhook secret...") + webhookSecret, err := common.GetSecretFromVolume(bitbucketserverEventSource.WebhookSecret) + if err != nil { + return errors.Errorf("failed to get bitbucketserver webhook secret. err: %+v", err) + } + + router.hookSecret = webhookSecret + } - logger.Info("setting up the client to connect to Bitbucket Server...") - bitbucketConfig := bitbucketv1.NewConfiguration(bitbucketserverEventSource.BitbucketServerBaseURL) - bitbucketConfig.AddDefaultHeader("x-atlassian-token", "no-check") - bitbucketConfig.AddDefaultHeader("x-requested-with", "XMLHttpRequest") + logger.Info("setting up the client to connect to Bitbucket Server...") + bitbucketConfig := bitbucketv1.NewConfiguration(bitbucketserverEventSource.BitbucketServerBaseURL) + bitbucketConfig.AddDefaultHeader("x-atlassian-token", "no-check") + bitbucketConfig.AddDefaultHeader("x-requested-with", "XMLHttpRequest") - ctx, cancel := context.WithCancel(ctx) - defer cancel() + ctx, cancel := context.WithCancel(ctx) + defer cancel() - ctx = context.WithValue(ctx, bitbucketv1.ContextAccessToken, bitbucketToken) + ctx = context.WithValue(ctx, bitbucketv1.ContextAccessToken, bitbucketToken) - applyWebhooks := func() { - for _, repo := range bitbucketserverEventSource.GetBitbucketServerRepositories() { - if err = router.applyBitbucketServerWebhook(ctx, bitbucketConfig, repo); err != nil { - logger.Errorw("failed to create/update Bitbucket webhook", - zap.String("project-key", repo.ProjectKey), zap.String("repository-slug", repo.RepositorySlug), zap.Error(err)) - continue - } + applyWebhooks := func() { + for _, repo := range bitbucketserverEventSource.GetBitbucketServerRepositories() { + if err = router.applyBitbucketServerWebhook(ctx, bitbucketConfig, repo); err != nil { + logger.Errorw("failed to create/update Bitbucket webhook", + zap.String("project-key", repo.ProjectKey), zap.String("repository-slug", repo.RepositorySlug), zap.Error(err)) + continue + } - time.Sleep(500 * time.Millisecond) + time.Sleep(500 * time.Millisecond) + } } - } - // When running multiple replicas of the eventsource, they will all try to create the webhook. - // Randomly sleep some time to mitigate the issue. - randomNum, _ := rand.Int(rand.Reader, big.NewInt(int64(2000))) - time.Sleep(time.Duration(randomNum.Int64()) * time.Millisecond) - applyWebhooks() - - go func() { - // Another kind of race conditions might happen when pods do rolling upgrade - new pod starts - // and old pod terminates, if DeleteHookOnFinish is true, the hook will be deleted from Bitbucket. - // This is a workaround to mitigate the race conditions. - logger.Info("starting bitbucket hooks manager daemon") - ticker := time.NewTicker(60 * time.Second) - defer ticker.Stop() - for { - select { - case <-ctx.Done(): - logger.Info("exiting bitbucket hooks manager daemon") - return - case <-ticker.C: - applyWebhooks() + // When running multiple replicas of the eventsource, they will all try to create the webhook. + // Randomly sleep some time to mitigate the issue. + randomNum, _ := rand.Int(rand.Reader, big.NewInt(int64(2000))) + time.Sleep(time.Duration(randomNum.Int64()) * time.Millisecond) + applyWebhooks() + + go func() { + // Another kind of race conditions might happen when pods do rolling upgrade - new pod starts + // and old pod terminates, if DeleteHookOnFinish is true, the hook will be deleted from Bitbucket. + // This is a workaround to mitigate the race conditions. + logger.Info("starting bitbucket hooks manager daemon") + ticker := time.NewTicker(60 * time.Second) + defer ticker.Stop() + for { + select { + case <-ctx.Done(): + logger.Info("exiting bitbucket hooks manager daemon") + return + case <-ticker.C: + applyWebhooks() + } } - } - }() + }() + } else { + logger.Info("access token or webhook configuration were not provided, skipping webhook creation") + } return webhook.ManageRoute(ctx, router, controller, dispatch) } diff --git a/eventsources/sources/bitbucketserver/validate.go b/eventsources/sources/bitbucketserver/validate.go index 5862a859b1..12e073ccb7 100644 --- a/eventsources/sources/bitbucketserver/validate.go +++ b/eventsources/sources/bitbucketserver/validate.go @@ -36,14 +36,11 @@ func validate(eventSource *v1alpha1.BitbucketServerEventSource) error { if eventSource.GetBitbucketServerRepositories() == nil { return fmt.Errorf("at least one repository is required") } - if eventSource.Events == nil { - return fmt.Errorf("events can't be empty") + if eventSource.ShouldCreateWebhooks() && eventSource.Events == nil { + return fmt.Errorf("events must be defined to create a bitbucket server webhook") } if eventSource.BitbucketServerBaseURL == "" { return fmt.Errorf("bitbucket server base url can't be empty") } - if eventSource.AccessToken == nil { - return fmt.Errorf("access token can't be nil") - } return webhook.ValidateWebhookContext(eventSource.Webhook) } diff --git a/pkg/apis/eventsource/v1alpha1/types.go b/pkg/apis/eventsource/v1alpha1/types.go index f209ab19b0..60dde541a2 100644 --- a/pkg/apis/eventsource/v1alpha1/types.go +++ b/pkg/apis/eventsource/v1alpha1/types.go @@ -948,6 +948,10 @@ type BitbucketServerRepository struct { RepositorySlug string `json:"repositorySlug" protobuf:"bytes,2,rep,name=repositorySlug"` } +func (b BitbucketServerEventSource) ShouldCreateWebhooks() bool { + return b.AccessToken != nil && b.Webhook != nil && b.Webhook.URL != "" +} + func (b BitbucketServerEventSource) GetBitbucketServerRepositories() []BitbucketServerRepository { if len(b.Repositories) > 0 { return b.Repositories