Skip to content

Commit

Permalink
refactor(scanner)!: Remove the unused ScannerConfigMatcher
Browse files Browse the repository at this point in the history
The `ScannerConfigMatcher` was intended to support cases where the
`ScannerDetails.configuration` must not be matched exactly. As the
feature was not taken into use since its introduction three years ago,
replace it with a simpler approach to match either the whole
configuration or ignore the configuration to simplify code.

Signed-off-by: Martin Nonnenmacher <martin.nonnenmacher@bosch.io>
  • Loading branch information
mnonnenmacher committed Sep 26, 2023
1 parent a84a1f4 commit fd71440
Show file tree
Hide file tree
Showing 3 changed files with 27 additions and 61 deletions.
37 changes: 11 additions & 26 deletions scanner/src/main/kotlin/ScannerCriteria.kt
Original file line number Diff line number Diff line change
Expand Up @@ -25,18 +25,6 @@ import org.ossreviewtoolkit.model.config.Options
import org.semver4j.Semver
import org.semver4j.Semver.VersionDiff

/**
* Definition of a predicate to check whether the configuration of a scanner is compatible with the requirements
* specified by a [ScannerCriteria].
*
* When testing whether a scan result is compatible with specific criteria this function is invoked on the
* scanner configuration data stored in the result. By having different, scanner-specific matcher functions, this
* compatibility check can be made very flexible.
*
* TODO: Switch to a more advanced type than String to represent the scanner configuration.
*/
typealias ScannerConfigMatcher = (String) -> Boolean

