public async Task OnOpenedHandlerAsync(PullRequestOpenedNotification notification) { Guard.AgainstNullArgument <PullRequestOpenedNotification>(nameof(notification), notification); await this.AddBotAsReviewer(notification); if (await this.HasMergeConflicts(notification.PullRequest)) { // update the pr with needs_work await this.bitbucketClient.SetReviewerStatus(notification.PullRequest, new BitbucketParticipant() { User = new BitbucketUser() { Name = this.integrations.Bitbucket.Credentials.UserName, Slug = this.integrations.Bitbucket.Credentials.UserName }, IsApproved = false, Status = BitbucketStatus.NeedsWork }); // comment with, please fix merge conflicts and add steps for fix await this.bitbucketClient.AddComment(notification.PullRequest, new BitbucketComment() { Text = string.Format(Resources.PullRequest_MergeConflictResolution, notification.PullRequest.ToReference.DisplayName, notification.PullRequest.FromReference.DisplayName) }); //return; } // check other criteria FishEyeChangesets Changesets = await this.FindReviewsByCommits(notification.PullRequest); // check all commits are associated with a review await this.AreAllCommitsReviewed(notification.PullRequest, Changesets); // check for closed review // check for 2 reviewers in complete status await this.ValidateReviewConditions(notification.PullRequest, Changesets); }
private async Task ValidateReviewConditions(BitbucketPullRequest pullRequest, FishEyeChangesets changesets) { // find distinctive reviews from changesets List <FishEyeReview> FishEyeReviews = new List <FishEyeReview>(); List <Problem> Problems; foreach (FishEyeChangeset Changeset in changesets.Changesets) { FishEyeReviews.AddRange(Changeset.Reviews.GroupBy(g => g.ProjectKey).Select(r => r.First())); } // get details on the reviews List <CrucibleReview> CrucibleReviews = new List <CrucibleReview>(); foreach (FishEyeReview Review in FishEyeReviews) { CrucibleReviews.Add(await this.crucibleClient.GetReviewDetails(Review.PermaId["id"].ToString())); } // check if all reviews are closed and have 2 completed reviewers Problems = this.ValidateStateForAssociatedReviews(CrucibleReviews); Problems = Problems.Merge(this.ValidateCompletedReviewersForAssociatedReviews(CrucibleReviews)); // if failure found, comment to the pr the problem, make sure to check both though if (Problems.Count > 0) { await this.bitbucketClient.SetReviewerStatus(pullRequest, new BitbucketParticipant() { User = new BitbucketUser() { Name = this.integrations.Bitbucket.Credentials.UserName, Slug = this.integrations.Bitbucket.Credentials.UserName }, IsApproved = false, Status = BitbucketStatus.NeedsWork }); await this.bitbucketClient.AddComment(pullRequest, new BitbucketComment() { Text = string.Format(Resources.PullRequest_NeedsWorkReviewConditions, pullRequest.Author.User.Name, string.Join("\n", Problems.Select(s => $"* {s.Message}"))) }); } }
private async Task <bool> AreAllCommitsReviewed(BitbucketPullRequest pullRequest, FishEyeChangesets changesets) { List <FishEyeChangeset> ChangesetsMissingReviews = changesets.Changesets.FindAll(c => c.Reviews.Count <= 0); if (ChangesetsMissingReviews.Count > 0) { // list commits that are not associated with a review await this.bitbucketClient.AddComment(pullRequest, new BitbucketComment() { Text = string.Format(Resources.PullRequest_CommitsNotAssociatedWithAReview, string.Join("\n", ChangesetsMissingReviews.Select(s => $"* {s.ChangesetId}"))) }); } return(false); }