update to ensure NodePackageAnalyzer will not run without a backing vulnerability analyzer

This commit is contained in:
Jeremy Long
2017-11-20 06:46:25 -05:00
parent a754a8e6b4
commit e4b7f7aa8f
8 changed files with 86 additions and 6 deletions

View File

@@ -1038,6 +1038,15 @@ public class Engine implements FileFilter, AutoCloseable {
return settings; return settings;
} }
/**
* Returns the mode of the engine.
*
* @return the mode of the engine
*/
public Mode getMode() {
return mode;
}
/** /**
* Adds a file type analyzer. This has been added solely to assist in unit * Adds a file type analyzer. This has been added solely to assist in unit
* testing the Engine. * testing the Engine.

View File

@@ -30,6 +30,8 @@ import org.slf4j.LoggerFactory;
import java.io.File; import java.io.File;
import java.io.FileFilter; import java.io.FileFilter;
import java.io.IOException; import java.io.IOException;
import java.util.Arrays;
import java.util.List;
import java.util.Map; import java.util.Map;
import javax.annotation.concurrent.ThreadSafe; import javax.annotation.concurrent.ThreadSafe;
import javax.json.Json; import javax.json.Json;
@@ -38,8 +40,10 @@ import javax.json.JsonObject;
import javax.json.JsonReader; import javax.json.JsonReader;
import javax.json.JsonString; import javax.json.JsonString;
import javax.json.JsonValue; import javax.json.JsonValue;
import org.owasp.dependencycheck.Engine.Mode;
import org.owasp.dependencycheck.exception.InitializationException; import org.owasp.dependencycheck.exception.InitializationException;
import org.owasp.dependencycheck.dependency.EvidenceType; import org.owasp.dependencycheck.dependency.EvidenceType;
import org.owasp.dependencycheck.utils.InvalidSettingException;
/** /**
* Used to analyze Node Package Manager (npm) package.json files, and collect * Used to analyze Node Package Manager (npm) package.json files, and collect
@@ -87,9 +91,35 @@ public class NodePackageAnalyzer extends AbstractFileTypeAnalyzer {
return PACKAGE_JSON_FILTER; return PACKAGE_JSON_FILTER;
} }
/**
* Performs validation on the configuration to ensure that the correct
* analyzers are in place.
*
* @param engine the dependency-check engine
* @throws InitializationException thrown if there is a configuration error
*/
@Override @Override
protected void prepareFileTypeAnalyzer(Engine engine) throws InitializationException { protected void prepareFileTypeAnalyzer(Engine engine) throws InitializationException {
// NO-OP if (engine.getMode() != Mode.EVIDENCE_COLLECTION) {
try {
Settings settings = engine.getSettings();
final String[] tmp = settings.getArray(Settings.KEYS.ECOSYSTEM_SKIP_NVDCVE);
if (tmp != null) {
List<String> skipEcosystems = Arrays.asList(tmp);
if (skipEcosystems.contains(DEPENDENCY_ECOSYSTEM)
&& !settings.getBoolean(Settings.KEYS.ANALYZER_NSP_PACKAGE_ENABLED)) {
LOGGER.debug("NodePackageAnalyzer enabled without a corresponding vulnerability analyzer");
final String msg = "Invalid Configuration: enabling the Node Package Analyzer without "
+ "using the NSP Analyzer is not supported.";
throw new InitializationException(msg);
} else if (!skipEcosystems.contains(DEPENDENCY_ECOSYSTEM)) {
LOGGER.warn("Using the NVD CVE Analyzer with Node.js can result in many false positives.");
}
}
} catch (InvalidSettingException ex) {
throw new InitializationException("Unable to read configuration settings", ex);
}
}
} }
/** /**
@@ -144,6 +174,7 @@ public class NodePackageAnalyzer extends AbstractFileTypeAnalyzer {
/** /**
* Collects evidence from the given JSON for the associated dependency. * Collects evidence from the given JSON for the associated dependency.
*
* @param json the JSON that contains the evidence to collect * @param json the JSON that contains the evidence to collect
* @param dependency the dependency to add the evidence too * @param dependency the dependency to add the evidence too
*/ */

View File