/**
* A data class defining selection criteria for scanners.
*
Expand Down Expand Up @@ -69,17 +57,12 @@ data class ScannerCriteria(
val maxVersion: Semver,

/**
* A function to check whether the configuration of a scanner is compatible with this [ScannerCriteria].
* Criterion to match the [configuration][ScannerDetails.configuration] of the scanner. If `null`, all
* configurations are matched.
*/
val configMatcher: ScannerConfigMatcher
val configuration: String?
) {
companion object {
/**
* A matcher for scanner configurations that accepts all configurations passed in. This function can be
* used if the concrete configuration of a scanner is irrelevant.
*/
val ALL_CONFIG_MATCHER: ScannerConfigMatcher = { true }

/**
* The name of the property defining the regular expression for the scanner name as part of [ScannerCriteria].
* The [scanner details][ScannerDetails] of the corresponding scanner must match the criteria.
Expand All @@ -99,10 +82,10 @@ data class ScannerCriteria(
const val PROP_CRITERIA_MAX_VERSION = "maxVersion"

/**
* A matcher for scanner configurations that accepts only exact matches of the [originalConfig]. This
* function can be used by scanners that are extremely sensitive about their configuration.
* The name of the property defining the configuration of the scanner as part of [ScannerCriteria]. The
* [scanner details][ScannerDetails] of the corresponding scanner must match the criteria.
*/
fun exactConfigMatcher(originalConfig: String): ScannerConfigMatcher = { config -> originalConfig == config }
const val PROP_CRITERIA_CONFIGURATION = "configuration"

/**
* Generate a [ScannerCriteria] instance that is compatible with the given [details] and versions that differ
Expand All @@ -122,7 +105,7 @@ data class ScannerCriteria(
regScannerName = details.name,
minVersion = minVersion,
maxVersion = maxVersion,
configMatcher = exactConfigMatcher(details.configuration)
configuration = details.configuration
)
}

Expand All @@ -138,8 +121,9 @@ data class ScannerCriteria(
val minVersion = parseVersion(options[PROP_CRITERIA_MIN_VERSION]) ?: scannerVersion
val maxVersion = parseVersion(options[PROP_CRITERIA_MAX_VERSION]) ?: minVersion.nextMinor()
val name = options[PROP_CRITERIA_NAME] ?: details.name
val configuration = options[PROP_CRITERIA_CONFIGURATION] ?: details.configuration

return ScannerCriteria(name, minVersion, maxVersion, exactConfigMatcher(details.configuration))
return ScannerCriteria(name, minVersion, maxVersion, configuration)
}
}

Expand All @@ -160,7 +144,8 @@ data class ScannerCriteria(
if (!nameRegex.matches(details.name)) return false

val version = Semver(details.version)
return minVersion <= version && version < maxVersion && configMatcher(details.configuration)
return minVersion <= version && version < maxVersion &&
(configuration == null || configuration == details.configuration)
}
}

Expand Down
45 changes: 15 additions & 30 deletions scanner/src/test/kotlin/ScannerCriteriaTest.kt
Original file line number Diff line number Diff line change
Expand Up @@ -27,22 +27,6 @@ import org.ossreviewtoolkit.model.ScannerDetails
import org.semver4j.Semver

class ScannerCriteriaTest : WordSpec({
"ScannerCriteria" should {
"provide a config matcher that accepts every configuration" {
ScannerCriteria.ALL_CONFIG_MATCHER("") shouldBe true
ScannerCriteria.ALL_CONFIG_MATCHER("foo") shouldBe true
ScannerCriteria.ALL_CONFIG_MATCHER("Supercalifragilisticexpialidocious") shouldBe true
}

"provide a config matcher that accepts only exact configuration matches" {
val orgConfig = "--info --copyright --licenses"
val matcher = ScannerCriteria.exactConfigMatcher(orgConfig)

matcher(orgConfig) shouldBe true
matcher("$orgConfig --more") shouldBe false
}
}

"ScannerCriteria.forDetails()" should {
"create criteria that only match the passed details by default" {
val criteria = ScannerCriteria.forDetails(testDetails)
Expand Down Expand Up @@ -73,20 +57,23 @@ class ScannerCriteriaTest : WordSpec({
criteria.regScannerName shouldBe SCANNER_NAME
criteria.minVersion.version shouldBe SCANNER_VERSION
criteria.maxVersion shouldBe Semver(SCANNER_VERSION).nextMinor()
criteria.configuration shouldBe SCANNER_CONFIGURATION
}

"obtain values from the configuration" {
val options = mapOf(
ScannerCriteria.PROP_CRITERIA_NAME to "foo",
ScannerCriteria.PROP_CRITERIA_MIN_VERSION to "1.2.3",
ScannerCriteria.PROP_CRITERIA_MAX_VERSION to "4.5.6"
ScannerCriteria.PROP_CRITERIA_MAX_VERSION to "4.5.6",
ScannerCriteria.PROP_CRITERIA_CONFIGURATION to "config"
)

val criteria = ScannerCriteria.create(testDetails, options)

criteria.regScannerName shouldBe "foo"
criteria.minVersion.version shouldBe "1.2.3"
criteria.maxVersion.version shouldBe "4.5.6"
criteria.configuration shouldBe "config"
}

"parse versions in a lenient way" {
Expand All @@ -100,13 +87,6 @@ class ScannerCriteriaTest : WordSpec({
criteria.minVersion.version shouldBe "1.0.0"
criteria.maxVersion.version shouldBe "3.7.0"
}

"use an exact configuration matcher" {
val criteria = ScannerCriteria.create(testDetails)

criteria.configMatcher(testDetails.configuration) shouldBe true
criteria.configMatcher(testDetails.configuration + "_other") shouldBe false
}
}

"ScannerCriteria.matches()" should {
Expand Down Expand Up @@ -144,26 +124,31 @@ class ScannerCriteriaTest : WordSpec({
criteria.matches(testDetails) shouldBe false
}

"detect a difference reported by the config matcher" {
val criteria = matchingCriteria.copy(
configMatcher = ScannerCriteria.exactConfigMatcher(testDetails.configuration + "_other")
)
"detect a scanner configuration that does not match" {
val criteria = matchingCriteria.copy(configuration = "${testDetails.configuration}_other")

criteria.matches(testDetails) shouldBe false
}

"ignore the scanner configuration if it is null" {
val criteria = matchingCriteria.copy(configuration = null)

criteria.matches(testDetails) shouldBe true
}
}
})

private const val SCANNER_NAME = "ScannerCriteriaTest"
private const val SCANNER_VERSION = "3.2.1-rc2"
private const val SCANNER_CONFIGURATION = "--command-line-option"

/** Test details to match against. */
private val testDetails = ScannerDetails(SCANNER_NAME, SCANNER_VERSION, "--command-line-option")
private val testDetails = ScannerDetails(SCANNER_NAME, SCANNER_VERSION, SCANNER_CONFIGURATION)

/** A test instance which should accept the test details. */
private val matchingCriteria = ScannerCriteria(
regScannerName = testDetails.name,
minVersion = Semver(testDetails.version),
maxVersion = Semver(testDetails.version).nextPatch(),
configMatcher = ScannerCriteria.exactConfigMatcher(testDetails.configuration)
configuration = testDetails.configuration
)
Original file line number Diff line number Diff line change
Expand Up @@ -106,11 +106,7 @@ private val TEST_PACKAGE =
)

/** The scanner details used by tests. */
private val SCANNER_CRITERIA =
ScannerCriteria(
"aScanner", Semver("1.0.0"), Semver("2.0.0"),
ScannerCriteria.exactConfigMatcher("aConfig")
)
private val SCANNER_CRITERIA = ScannerCriteria("aScanner", Semver("1.0.0"), Semver("2.0.0"), "aConfig")

/** The template for a ClearlyDefined definitions request. */
private val DEFINITIONS_TEMPLATE = readDefinitionsTemplate()
Expand Down

0 comments on commit fd71440

Please sign in to comment.