Skip to content

Commit

Permalink
Add an additional rules for security hotspot (#252)
Browse files Browse the repository at this point in the history
  • Loading branch information
Reamer authored May 24, 2020
1 parent ddcc4ec commit 5bed497
Show file tree
Hide file tree
Showing 12 changed files with 172 additions and 34 deletions.
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,13 @@ sonar.dependencyCheck.skip=true
sonar.dependencyCheck.skip=false (default)
```

If you want to work with [Security-Hotspots][Security-Hotspot] to enable a review process in your team, use the following configuration.

```ini
sonar.dependencyCheck.securityHotspot=true
sonar.dependencyCheck.securityHotspot=false (default)
```

## Ecosystem

Dependency-Check is available as a:
Expand All @@ -138,3 +145,4 @@ Permission to modify and redistribute is granted under the terms of the [LGPLv3]
[sonarqube 6.x]: https://github.com/dependency-check/dependency-check-sonar-plugin/tree/SonarQube_6.x
[bintray]: https://bintray.com/dependency-check/owasp/sonar-dependency-check
[sonar-custom-plugin-example]: https://github.com/SonarSource/sonar-custom-plugin-example
[security-hotspot]: https://docs.sonarqube.org/latest/user-guide/security-hotspots/
Original file line number Diff line number Diff line change
Expand Up @@ -81,18 +81,25 @@ public static List<PropertyDefinition> getPropertyDefinitions() {
.type(PropertyType.FLOAT)
.build(),
PropertyDefinition.builder(DependencyCheckConstants.SUMMARIZE_PROPERTY)
.subCategory("General")
.subCategory(DependencyCheckConstants.SUB_CATEGORY_GENERAL)
.name("Summarize")
.description("When enabled we summarize all vulnerabilities per dependency.")
.defaultValue(Boolean.toString(DependencyCheckConstants.SUMMARIZE_PROPERTY_DEFAULT))
.type(PropertyType.BOOLEAN)
.build(),
PropertyDefinition.builder(DependencyCheckConstants.SKIP_PROPERTY)
.subCategory("General")
.subCategory(DependencyCheckConstants.SUB_CATEGORY_GENERAL)
.name("Skip")
.description("When enabled we skip this plugin.")
.defaultValue(Boolean.toString(DependencyCheckConstants.SKIP_PROPERTY_DEFAULT))
.type(PropertyType.BOOLEAN)
.build(),
PropertyDefinition.builder(DependencyCheckConstants.SECURITY_HOTSPOT)
.subCategory(DependencyCheckConstants.SUB_CATEGORY_GENERAL)
.name("Security-Hotspot")
.description("When enabled all SonarQube issues are flagged as Security-Hotspot.")
.defaultValue(Boolean.toString(DependencyCheckConstants.SECURITY_HOTSPOT_DEFAULT))
.type(PropertyType.BOOLEAN)
.build()
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ public final class DependencyCheckConstants {
public static final String SEVERITY_MINOR = "sonar.dependencyCheck.severity.minor";
public static final String SUMMARIZE_PROPERTY = "sonar.dependencyCheck.summarize";
public static final String SKIP_PROPERTY = "sonar.dependencyCheck.skip";
public static final String SECURITY_HOTSPOT = "sonar.dependencyCheck.securityHotspot";

public static final Float SEVERITY_BLOCKER_DEFAULT = 9.0f;
public static final Float SEVERITY_CRITICAL_DEFAULT = 7.0f;
Expand All @@ -41,12 +42,15 @@ public final class DependencyCheckConstants {
public static final String HTML_REPORT_PATH_DEFAULT = "${WORKSPACE}/dependency-check-report.html";
public static final Boolean SUMMARIZE_PROPERTY_DEFAULT = Boolean.FALSE;
public static final Boolean SKIP_PROPERTY_DEFAULT = Boolean.FALSE;
public static final Boolean SECURITY_HOTSPOT_DEFAULT = Boolean.FALSE;

public static final String REPOSITORY_KEY = "OWASP";
public static final String LANGUAGE_KEY = "neutral";
public static final String RULE_KEY = "UsingComponentWithKnownVulnerability";
public static final String RULE_KEY_WITH_SECURITY_HOTSPOT = "UsingComponentWithKnownVulnerabilitySecurityHotspot";
public static final String SUB_CATEGORY_SEVERITIES = "Severities";
public static final String SUB_CATEGORY_PATHS = "Paths";
public static final String SUB_CATEGORY_GENERAL = "General";

private DependencyCheckConstants() {
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,13 @@ public static Severity cvssToSonarQubeSeverity(Float cvssScore, Configuration co
return DependencyCheckUtils.cvssToSonarQubeSeverity(cvssScore, severityBlocker ,severityCritical, severityMajor, severityMinor);
}

public static String getRuleKey(Configuration config) {
return config.getBoolean(DependencyCheckConstants.SECURITY_HOTSPOT)
.orElse(DependencyCheckConstants.SECURITY_HOTSPOT_DEFAULT)
? DependencyCheckConstants.RULE_KEY_WITH_SECURITY_HOTSPOT
: DependencyCheckConstants.RULE_KEY;
}

/**
* We are using following sources for score calculation
* https://nvd.nist.gov/vuln-metrics/cvss
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ public void addIssue(SensorContext context, Dependency dependency) {

sonarIssue
.at(location)
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.RULE_KEY))
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckUtils.getRuleKey(context.config())))
.overrideSeverity(severity)
.save();
metrics.incrementCount(severity);
Expand All @@ -109,7 +109,7 @@ public void addIssue(SensorContext context, Dependency dependency, Vulnerability

sonarIssue
.at(location)
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.RULE_KEY))
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckUtils.getRuleKey(context.config())))
.overrideSeverity(severity)
.save();
metrics.incrementCount(severity);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,7 @@ public void addIssueToProject(SensorContext context, Dependency dependency, Vuln

sonarIssue
.at(location)
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.RULE_KEY))
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckUtils.getRuleKey(context.config())))
.overrideSeverity(severity)
.save();
projectMetric.incrementCount(severity);
Expand All @@ -212,7 +212,7 @@ private void addIssueToProject(SensorContext context, Dependency dependency) {

sonarIssue
.at(location)
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.RULE_KEY))
.forRule(RuleKey.of(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckUtils.getRuleKey(context.config())))
.overrideSeverity(severity)
.save();
projectMetric.incrementCount(severity);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,44 +21,49 @@

import org.sonar.api.rule.RuleStatus;
import org.sonar.api.rule.Severity;
import org.sonar.api.rules.RuleType;
import org.sonar.api.server.rule.RulesDefinition;
import org.sonar.dependencycheck.base.DependencyCheckConstants;

import javax.annotation.ParametersAreNonnullByDefault;

public class KnownCveRuleDefinition implements RulesDefinition {


private static final int CWE_937 = 937;

@Override
@Override
@ParametersAreNonnullByDefault
public void define(Context context) {
NewRepository repo = context.createRepository(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.LANGUAGE_KEY);
NewRepository repo = context.createRepository(DependencyCheckConstants.REPOSITORY_KEY,
DependencyCheckConstants.LANGUAGE_KEY);
repo.setName("OWASP");

NewRule rule = repo.createRule(DependencyCheckConstants.RULE_KEY);
fillOWASPRule(rule);
NewRule ruleWithSecuityHotspot = repo.createRule(DependencyCheckConstants.RULE_KEY_WITH_SECURITY_HOTSPOT);
fillOWASPRule(ruleWithSecuityHotspot);
ruleWithSecuityHotspot.setType(RuleType.SECURITY_HOTSPOT);
repo.done();
}

private void fillOWASPRule(NewRule rule) {
rule.addTags("cwe-937", "cwe", "cve", "owasp-a9", "security", "vulnerability");
rule.setName("Using Components with Known Vulnerabilities");
rule.setSeverity(Severity.MAJOR);
rule.setStatus(RuleStatus.READY);
rule.addOwaspTop10(OwaspTop10.A9);
rule.addCwe(CWE_937);

String description = "<p>Components, such as libraries, frameworks, and other software modules, " +
"almost always run with full privileges. If a vulnerable component is exploited, such " +
"an attack can facilitate serious data loss or server takeover. Applications using " +
"components with known vulnerabilities may undermine application defenses and enable " +
"a range of possible attacks and impacts.</p>" +
"<h3>References:</h3>" +
"<ul><li>OWASP Top 10 2013-A9: <a href=\"https://www.owasp.org/index.php/Top_10_2013-A9-Using_Components_with_Known_Vulnerabilities\">Using Components with Known Vulnerabilities</a></li>" +
"<li><a href=\"https://cwe.mitre.org/data/definitions/937.html\">Common Weakness Enumeration CWE-937</a></li>" +
"<p>This issue was generated by <a href=\"https://www.owasp.org/index.php/OWASP_Dependency_Check\">Dependency-Check</a>";
String description = "<p>Components, such as libraries, frameworks, and other software modules, "
+ "almost always run with full privileges. If a vulnerable component is exploited, such "
+ "an attack can facilitate serious data loss or server takeover. Applications using "
+ "components with known vulnerabilities may undermine application defenses and enable "
+ "a range of possible attacks and impacts.</p>"
+ "<h3>References:</h3>"
+ "<ul><li>OWASP Top 10 2013-A9: <a href=\"https://www.owasp.org/index.php/Top_10_2013-A9-Using_Components_with_Known_Vulnerabilities\">Using Components with Known Vulnerabilities</a></li>"
+ "<li><a href=\"https://cwe.mitre.org/data/definitions/937.html\">Common Weakness Enumeration CWE-937</a></li>"
+ "<p>This issue was generated by <a href=\"https://www.owasp.org/index.php/OWASP_Dependency_Check\">Dependency-Check</a>";
rule.setHtmlDescription(description);

// There's simply no way to know how much effort will be involved in updating/replacing a vulnerable component

repo.done();
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ public class NeutralProfile implements BuiltInQualityProfilesDefinition {
public void define(Context context) {
NewBuiltInQualityProfile dependencyCheckWay = context.createBuiltInQualityProfile("Neutral", DependencyCheckConstants.LANGUAGE_KEY);
dependencyCheckWay.activateRule(DependencyCheckConstants.REPOSITORY_KEY, DependencyCheckConstants.RULE_KEY);
dependencyCheckWay.activateRule(DependencyCheckConstants.REPOSITORY_KEY,
DependencyCheckConstants.RULE_KEY_WITH_SECURITY_HOTSPOT);
dependencyCheckWay.done();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,6 @@ public void testExtensions() {
Plugin.Context context = new PluginContextImpl.Builder().setSonarRuntime(runtime).build();
DependencyCheckPlugin plugin = new DependencyCheckPlugin();
plugin.define(context);
assertEquals(16, context.getExtensions().size());
assertEquals(17, context.getExtensions().size());
}
}
Loading

0 comments on commit 5bed497

Please sign in to comment.