Skip to content

Commit

Permalink
Merge pull request #55 from oev-berlin/feat/sonarqube-branch-plugin-s…
Browse files Browse the repository at this point in the history
…upport

feat: Pull Request support if using SonarQube community version with community-branch-plugin installed
  • Loading branch information
hblab-dieuhd authored Jan 12, 2024
2 parents 69fb8d0 + 1579299 commit 567055e
Show file tree
Hide file tree
Showing 6 changed files with 68 additions and 11 deletions.
6 changes: 4 additions & 2 deletions src/cli/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ export class Cli {
this.sonarURL = this.argv.sonar.url ? this.argv.sonar.url : process.env.SONAR_URL;
this.sonarToken = this.argv.sonar.token ? this.argv.sonar.token : process.env.SONAR_TOKEN;
this.sonarProjectKey = this.argv.sonar.project_key ? this.argv.sonar.project_key : process.env.SONAR_PROJECT_KEY;

if (!this.validate()) {
process.exit(1);
}
Expand Down Expand Up @@ -124,7 +124,9 @@ export class Cli {
const sonar = new Sonar({
tokenKey: this.sonarToken,
host: this.sonarURL,
projectKey: this.sonarProjectKey
projectKey: this.sonarProjectKey,
branchPluginEnabled: this.argv.sonarBranchPlugin,
branchPluginMergeId: parseInt(this.gitMergeID)
});

let gitMerge: GitMerge;
Expand Down
7 changes: 7 additions & 0 deletions src/cli/options.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ export enum Provide {
export interface Arguments {
_: ArgsOutput;
provide: Provide;
sonarBranchPlugin?: boolean;
skipScanner?: boolean;
define: (string | number)[] | undefined;
git: { [key: string]: string };
Expand Down Expand Up @@ -41,6 +42,12 @@ export function createOptions() {
desc: "Skip run sonar-scanner",
default: false
})
.option("sonar-branch-plugin", {
alias: "b",
group: "Global Options:",
desc: "Enable SonarQube Community-Branch-Plugin support. Please make sure, that you've properly installed the plugin in SonarQube: https://github.com/mc1arke/sonarqube-community-branch-plugin",
default: false
})
.option("define", {
alias: "D",
requiresArg: true,
Expand Down
2 changes: 1 addition & 1 deletion src/quality-gate/core.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Git, GitMerge, GitReviewParam } from "../git";
import { Sonar } from "../sonar";

const INTERVAL_SECONDS = 60;
const INTERVAL_SECONDS = 300;

declare global {
interface Date {
Expand Down
32 changes: 27 additions & 5 deletions src/sonar/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,13 @@ export class Sonar {
qualityGate: SonarReport;
config?: SonarProperties;

constructor(opt: { tokenKey: string; host: string; projectKey: string }) {
constructor(opt: {
tokenKey: string;
host: string;
projectKey: string;
branchPluginEnabled?: boolean;
branchPluginMergeId?: number;
}) {
try {
this.config = new SonarProperties({ projectDir: process.cwd() });
this.host = this.config.getSonarURL();
Expand All @@ -30,6 +36,8 @@ export class Sonar {
this.qualityGate = new SonarReport({
host: this.host,
projectKey: this.projectKey,
branchPluginEnabled: opt.branchPluginEnabled,
branchPluginMergeId: opt.branchPluginMergeId,
});

const headers = {
Expand All @@ -39,10 +47,18 @@ export class Sonar {
}

async getQualityStatus() {
const parameters: entity.SonarApiRequestParameters = {
projectKey: this.projectKey,
}

if (this.qualityGate.branchPluginEnabled) {
parameters.pullRequest = this.qualityGate.branchPluginMergeId;
}

Log.debug("sonar get quality status", SONAR_QUALITY_API);
const response = await this.http.get<entity.Qualitygate>(
SONAR_QUALITY_API,
{ projectKey: this.projectKey }
parameters
);
return response.data;
}
Expand All @@ -57,13 +73,19 @@ export class Sonar {
}

private async findIssuesByPage(fromTime: string, page: number) {
const response = await this.http.get<entity.IssueList>(SONAR_ISSUE_API, {
const parameters: entity.SonarApiRequestParameters = {
componentKeys: this.projectKey,
createdAfter: fromTime,
// sinceLeakPeriod: true, // get issues of new code on sonar
p: page,
ps: PAGE_SIZE,
});
createdAfter: fromTime,
};

if (this.qualityGate.branchPluginEnabled) {
parameters.pullRequest = this.qualityGate.branchPluginMergeId;
}

const response = await this.http.get<entity.IssueList>(SONAR_ISSUE_API, parameters);
return response.data;
}

Expand Down
10 changes: 10 additions & 0 deletions src/sonar/entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,3 +55,13 @@ export interface Task {
export interface Tasks {
tasks: Task[];
}

export interface SonarApiRequestParameters {
projectKey?: string;
componentKeys?: string;
sinceLeakPeriod?: boolean;
createdAfter?: string;
pullRequest?: number;
p?: number;
ps?: number;
}
22 changes: 19 additions & 3 deletions src/sonar/report.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,18 @@ const IMAGE_DIR_LINK = "https://hsonar.s3.ap-southeast-1.amazonaws.com/images/";
export class SonarReport {
host?: string;
projectKey?: string;
branchPluginEnabled?: boolean;
branchPluginMergeId?: number;
constructor(opt: {
host?: string;
projectKey?: string;
branchPluginEnabled?: boolean;
branchPluginMergeId?: number;
}) {
this.host = opt.host;
this.projectKey = opt.projectKey;
this.branchPluginEnabled = opt.branchPluginEnabled;
this.branchPluginMergeId = opt.branchPluginMergeId;
}

private capitalize(text: string) {
Expand Down Expand Up @@ -57,12 +63,22 @@ export class SonarReport {
return level[val];
}

private appendPullRequestIdIfBranchPluginEnabled(url: string) {
if (this.branchPluginEnabled) {
return `${url}&pullRequest=${this.branchPluginMergeId}`
}

return url;
}

private getIssueURL(type: string) {
return this.host + `/project/issues?id=${this.projectKey}&resolved=false&sinceLeakPeriod=true&types=${type}`;
const url = this.host + `/project/issues?id=${this.projectKey}&resolved=false&sinceLeakPeriod=true&types=${type}`;
return this.appendPullRequestIdIfBranchPluginEnabled(url);
}

private getMetricURL(metric: string) {
return this.host + `/project/issues?id=${this.projectKey}&metric=${metric}&view=list`;
const url = this.host + `/project/issues?id=${this.projectKey}&metric=${metric}&view=list`;
return this.appendPullRequestIdIfBranchPluginEnabled(url);
}

private getIssueSecurity(projectStatus: ProjectStatus) {
Expand Down Expand Up @@ -121,7 +137,7 @@ export class SonarReport {
status = "failed";
}

const report = `# SonarQube Code Analytics
const report = `# SonarQube Code Analytics
## Quality Gate ${status}
${this.icon(status)}
Expand Down

0 comments on commit 567055e

Please sign in to comment.