Skip to content
This repository was archived by the owner on Jan 7, 2021. It is now read-only.
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,17 @@ public void executeOn(Project project, SensorContext context) {
String stashURL = stashRequestFacade.getStashURL();
String stashProject = stashRequestFacade.getStashProject();
String repository = stashRequestFacade.getStashRepository();

String stashPullRequestId = stashRequestFacade.getStashPullRequestId();

String stashCommitId = stashRequestFacade.getStashCommitId();

if (stashPullRequestId == null && stashCommitId == null) {
throw new StashConfigurationException("Must specify either Commit ID or Pull Reuquest ID");
}
if (stashPullRequestId != null && stashCommitId != null) {
throw new StashConfigurationException("Cannot specify both Commit ID and Pull Reuquest ID");
}

int stashTimeout = config.getStashTimeout();

StashCredentials stashCredentials = stashRequestFacade.getCredentials();
Expand All @@ -58,39 +67,53 @@ public void executeOn(Project project, SensorContext context) {
LOGGER.error("Process stopped: no SonarQube reviewer identified to publish to Stash the SQ analysis");
}
else {

// Get all changes exposed from Stash differential view of the pull-request
StashDiffReport diffReport = stashRequestFacade.getPullRequestDiffReport(stashProject, repository, stashPullRequestId, stashClient);
if (diffReport == null) {
LOGGER.error("Process stopped: No Stash differential report available to process the SQ analysis");
} else {

// if requested, reset all comments linked to the pull-request
if (config.resetComments()) {
stashRequestFacade.resetComments(stashProject, repository, stashPullRequestId, diffReport, stashUser, stashClient);
}

boolean canApprovePullrequest = config.canApprovePullRequest();
if (canApprovePullrequest) {
stashRequestFacade.addPullRequestReviewer(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
}

// if threshold exceeded, do not push issue list to Stash
if (issueReport.countIssues() >= issueThreshold) {
LOGGER.warn("Too many issues detected ({}/{}): Issues cannot be displayed in Diff view", issueReport.countIssues(), issueThreshold);
if (stashPullRequestId == null) {
// Get all changes exposed from Stash differential view of the commit
StashDiffReport diffReport = stashRequestFacade.getCommitDiffReport(stashProject, repository, stashCommitId, stashClient);
if (diffReport == null) {
LOGGER.error("Process stopped: No Stash differential report available to process the SQ analysis");
} else {
stashRequestFacade.postCommentPerIssue(stashProject, repository, stashPullRequestId, sonarQubeURL, issueReport, diffReport, stashClient);
if (issueReport.countIssues() >= issueThreshold) {
LOGGER.warn("Too many issues detected ({}/{}): Issues cannot be displayed in Diff view", issueReport.countIssues(), issueThreshold);
} else {
stashRequestFacade.postCommitCommentPerIssue(stashProject, repository, stashCommitId, sonarQubeURL, issueReport, diffReport, stashClient);
}
stashRequestFacade.postCommitAnalysisOverview(stashProject, repository, stashCommitId, sonarQubeURL, issueThreshold, issueReport, stashClient);
}

stashRequestFacade.postAnalysisOverview(stashProject, repository, stashPullRequestId, sonarQubeURL, issueThreshold, issueReport, stashClient);

if (canApprovePullrequest) {

// if no new issues, plugin approves the pull-request
if (issueReport.countIssues() == 0) {
stashRequestFacade.approvePullRequest(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
}
else {
// Get all changes exposed from Stash differential view of the pull-request
StashDiffReport diffReport = stashRequestFacade.getPullRequestDiffReport(stashProject, repository, stashPullRequestId, stashClient);
if (diffReport == null) {
LOGGER.error("Process stopped: No Stash differential report available to process the SQ analysis");
} else {

// if requested, reset all comments linked to the pull-request
if (config.resetComments()) {
stashRequestFacade.resetComments(stashProject, repository, stashPullRequestId, diffReport, stashUser, stashClient);
}

boolean canApprovePullrequest = config.canApprovePullRequest();
if (canApprovePullrequest) {
stashRequestFacade.addPullRequestReviewer(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
}

// if threshold exceeded, do not push issue list to Stash
if (issueReport.countIssues() >= issueThreshold) {
LOGGER.warn("Too many issues detected ({}/{}): Issues cannot be displayed in Diff view", issueReport.countIssues(), issueThreshold);
} else {
stashRequestFacade.resetPullRequestApproval(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
stashRequestFacade.postCommentPerIssue(stashProject, repository, stashPullRequestId, sonarQubeURL, issueReport, diffReport, stashClient);
}
stashRequestFacade.postAnalysisOverview(stashProject, repository, stashPullRequestId, sonarQubeURL, issueThreshold, issueReport, stashClient);

if (canApprovePullrequest) {

// if no new issues, plugin approves the pull-request
if (issueReport.countIssues() == 0) {
stashRequestFacade.approvePullRequest(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
} else {
stashRequestFacade.resetPullRequestApproval(stashProject, repository, stashPullRequestId, stashCredentials.getLogin(), stashClient);
}
}
}
}
Expand Down
21 changes: 11 additions & 10 deletions src/main/java/org/sonar/plugins/stash/StashPlugin.java
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ public class StashPlugin extends SonarPlugin {
public static final String STASH_PROJECT = "sonar.stash.project";
public static final String STASH_REPOSITORY = "sonar.stash.repository";
public static final String STASH_PULL_REQUEST_ID = "sonar.stash.pullrequest.id";
public static final String STASH_COMMIT_ID = "sonar.stash.commit.id";
public static final String STASH_RESET_COMMENTS = "sonar.stash.comments.reset";
public static final String STASH_URL = "sonar.stash.url";
public static final String STASH_LOGIN = "sonar.stash.login";
Expand All @@ -46,7 +47,7 @@ public class StashPlugin extends SonarPlugin {
public static final String STASH_ISSUE_THRESHOLD = "sonar.stash.issue.threshold";
public static final String STASH_TIMEOUT = "sonar.stash.timeout";
public static final String SONARQUBE_URL = "sonar.host.url";
public static final String STASH_TASK_SEVERITY_THRESHOLD = "sonar.stash.task.issue.severity.threshold";
public static final String STASH_TASK_SEVERITY_THRESHOLD = "sonar.stash.task.issue.severity.threshold";

@Override
public List getExtensions() {
Expand Down Expand Up @@ -85,15 +86,15 @@ public List getExtensions() {
.description("Threshold to limit the number of issues pushed to Stash server")
.subCategory(CONFIG_PAGE_SUB_CATEGORY_STASH)
.onQualifiers(Qualifiers.PROJECT)
.defaultValue(DEFAULT_STASH_THRESHOLD_VALUE).build(),
PropertyDefinition.builder(STASH_TASK_SEVERITY_THRESHOLD)
.name("Stash tasks severity threshold")
.description("Only create tasks for issues with the same or higher severity")
.type(PropertyType.SINGLE_SELECT_LIST)
.subCategory(CONFIG_PAGE_SUB_CATEGORY_STASH)
.onQualifiers(Qualifiers.PROJECT)
.defaultValue(SEVERITY_NONE)
.defaultValue(DEFAULT_STASH_THRESHOLD_VALUE).build(),
PropertyDefinition.builder(STASH_TASK_SEVERITY_THRESHOLD)
.name("Stash tasks severity threshold")
.description("Only create tasks for issues with the same or higher severity")
.type(PropertyType.SINGLE_SELECT_LIST)
.subCategory(CONFIG_PAGE_SUB_CATEGORY_STASH)
.onQualifiers(Qualifiers.PROJECT)
.defaultValue(SEVERITY_NONE)
.options(ListUtils.sum(Arrays.asList(SEVERITY_NONE), SEVERITY_LIST)).build());
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,9 @@ public String getPullRequestId() {
return settings.getString(StashPlugin.STASH_PULL_REQUEST_ID);
}

public String getCommitId() {
return settings.getString(StashPlugin.STASH_COMMIT_ID);
}
public String getStashURL() {
return settings.getString(StashPlugin.STASH_URL);
}
Expand Down Expand Up @@ -64,4 +67,4 @@ public boolean resetComments() {
public String getTaskIssueSeverityThreshold() {
return settings.getString(StashPlugin.STASH_TASK_SEVERITY_THRESHOLD);
}
}
}
123 changes: 115 additions & 8 deletions src/main/java/org/sonar/plugins/stash/StashRequestFacade.java
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,24 @@ public void postAnalysisOverview(String project, String repository, String pullR
}
}

/**
* Post SQ analysis overview on Stash
*/
public void postCommitAnalysisOverview(String project, String repository, String commitId, String sonarQubeURL, int issueThreshold, SonarQubeIssuesReport issueReport, StashClient stashClient){
try {
stashClient.postCommentOnCommit(project,
repository,
commitId,
MarkdownPrinter.printReportMarkdown(issueReport, sonarQubeURL, issueThreshold));

LOGGER.info("SonarQube analysis overview has been reported to Stash.");

} catch(StashClientException e){
LOGGER.error("Unable to push SonarQube analysis overview to Stash: {}", e.getMessage());
LOGGER.debug("Exception stack trace", e);
}
}

/**
* Approve pull-request
*/
Expand Down Expand Up @@ -118,6 +136,73 @@ public void addPullRequestReviewer(String project, String repository, String pul
}
}

/**
* Post one comment on a commit by found issue on Stash.
*/
public void postCommitCommentPerIssue(String project, String repository, String commitId, String sonarQubeURL, SonarQubeIssuesReport issueReport, StashDiffReport diffReport, StashClient stashClient){
try {
// to optimize request to Stash, builds comment match ordered by filepath
Map<String,StashCommentReport> commentsByFile = new HashMap<>();
for (SonarQubeIssue issue : issueReport.getIssues()) {
if (commentsByFile.get(issue.getPath()) == null){
StashCommentReport comments = stashClient.getCommitComments(project, repository, commitId, issue.getPath());

// According to the type of the comment
// if type == CONTEXT, comment.line is set to source line instead of destination line
comments.applyDiffReport(diffReport);

commentsByFile.put(issue.getPath(), comments);
}
}

// Severity available to create a task
List<String> taskSeverities = getReportedSeverities();

for (SonarQubeIssue issue : issueReport.getIssues()) {
StashCommentReport comments = commentsByFile.get(issue.getPath());

// if comment not already pushed to Stash
if ((comments != null) &&
(comments.contains(MarkdownPrinter.printIssueMarkdown(issue, sonarQubeURL), issue.getPath(), issue.getLine()))) {
LOGGER.debug("Comment \"{}\" already pushed on file {} ({})", issue.getRule(), issue.getPath(), issue.getLine());
} else {

// check if issue belongs to the Stash diff view
String type = diffReport.getType(issue.getPath(), issue.getLine());
if (type == null){
LOGGER.info("Comment \"{}\" cannot be pushed to Stash like it does not belong to diff view - {} (line: {})", issue.getRule(), issue.getPath(), issue.getLine());
} else{

long line = diffReport.getLine(issue.getPath(), issue.getLine());

StashComment comment = stashClient.postCommentLineOnCommit(project,
repository,
commitId,
MarkdownPrinter.printIssueMarkdown(issue, sonarQubeURL),
issue.getPath(),
line,
type);

LOGGER.debug("Comment \"{}\" has been created ({}) on file {} ({})", issue.getRule(), type, issue.getPath(), line);

// Create task linked to the comment if configured
if (taskSeverities.contains(issue.getSeverity())) {
stashClient.postTaskOnComment(issue.getMessage(), comment.getId());

LOGGER.debug("Comment \"{}\" has been linked to a Stash task", comment.getId());
}
}
}
}

LOGGER.info("New SonarQube issues have been reported to Stash.");

} catch (StashClientException e){
LOGGER.error("Unable to link SonarQube issues to Stash: {}", e.getMessage());
LOGGER.debug("Exception stack trace", e);
}
}

/**
* Post one comment by found issue on Stash.
*/
Expand Down Expand Up @@ -243,16 +328,19 @@ public String getStashRepository() throws StashConfigurationException {
}

/**
* Mandatory Stash pull-request ID option.
* Stash pull-request ID option. Must specify this or commit ID
* @throws StashConfigurationException if unable to get parameter
*/
public String getStashPullRequestId() throws StashConfigurationException {
String result = config.getPullRequestId();
if (result == null){
throw new StashConfigurationException("Unable to get " + StashPlugin.STASH_PULL_REQUEST_ID + ": value is null");
}

return result;
public String getStashPullRequestId() {
return config.getPullRequestId();
}

/**
* Stash commit ID option. Must specify this or pull request ID
* @throws StashConfigurationException if unable to get parameter
*/
public String getStashCommitId() {
return config.getCommitId();
}

/**
Expand Down Expand Up @@ -293,6 +381,25 @@ public StashDiffReport getPullRequestDiffReport(String project, String repositor
return result;
}

/**
* Get all changes exposed through the Stash commit.
*/
public StashDiffReport getCommitDiffReport(String project, String repository, String commitId, StashClient stashClient){
StashDiffReport result = null;

try {
result = stashClient.getCommitDiffs(project, repository, commitId);

LOGGER.debug("Stash differential report retrieved from commit {} #{}", repository, commitId);

} catch(StashClientException e){
LOGGER.error("Unable to get Stash differential report from Stash: {}", e.getMessage());
LOGGER.debug("Exception stack trace", e);
}

return result;
}

/**
* Reset all comments linked to a pull-request.
*/
Expand Down
Loading