This repository has been archived by the owner on Jan 17, 2022. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
M999JAD
authored and
M999JAD
committed
Sep 24, 2021
1 parent
8fca047
commit 7710d90
Showing
7 changed files
with
345 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
# A push on master will build, test and publish Jeka on OSSRH. | ||
# Beside it will push the built documentation on the Jeka landing page. | ||
|
||
# If a tag is present on the last commit, Jeka will publish versioned artifacts according tag name on OSSRH public repo. | ||
# If no tag is present, the built artifacts will be published to OSSRH snapshot repository. | ||
# This logic is implemented within the Jeka build. | ||
|
||
name: Java Build and Publish | ||
|
||
on: | ||
push: | ||
branches: [ master ] | ||
workflow_dispatch: | ||
branches: [ master ] | ||
|
||
jobs: | ||
build: | ||
runs-on: ubuntu-latest | ||
steps: | ||
- uses: actions/checkout@v2 | ||
- name: Set up JDK 1.8 | ||
uses: actions/setup-java@v1 | ||
with: | ||
java-version: 1.8 | ||
- name: Build with Jekaw | ||
env: | ||
OSSRH_USER: ${{ secrets.OSSRH_USER }} | ||
OSSRH_PWD: ${{ secrets.OSSRH_PWD }} | ||
GPG_PASSPHRASE: ${{ secrets.GPG_PASSPHRASE }} | ||
run: | | ||
cd ./dev.jeka.plugins.sonarqube | ||
./jekaw java#pack java#publish |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,4 @@ | ||
[![Maven Central](https://img.shields.io/maven-central/v/dev.jeka/sonarqube-plugin.svg?label=Maven%20Central)](https://search.maven.org/search?q=g:%22dev.jeka22%20AND%20a:%22springboot-plugin%22) | ||
|
||
# sonarqube-plugin | ||
A Sonarqube plugin for Jeka |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
## Next line means plugin 2.4.0.RC11 is not compatile with Jeka 0.9.0.RELEASE and above | ||
## 2.4.0.RC11 : 0.9.0.RELEASE | ||
|
83 changes: 83 additions & 0 deletions
83
dev.jeka.plugins.sonarqube/src/main/java/dev/jeka/plugins/sonarqube/JkPluginSonarqube.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,83 @@ | ||
package dev.jeka.plugins.sonarqube; | ||
|
||
import dev.jeka.core.api.depmanagement.JkDependencySet; | ||
import dev.jeka.core.api.depmanagement.JkModuleId; | ||
import dev.jeka.core.api.file.JkPathSequence; | ||
import dev.jeka.core.api.java.project.JkCompileLayout; | ||
import dev.jeka.core.api.java.project.JkJavaProject; | ||
import dev.jeka.core.api.java.project.JkJavaProjectConstruction; | ||
import dev.jeka.core.tool.*; | ||
import dev.jeka.core.tool.builtins.java.JkPluginJava; | ||
|
||
import java.nio.file.Path; | ||
import java.util.HashMap; | ||
import java.util.Map; | ||
|
||
@JkDoc("Run SonarQube analysis.") | ||
@JkDocPluginDeps(JkPluginJava.class) | ||
public class JkPluginSonarqube extends JkPlugin { | ||
|
||
private final Map<String, String> properties = new HashMap<>(); | ||
|
||
public JkPluginSonarqube(JkClass jkClass) { | ||
super(jkClass); | ||
} | ||
|
||
public static JkSonarqube configureSonarFrom(JkJavaProject project) { | ||
final JkCompileLayout prodLayout = project.getConstruction().getCompilation().getLayout(); | ||
final JkCompileLayout testLayout = project.getConstruction().getTesting().getCompilation().getLayout(); | ||
final Path baseDir = project.getBaseDir(); | ||
JkJavaProjectConstruction construction = project.getConstruction(); | ||
JkDependencySet deps = construction.getCompilation().getDependencies() | ||
.merge(construction.getRuntimeDependencies()).getResult(); | ||
final JkPathSequence libs = project.getConstruction().getDependencyResolver().resolve(deps).getFiles(); | ||
final Path testReportDir = project.getConstruction().getTesting().getReportDir(); | ||
final JkModuleId moduleId = project.getPublication().getModuleId(); | ||
final String version = project.getPublication().getVersion(); | ||
final String fullName = moduleId.getDotedName(); | ||
final String name = moduleId.getName(); | ||
return JkSonarqube | ||
.of(fullName, name, version) | ||
.withProperties(JkOptions.getAllStartingWith("sonar.")).withProjectBaseDir(baseDir) | ||
.withBinaries(project.getConstruction().getCompilation().getLayout().resolveClassDir()) | ||
.withLibraries(libs) | ||
.withSourcesPath(prodLayout.resolveSources().getRootDirsOrZipFiles()) | ||
.withTestPath(testLayout.resolveSources().getRootDirsOrZipFiles()) | ||
.withProperty(JkSonarqube.WORKING_DIRECTORY, baseDir.resolve(JkConstants.JEKA_DIR + "/.sonar").toString()) | ||
.withProperty(JkSonarqube.JUNIT_REPORTS_PATH, | ||
baseDir.relativize( testReportDir.resolve("junit")).toString()) | ||
.withProperty(JkSonarqube.SUREFIRE_REPORTS_PATH, | ||
baseDir.relativize(testReportDir.resolve("junit")).toString()) | ||
.withProperty(JkSonarqube.SOURCE_ENCODING, project.getConstruction().getSourceEncoding()) | ||
.withProperty(JkSonarqube.JACOCO_REPORTS_PATHS, | ||
baseDir.relativize(project.getOutputDir().resolve("jacoco/jacoco.exec")).toString()); | ||
|
||
} | ||
|
||
@JkDoc("Runs sonar-scanner based on properties defined in this plugin. " + | ||
"Options prefixed with 'sonar.' as '-sonar.host.url=http://myserver/..' " + | ||
"will be appended to sonarQube properties.") | ||
public void run() { | ||
configureSonarFrom(getJkClass().getPlugins().get(JkPluginJava.class).getProject()) | ||
.withProperties(properties) | ||
.launchRunner(); | ||
} | ||
|
||
@JkDoc("Runs sonar-runner based on properties defined in this plugin. " + | ||
"Options prefixed with 'sonar.' as '-sonar.host.url=http://myserver/..' " + | ||
"will be appended to sonarQube properties.") | ||
public void runLegacy() { | ||
configureSonarFrom(getJkClass().getPlugins().get(JkPluginJava.class).getProject()) | ||
.withProperties(properties) | ||
.launchRunner(); | ||
} | ||
|
||
/** | ||
* Adds a property to setupAfterPluginActivations sonar instance to run. You'll find predefined keys in {@link JkSonarqube}. | ||
*/ | ||
public JkPluginSonarqube setProp(String key, String value) { | ||
this.properties.put(key, value); | ||
return this; | ||
} | ||
|
||
} |
225 changes: 225 additions & 0 deletions
225
dev.jeka.plugins.sonarqube/src/main/java/dev/jeka/plugins/sonarqube/JkSonarqube.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,225 @@ | ||
package dev.jeka.plugins.sonarqube; | ||
|
||
|
||
import dev.jeka.core.api.file.JkPathFile; | ||
import dev.jeka.core.api.java.JkInternalClassloader; | ||
import dev.jeka.core.api.java.JkJavaProcess; | ||
import dev.jeka.core.api.system.JkLog; | ||
import dev.jeka.core.api.utils.JkUtilsAssert; | ||
import dev.jeka.core.api.utils.JkUtilsIO; | ||
import dev.jeka.core.api.utils.JkUtilsPath; | ||
import dev.jeka.core.tool.JkConstants; | ||
|
||
import java.net.URL; | ||
import java.nio.file.Path; | ||
import java.nio.file.Paths; | ||
import java.util.*; | ||
|
||
/** | ||
* Sonar wrapper class for launching sonar analysis in a convenient way. This | ||
* Sonar wrapper is not specific to Java project so can be used for to analyse | ||
* any kind of project supported by SonarQube. | ||
* | ||
* @author Jerome Angibaud | ||
*/ | ||
public final class JkSonarqube { | ||
|
||
public static final String PROJECT_KEY = "projectKey"; | ||
public static final String PROJECT_NAME = "projectName"; | ||
public static final String PROJECT_VERSION = "projectVersion"; | ||
public static final String LANGUAGE = "language"; | ||
public static final String PROFILE = "profile"; | ||
public static final String BRANCH = "branch"; | ||
public static final String SOURCE_ENCODING = "sourceEncoding"; | ||
public static final String VERBOSE = "verbose"; | ||
public static final String WORKING_DIRECTORY = "working.directory"; | ||
public static final String JUNIT_REPORTS_PATH = "junit.reportsPath"; | ||
public static final String SUREFIRE_REPORTS_PATH = "surefire.reportsPath"; | ||
public static final String JACOCO_REPORTS_PATHS = "jacoco.reportPaths"; | ||
public static final String COVERTURA_REPORTS_PATH = "cobertura.reportPath"; | ||
public static final String CLOVER_REPORTS_PATH = "clover.reportPath"; | ||
public static final String DYNAMIC_ANALYSIS = "dynamicAnalysis"; | ||
public static final String PROJECT_BASE_DIR = "projectBaseDir"; | ||
public static final String SOURCES = "sources"; | ||
public static final String BINARIES = "binaries"; | ||
public static final String JAVA_BINARIES = "java.binaries"; | ||
public static final String TEST = "tests"; | ||
public static final String LIBRARIES = "libraries"; | ||
public static final String SKIP_DESIGN = "skipDesign"; | ||
public static final String HOST_URL = "host.url"; | ||
public static final String JDBC_URL = "jdbc.url"; | ||
public static final String JDBC_USERNAME = "jdbc.username"; | ||
public static final String JDBC_PASSWORD = "jdbc.password"; | ||
private static final String RUNNER_JAR_NAME_24 = "sonar-runner-2.4.jar"; | ||
private static final String SCANNER_JAR_NAME_46 = "sonar-scanner-cli-4.6.2.2472.jar"; | ||
private static final String RUNNER_LOCAL_PATH = JkConstants.OUTPUT_PATH + "/temp/" + RUNNER_JAR_NAME_24; | ||
private static final String SONAR_PREFIX = "sonar."; | ||
private final Map<String, String> params; | ||
|
||
private final boolean enabled; | ||
|
||
private JkSonarqube(Map<String, String> params, boolean enabled) { | ||
super(); | ||
this.params = Collections.unmodifiableMap(params); | ||
this.enabled = enabled; | ||
} | ||
|
||
public static JkSonarqube of(String projectKey, String projectName, String version) { | ||
JkUtilsAssert.argument(projectName != null, "Project name can't be null."); | ||
JkUtilsAssert.argument(projectKey != null, "Project key can't be null."); | ||
JkUtilsAssert.argument(version != null, "Project version can't be null."); | ||
final Map<String, String> map = new HashMap<>(); | ||
map.put(PROJECT_KEY, projectKey); | ||
map.put(PROJECT_NAME, projectName); | ||
map.put(PROJECT_VERSION, version); | ||
map.put(WORKING_DIRECTORY, ".sonarTempDir"); | ||
map.put(VERBOSE, Boolean.toString(JkLog.Verbosity.VERBOSE == JkLog.verbosity())); | ||
final Properties properties = System.getProperties(); | ||
for (final Object keyObject : properties.keySet()) { | ||
final String key = (String) keyObject; | ||
if (key.startsWith(SONAR_PREFIX)) { | ||
map.put(key.substring(SONAR_PREFIX.length()), properties.getProperty(key)); | ||
} | ||
} | ||
return new JkSonarqube(map, true); | ||
} | ||
|
||
public void launchRunner() { | ||
if (!enabled) { | ||
JkLog.info("Sonar analysis skipped."); | ||
} | ||
JkLog.startTask("Launch Sonar analysis wih sonar-runner."); | ||
if (JkLog.verbosity() == JkLog.Verbosity.VERBOSE) { | ||
javaRunnerProcess().runClassSync("org.sonar.runner.Main", "-e", "-X"); | ||
} else { | ||
javaRunnerProcess().runClassSync("org.sonar.runner.Main", "-e"); | ||
} | ||
JkLog.endTask(); | ||
} | ||
|
||
public void launchScanner() { | ||
if (!enabled) { | ||
JkLog.info("Sonar analysis skipped."); | ||
} | ||
JkLog.startTask("Launch Sonar analysis with sonar-scanner"); | ||
if (JkLog.verbosity() == JkLog.Verbosity.VERBOSE) { | ||
javaScannerProcess().runClassSync("org.sonar.runner.Main", "-e", "-X"); | ||
} else { | ||
javaScannerProcess().runClassSync("org.sonar.runner.Main", "-e"); | ||
} | ||
JkLog.endTask(); | ||
} | ||
|
||
public JkSonarqube enabled(boolean enabled) { | ||
return new JkSonarqube(this.params, enabled); | ||
} | ||
|
||
// Runner is the legacy cliennt | ||
private JkJavaProcess javaRunnerProcess() { | ||
URL embeddedUrl = JkSonarqube.class.getResource(RUNNER_JAR_NAME_24); | ||
Path cachedUrl = JkUtilsIO.copyUrlContentToCacheFile(embeddedUrl, null, JkInternalClassloader.URL_CACHE_DIR); | ||
return JkJavaProcess.of().withClasspath(cachedUrl).andOptions(toProperties()); | ||
} | ||
|
||
// Scanner replaces legacy Runner client | ||
private JkJavaProcess javaScannerProcess() { | ||
URL embeddedUrl = JkSonarqube.class.getResource(SCANNER_JAR_NAME_46); | ||
Path cachedUrl = JkUtilsIO.copyUrlContentToCacheFile(embeddedUrl, null, JkInternalClassloader.URL_CACHE_DIR); | ||
return JkJavaProcess.of().withClasspath(cachedUrl).andOptions(toProperties()); | ||
} | ||
|
||
private List<String> toProperties() { | ||
final List<String> result = new LinkedList<>(); | ||
for (final Map.Entry<String, String> entry : this.params.entrySet()) { | ||
result.add("-Dsonar." + entry.getKey() + "=" + entry.getValue()); | ||
} | ||
return result; | ||
} | ||
|
||
public JkSonarqube withProperty(String key, String value) { | ||
return new JkSonarqube(andParams(key, value), enabled); | ||
} | ||
|
||
public JkSonarqube withProperties(Map<String, String> props) { | ||
final Map<String, String> newProps = new HashMap<>(this.params); | ||
newProps.putAll(props); | ||
return new JkSonarqube(newProps, enabled); | ||
} | ||
|
||
public JkSonarqube withProjectBaseDir(Path baseDir) { | ||
return withProperty(PROJECT_BASE_DIR, baseDir.toAbsolutePath().toString()); | ||
} | ||
|
||
public JkSonarqube withSourcesPath(Iterable<Path> files) { | ||
return withProperty(SOURCES, toPaths(JkUtilsPath.disambiguate(files))); | ||
} | ||
|
||
|
||
public JkSonarqube withTestPath(Iterable<Path> files) { | ||
return withProperty(TEST, toPaths(files)); | ||
} | ||
|
||
public JkSonarqube withBinaries(Iterable<Path> files) { | ||
String path = toPaths(JkUtilsPath.disambiguate(files)); | ||
return withProperty(BINARIES, path).withProperty(JAVA_BINARIES, path); | ||
} | ||
|
||
public JkSonarqube withBinaries(Path... files) { | ||
return withBinaries(Arrays.asList(files)); | ||
} | ||
|
||
public JkSonarqube withLibraries(Iterable<Path> files) { | ||
return withProperty(LIBRARIES, toPaths(JkUtilsPath.disambiguate(files))); | ||
} | ||
|
||
public JkSonarqube withSkipDesign(boolean skip) { | ||
return withProperty(SKIP_DESIGN, Boolean.toString(skip)); | ||
} | ||
|
||
public JkSonarqube withHostUrl(String url) { | ||
return withProperty(HOST_URL, url); | ||
} | ||
|
||
public JkSonarqube withJdbcUrl(String url) { | ||
return withProperty(JDBC_URL, url); | ||
} | ||
|
||
public JkSonarqube withJdbcUserName(String userName) { | ||
return withProperty(JDBC_USERNAME, userName); | ||
} | ||
|
||
public JkSonarqube withJdbcPassword(String pwd) { | ||
return withProperty(JDBC_PASSWORD, pwd); | ||
} | ||
|
||
private String toPaths(Iterable<Path> files) { | ||
final Iterator<Path> it = files.iterator(); | ||
final StringBuilder result = new StringBuilder(); | ||
final Path projectDir = projectDir(); | ||
while (it.hasNext()) { | ||
final Path file = it.next(); | ||
String path; | ||
if (file.startsWith(projectDir)) { | ||
path = projectDir.relativize(file).toString(); | ||
} else { | ||
path = file.toAbsolutePath().toString(); | ||
} | ||
result.append(path); | ||
if (it.hasNext()) { | ||
result.append(","); | ||
} | ||
} | ||
return result.toString(); | ||
} | ||
|
||
private Map<String, String> andParams(String key, String value) { | ||
final Map<String, String> newMap = new HashMap<>(this.params); | ||
newMap.put(key, value); | ||
return newMap; | ||
} | ||
|
||
private Path projectDir() { | ||
return Paths.get(this.params.get(PROJECT_BASE_DIR)); | ||
} | ||
|
||
} |
Binary file added
BIN
+273 KB
dev.jeka.plugins.sonarqube/src/main/java/dev/jeka/plugins/sonarqube/sonar-runner-2.4.jar
Binary file not shown.
Binary file added
BIN
+633 KB
...ugins.sonarqube/src/main/java/dev/jeka/plugins/sonarqube/sonar-scanner-cli-4.6.2.2472.jar
Binary file not shown.