@@ -75,7 +75,7 @@ public class NspAnalyzer extends AbstractFileTypeAnalyzer {
* A descriptor for the type of dependencies processed or added by this * A descriptor for the type of dependencies processed or added by this
* analyzer. * analyzer.
*/ */
public static final String DEPENDENCY_ECOSYSTEM = "npm"; public static final String DEPENDENCY_ECOSYSTEM = NodePackageAnalyzer.DEPENDENCY_ECOSYSTEM;
/** /**
* The file name to scan. * The file name to scan.
*/ */

View File

@@ -17,7 +17,10 @@
*/ */
package org.owasp.dependencycheck.analyzer; package org.owasp.dependencycheck.analyzer;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List; import java.util.List;
import java.util.Set;
import javax.annotation.concurrent.ThreadSafe; import javax.annotation.concurrent.ThreadSafe;
import org.owasp.dependencycheck.Engine; import org.owasp.dependencycheck.Engine;
import org.owasp.dependencycheck.analyzer.exception.AnalysisException; import org.owasp.dependencycheck.analyzer.exception.AnalysisException;
@@ -27,6 +30,7 @@ import org.owasp.dependencycheck.dependency.Dependency;
import org.owasp.dependencycheck.dependency.Identifier; import org.owasp.dependencycheck.dependency.Identifier;
import org.owasp.dependencycheck.dependency.Vulnerability; import org.owasp.dependencycheck.dependency.Vulnerability;
import org.owasp.dependencycheck.utils.Settings; import org.owasp.dependencycheck.utils.Settings;
import org.slf4j.LoggerFactory;
/** /**
* NvdCveAnalyzer is a utility class that takes a project dependency and * NvdCveAnalyzer is a utility class that takes a project dependency and
@@ -41,7 +45,27 @@ public class NvdCveAnalyzer extends AbstractAnalyzer {
/** /**
* The Logger for use throughout the class * The Logger for use throughout the class
*/ */
//private static final org.slf4j.Logger LOGGER = LoggerFactory.getLogger(NvdCveAnalyzer.class); private static final org.slf4j.Logger LOGGER = LoggerFactory.getLogger(NvdCveAnalyzer.class);
private List<String> skipEcosystems;
/**
* Initializes the analyzer with the configured settings.
*
* @param settings the configured settings to use
*/
@Override
public void initialize(Settings settings) {
super.initialize(settings);
final String[] tmp = settings.getArray(Settings.KEYS.ECOSYSTEM_SKIP_NVDCVE);
if (tmp == null) {
skipEcosystems = new ArrayList<>();
} else {
LOGGER.info("Skipping NVD CVE Analysis for {}", tmp);
skipEcosystems = Arrays.asList(tmp);
}
}
/** /**
* Analyzes a dependency and attempts to determine if there are any CPE * Analyzes a dependency and attempts to determine if there are any CPE
* identifiers for this dependency. * identifiers for this dependency.
@@ -53,6 +77,10 @@ public class NvdCveAnalyzer extends AbstractAnalyzer {
*/ */
@Override @Override
protected void analyzeDependency(Dependency dependency, Engine engine) throws AnalysisException { protected void analyzeDependency(Dependency dependency, Engine engine) throws AnalysisException {
if (skipEcosystems.contains(dependency.getEcosystem())) {
return;
}
final CveDB cveDB = engine.getDatabase(); final CveDB cveDB = engine.getDatabase();
for (Identifier id : dependency.getIdentifiers()) { for (Identifier id : dependency.getIdentifiers()) {
if ("cpe".equals(id.getType())) { if ("cpe".equals(id.getType())) {

View File

@@ -127,3 +127,5 @@ analyzer.vulnerabilitysuppression.enabled=true
updater.nvdcve.enabled=true updater.nvdcve.enabled=true
updater.versioncheck.enabled=true updater.versioncheck.enabled=true
analyzer.versionfilter.enabled=true analyzer.versionfilter.enabled=true
ecosystem.skip.nvdcve=npm

View File

@@ -29,6 +29,7 @@ import java.io.File;
import static org.hamcrest.CoreMatchers.containsString; import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.is; import static org.hamcrest.CoreMatchers.is;
import static org.junit.Assert.*; import static org.junit.Assert.*;
import org.owasp.dependencycheck.Engine;
import org.owasp.dependencycheck.dependency.EvidenceType; import org.owasp.dependencycheck.dependency.EvidenceType;
/** /**
@@ -42,6 +43,7 @@ public class NodePackageAnalyzerTest extends BaseTest {
* The analyzer to test. * The analyzer to test.
*/ */
private NodePackageAnalyzer analyzer; private NodePackageAnalyzer analyzer;
private Engine engine;
/** /**
* Correctly setup the analyzer for testing. * Correctly setup the analyzer for testing.
@@ -52,14 +54,15 @@ public class NodePackageAnalyzerTest extends BaseTest {
@Override @Override
public void setUp() throws Exception { public void setUp() throws Exception {
super.setUp(); super.setUp();
engine = new Engine(this.getSettings());
analyzer = new NodePackageAnalyzer(); analyzer = new NodePackageAnalyzer();
analyzer.setFilesMatched(true); analyzer.setFilesMatched(true);
analyzer.initialize(getSettings()); analyzer.initialize(getSettings());
analyzer.prepare(null); analyzer.prepare(engine);
} }
/** /**
* Cleanup the analyzer's temp files, etc. * Cleanup temp files, close resources, etc.
* *
* @throws Exception thrown if there is a problem * @throws Exception thrown if there is a problem
*/ */
@@ -67,6 +70,7 @@ public class NodePackageAnalyzerTest extends BaseTest {
@Override @Override
public void tearDown() throws Exception { public void tearDown() throws Exception {
analyzer.close(); analyzer.close();
engine.close();
super.tearDown(); super.tearDown();
} }

View File

@@ -123,3 +123,5 @@ analyzer.nvdcve.enabled=true
analyzer.vulnerabilitysuppression.enabled=true analyzer.vulnerabilitysuppression.enabled=true
updater.nvdcve.enabled=true updater.nvdcve.enabled=true
updater.versioncheck.enabled=true updater.versioncheck.enabled=true
ecosystem.skip.nvdcve=npm

View File

@@ -442,6 +442,10 @@ public final class Settings {
* new version available. * new version available.
*/ */
public static final String UPDATE_VERSION_CHECK_ENABLED = "updater.versioncheck.enabled"; public static final String UPDATE_VERSION_CHECK_ENABLED = "updater.versioncheck.enabled";
/**
* The key to determine which ecosystems should skip the NVD CVE analysis.
*/
public static final String ECOSYSTEM_SKIP_NVDCVE = "ecosystem.skip.nvdcve";
/** /**
* private constructor because this is a "utility" class containing * private constructor because this is a "utility" class containing