From 637ca31ea17034fecd36b15401fed87c2448a72b Mon Sep 17 00:00:00 2001 From: jagarro3 Date: Fri, 26 Jan 2024 00:04:21 +0100 Subject: [PATCH 1/3] List workitems in tooltip --- src/components/Columns.tsx | 26 +++++++++- src/models/PullRequestModel.tsx | 92 ++++++++++++++++++++++----------- vss-extension.dev.json | 3 +- vss-extension.json | 3 +- vss-extension.version.json | 2 +- 5 files changed, 93 insertions(+), 33 deletions(-) diff --git a/src/components/Columns.tsx b/src/components/Columns.tsx index 244585b..0a0bba9 100644 --- a/src/components/Columns.tsx +++ b/src/components/Columns.tsx @@ -288,7 +288,31 @@ export function DetailsColumn( className={`button-icon fontSize font-size second-line-row`} iconProps={{ iconName: "WorkItem" }} tooltipProps={{ - text: `${tableItem.workItemsCount} linked Work Item(s)`, + renderContent: () => { + return ( + + + + + + + + {(tableItem.workItems.sort(w => w.id).map((workItem) => { + return ( + + + + ); + }) + )} + +
+ {tableItem.workItemsCount} linked Work Item(s) +
+ {workItem.fields['System.WorkItemType']} {workItem.id} - {workItem.fields['System.Title']} +
+ ); + }, delayMs: 500, }} subtle={true} diff --git a/src/models/PullRequestModel.tsx b/src/models/PullRequestModel.tsx index fc33b74..e3e7148 100644 --- a/src/models/PullRequestModel.tsx +++ b/src/models/PullRequestModel.tsx @@ -9,6 +9,7 @@ import * as DevOps from "azure-devops-extension-sdk"; import { Statuses } from "azure-devops-ui/Status"; import { getClient } from "azure-devops-extension-api"; import { GitRestClient } from "azure-devops-extension-api/Git/GitClient"; +import { WorkItemTrackingRestClient } from "azure-devops-extension-api/WorkItemTracking/WorkItemTrackingClient"; import { hasPullRequestFailure } from "./constants"; import { BranchDropDownItem, @@ -23,6 +24,8 @@ import { getEvaluationsPerPullRequest } from "../services/AzureGitServices"; import { EvaluationPolicyType } from "./GitModels"; import { GitRepository } from 'azure-devops-extension-api/Git/Git'; import { compare } from "../lib/date"; +import { WorkItem } from "azure-devops-extension-api/WorkItemTracking/WorkItemTracking"; +import { ResourceRef } from "azure-devops-extension-api/WebApi/WebApi"; export interface GitRepositoryModel extends GitRepository { isDisabled: boolean | undefined; @@ -46,6 +49,7 @@ export class PullRequestModel { public lastCommitDetails: GitCommitRef | undefined; public isAutoCompleteSet: boolean = false; public workItemsCount: number = 0; + public workItems: WorkItem[] = []; public comment: PullRequestComment; public policies: PullRequestPolicy[] = []; public isAllPoliciesOk: boolean = false; @@ -226,10 +230,7 @@ export class PullRequestModel { return voteResult; } - private getStatusIndicatorData( - reviewers: IdentityRefWithVote[], - isAllPoliciesOk: boolean - ): IStatusIndicatorData { + private getStatusIndicatorData(reviewers: IdentityRefWithVote[], isAllPoliciesOk: boolean): IStatusIndicatorData { const indicatorData: IStatusIndicatorData = { label: "Waiting Review", statusProps: { ...Statuses.Queued, ariaLabel: "Waiting Review" }, @@ -241,56 +242,68 @@ export class PullRequestModel { ariaLabel: "Pull Request is in failure status.", }; indicatorData.label = "Pull Request is in failure status."; - } else if (reviewers.some((r) => r.vote === ReviewerVoteOption.Rejected)) { + + return indicatorData; + } + + if (reviewers.some((r) => r.vote === ReviewerVoteOption.Rejected)) { indicatorData.statusProps = { ...Statuses.Failed, ariaLabel: "One or more reviewer(s) has rejected.", }; indicatorData.label = "One or more reviewer(s) has rejected."; - } else if ( - reviewers.some((r) => r.vote === ReviewerVoteOption.WaitingForAuthor) - ) { + + return indicatorData; + } + + if (reviewers.some((r) => r.vote === ReviewerVoteOption.WaitingForAuthor)) { indicatorData.statusProps = { ...Statuses.Warning, ariaLabel: "One or more reviewer(s) is waiting for the author.", }; - indicatorData.label = - "One or more reviewer(s) is waiting for the author."; - } else if ( - this.requiredReviewers.every( - (r) => - r.vote === ReviewerVoteOption.Approved || - r.vote === ReviewerVoteOption.ApprovedWithSuggestions - ) && - isAllPoliciesOk - ) { + indicatorData.label = "One or more reviewer(s) is waiting for the author."; + + return indicatorData; + } + + if (this.requiredReviewers.every((r) => r.vote === ReviewerVoteOption.Approved || r.vote === ReviewerVoteOption.ApprovedWithSuggestions) && isAllPoliciesOk) { indicatorData.statusProps = { ...Statuses.Success, ariaLabel: "Ready for completion", }; indicatorData.label = "Success"; - } else if (isAllPoliciesOk === false) { + + return indicatorData; + } + + if (isAllPoliciesOk === false) { indicatorData.statusProps = { ...Statuses.Running, ariaLabel: "Waiting all policies to be completed", }; - indicatorData.label = "Waiting all policies to be completed"; - } else if ( - this.requiredReviewers.every((r) => r.vote === ReviewerVoteOption.NoVote) - ) { + indicatorData.label = "Some policies are not completed"; + + return indicatorData; + } + + if (this.requiredReviewers.every((r) => r.vote === ReviewerVoteOption.NoVote)) { indicatorData.statusProps = { ...Statuses.Waiting, ariaLabel: "Waiting Review of required Reviewers", }; indicatorData.label = "Waiting Review of required Reviewers"; - } else if ( - this.requiredReviewers.some((r) => r.vote === ReviewerVoteOption.NoVote) - ) { + + return indicatorData; + } + + if (this.requiredReviewers.some((r) => r.vote === ReviewerVoteOption.NoVote)) { indicatorData.statusProps = { ...Statuses.Running, ariaLabel: "Waiting remaining required Reviewers", }; indicatorData.label = "Review in progress"; + + return indicatorData; } return indicatorData; @@ -362,6 +375,7 @@ export class PullRequestModel { private async getPullRequestWorkItemAsync() { const gitClient: GitRestClient = getClient(GitRestClient); let self = this; + let workItemIds : number[] = []; await gitClient .getPullRequestWorkItemRefs( @@ -371,11 +385,31 @@ export class PullRequestModel { ) .then((value) => { self.workItemsCount = value !== undefined ? value.length : 0; + workItemIds = value.map(v => Number(v.id)); }) .catch((error) => { - console.log( - "There was an error calling the Pull Request work item (method: getPullRequestWorkItemAsync)." - ); + console.log("There was an error calling the Pull Request work item (method: getPullRequestWorkItemAsync)."); + console.log(error); + }); + + await this.getWorkItemsAsync(workItemIds); + } + + private async getWorkItemsAsync(workItemIds : number[]) { + if (workItemIds.length === 0) { + return; + } + + const gitClient: WorkItemTrackingRestClient = getClient(WorkItemTrackingRestClient); + let self = this; + + await gitClient + .getWorkItems(workItemIds, self.projectName) + .then((value) => { + self.workItems = value; + }) + .catch((error) => { + console.log("There was an error calling the Work Item (method: getWorkItemsAsync)."); console.log(error); }); } diff --git a/vss-extension.dev.json b/vss-extension.dev.json index 3ff018f..2f0f328 100644 --- a/vss-extension.dev.json +++ b/vss-extension.dev.json @@ -6,7 +6,8 @@ "scopes": [ "vso.code", "vso.build", - "vso.graph" + "vso.graph", + "vso.work" ], "contributions": [{ "id": "view", diff --git a/vss-extension.json b/vss-extension.json index dda5301..5a4b34d 100644 --- a/vss-extension.json +++ b/vss-extension.json @@ -9,7 +9,8 @@ "scopes": [ "vso.code", "vso.build", - "vso.graph" + "vso.graph", + "vso.work" ], "targets": [{ "id": "Microsoft.VisualStudio.Services" diff --git a/vss-extension.version.json b/vss-extension.version.json index fea147e..fda7d62 100644 --- a/vss-extension.version.json +++ b/vss-extension.version.json @@ -1 +1 @@ -{"version": "2.234324324.1"} +{"version": "2.0.1"} From c5e22980daa8167ad5c3ee52063ecbf64f1c4a1f Mon Sep 17 00:00:00 2001 From: jagarro3 Date: Fri, 26 Jan 2024 00:12:04 +0100 Subject: [PATCH 2/3] Fix Sonar --- src/components/Columns.tsx | 2 +- src/models/PullRequestModel.tsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/components/Columns.tsx b/src/components/Columns.tsx index 0a0bba9..c49f83d 100644 --- a/src/components/Columns.tsx +++ b/src/components/Columns.tsx @@ -299,7 +299,7 @@ export function DetailsColumn( - {(tableItem.workItems.sort(w => w.id).map((workItem) => { + {(tableItem.workItems.map((workItem) => { return ( diff --git a/src/models/PullRequestModel.tsx b/src/models/PullRequestModel.tsx index e3e7148..8e2a846 100644 --- a/src/models/PullRequestModel.tsx +++ b/src/models/PullRequestModel.tsx @@ -406,7 +406,7 @@ export class PullRequestModel { await gitClient .getWorkItems(workItemIds, self.projectName) .then((value) => { - self.workItems = value; + self.workItems = value.sort(m => m.id); }) .catch((error) => { console.log("There was an error calling the Work Item (method: getWorkItemsAsync)."); From 8c284b5e27565396d3656375722baffd95fb06dc Mon Sep 17 00:00:00 2001 From: jagarro3 Date: Fri, 26 Jan 2024 00:14:25 +0100 Subject: [PATCH 3/3] Fix Sonar --- src/components/Columns.tsx | 2 +- src/models/PullRequestModel.tsx | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/components/Columns.tsx b/src/components/Columns.tsx index c49f83d..896fda7 100644 --- a/src/components/Columns.tsx +++ b/src/components/Columns.tsx @@ -301,7 +301,7 @@ export function DetailsColumn( {(tableItem.workItems.map((workItem) => { return ( - + {workItem.fields['System.WorkItemType']} {workItem.id} - {workItem.fields['System.Title']} diff --git a/src/models/PullRequestModel.tsx b/src/models/PullRequestModel.tsx index 8e2a846..7b20b83 100644 --- a/src/models/PullRequestModel.tsx +++ b/src/models/PullRequestModel.tsx @@ -25,7 +25,6 @@ import { EvaluationPolicyType } from "./GitModels"; import { GitRepository } from 'azure-devops-extension-api/Git/Git'; import { compare } from "../lib/date"; import { WorkItem } from "azure-devops-extension-api/WorkItemTracking/WorkItemTracking"; -import { ResourceRef } from "azure-devops-extension-api/WebApi/WebApi"; export interface GitRepositoryModel extends GitRepository { isDisabled: boolean | undefined;