diff --git a/README.md b/README.md
index ada68187..6abe42e1 100644
--- a/README.md
+++ b/README.md
@@ -161,12 +161,14 @@ By indexing the features of an image into the database, images only need to be r
| [Debian Security Bug Tracker] | Debian 6, 7, 8, unstable namespaces | [dpkg] | [Debian] |
| [Ubuntu CVE Tracker] | Ubuntu 12.04, 12.10, 13.04, 14.04, 14.10, 15.04, 15.10, 16.04 namespaces | [dpkg] | [GPLv2] |
| [Red Hat Security Data] | CentOS 5, 6, 7 namespaces | [rpm] | [CVRF] |
+| [Oracle Linux Security Data] | Oracle Linux 5, 6, 7 namespaces | [rpm] | [CVRF] |
| [Alpine SecDB] | Alpine 3.3, Alpine 3.4 namespaces | [apk] | [MIT] |
| [NVD] | Generic Vulnerability Metadata | N/A | [Public Domain] |
[Debian Security Bug Tracker]: https://security-tracker.debian.org/tracker
[Ubuntu CVE Tracker]: https://launchpad.net/ubuntu-cve-tracker
[Red Hat Security Data]: https://www.redhat.com/security/data/metrics
+[Oracle Linux Security Data]: https://linux.oracle.com/security/
[NVD]: https://nvd.nist.gov
[dpkg]: https://en.wikipedia.org/wiki/dpkg
[rpm]: http://www.rpm.org
diff --git a/cmd/clair/main.go b/cmd/clair/main.go
index 043977cc..1e3735d8 100644
--- a/cmd/clair/main.go
+++ b/cmd/clair/main.go
@@ -30,6 +30,7 @@ import (
_ "github.com/coreos/clair/updater/fetchers/alpine"
_ "github.com/coreos/clair/updater/fetchers/debian"
+ _ "github.com/coreos/clair/updater/fetchers/oracle"
_ "github.com/coreos/clair/updater/fetchers/rhel"
_ "github.com/coreos/clair/updater/fetchers/ubuntu"
_ "github.com/coreos/clair/updater/metadata_fetchers/nvd"
diff --git a/updater/fetchers/oracle/oracle.go b/updater/fetchers/oracle/oracle.go
new file mode 100644
index 00000000..5d8f942c
--- /dev/null
+++ b/updater/fetchers/oracle/oracle.go
@@ -0,0 +1,356 @@
+// Copyright 2015 clair authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package oracle
+
+import (
+ "bufio"
+ "encoding/xml"
+ "io"
+ "net/http"
+ "regexp"
+ "strconv"
+ "strings"
+
+ "github.com/coreos/clair/database"
+ "github.com/coreos/clair/updater"
+ cerrors "github.com/coreos/clair/utils/errors"
+ "github.com/coreos/clair/utils/types"
+ "github.com/coreos/pkg/capnslog"
+)
+
+const (
+ firstOracle5ELSA = 20070057
+ ovalURI = "https://linux.oracle.com/oval/"
+ elsaFilePrefix = "com.oracle.elsa-"
+ updaterFlag = "oracleUpdater"
+)
+
+var (
+ ignoredCriterions = []string{
+ " is signed with the Oracle Linux",
+ ".ksplice1.",
+ }
+
+ elsaRegexp = regexp.MustCompile(`com.oracle.elsa-(\d+).xml`)
+
+ log = capnslog.NewPackageLogger("github.com/coreos/clair", "updater/fetchers/oracle")
+)
+
+type oval struct {
+ Definitions []definition `xml:"definitions>definition"`
+}
+
+type definition struct {
+ Title string `xml:"metadata>title"`
+ Description string `xml:"metadata>description"`
+ References []reference `xml:"metadata>reference"`
+ Criteria criteria `xml:"criteria"`
+ Severity string `xml:"metadata>advisory>severity"`
+}
+
+type reference struct {
+ Source string `xml:"source,attr"`
+ URI string `xml:"ref_url,attr"`
+}
+
+type criteria struct {
+ Operator string `xml:"operator,attr"`
+ Criterias []*criteria `xml:"criteria"`
+ Criterions []criterion `xml:"criterion"`
+}
+
+type criterion struct {
+ Comment string `xml:"comment,attr"`
+}
+
+// OracleFetcher implements updater.Fetcher and gets vulnerability updates from
+// the Oracle Linux OVAL definitions.
+type OracleFetcher struct{}
+
+func init() {
+ updater.RegisterFetcher("Oracle", &OracleFetcher{})
+}
+
+// FetchUpdate gets vulnerability updates from the Oracle Linux OVAL definitions.
+func (f *OracleFetcher) FetchUpdate(datastore database.Datastore) (resp updater.FetcherResponse, err error) {
+ log.Info("fetching Oracle Linux vulnerabilities")
+
+ // Get the first ELSA we have to manage.
+ flagValue, err := datastore.GetKeyValue(updaterFlag)
+ if err != nil {
+ return resp, err
+ }
+
+ firstELSA, err := strconv.Atoi(flagValue)
+ if firstELSA == 0 || err != nil {
+ firstELSA = firstOracle5ELSA
+ }
+
+
+ // Fetch the update list.
+ r, err := http.Get(ovalURI)
+ if err != nil {
+ log.Errorf("could not download Oracle's update list: %s", err)
+ return resp, cerrors.ErrCouldNotDownload
+ }
+ defer r.Body.Close()
+
+ // Get the list of ELSAs that we have to process.
+ var elsaList []int
+ scanner := bufio.NewScanner(r.Body)
+ for scanner.Scan() {
+ line := scanner.Text()
+ r := elsaRegexp.FindStringSubmatch(line)
+ if len(r) == 2 {
+ elsaNo, _ := strconv.Atoi(r[1])
+ if elsaNo > firstELSA {
+ elsaList = append(elsaList, elsaNo)
+ }
+ }
+ }
+
+ for _, elsa := range elsaList {
+ // Download the ELSA's XML file.
+ r, err := http.Get(ovalURI + elsaFilePrefix + strconv.Itoa(elsa) + ".xml")
+ if err != nil {
+ log.Errorf("could not download Oracle's update file: %s", err)
+ return resp, cerrors.ErrCouldNotDownload
+ }
+
+ // Parse the XML.
+ vs, err := parseELSA(r.Body)
+ if err != nil {
+ return resp, err
+ }
+
+ // Collect vulnerabilities.
+ for _, v := range vs {
+ resp.Vulnerabilities = append(resp.Vulnerabilities, v)
+ }
+ }
+
+ // Set the flag if we found anything.
+ if len(elsaList) > 0 {
+ resp.FlagName = updaterFlag
+ resp.FlagValue = strconv.Itoa(elsaList[len(elsaList)-1])
+ } else {
+ log.Debug("no Oracle Linux update.")
+ }
+
+ return resp, nil
+}
+
+func parseELSA(ovalReader io.Reader) (vulnerabilities []database.Vulnerability, err error) {
+ // Decode the XML.
+ var ov oval
+ err = xml.NewDecoder(ovalReader).Decode(&ov)
+ if err != nil {
+ log.Errorf("could not decode Oracle's XML: %s", err)
+ err = cerrors.ErrCouldNotParse
+ return
+ }
+
+ // Iterate over the definitions and collect any vulnerabilities that affect
+ // at least one package.
+ for _, definition := range ov.Definitions {
+ pkgs := toFeatureVersions(definition.Criteria)
+ if len(pkgs) > 0 {
+ vulnerability := database.Vulnerability{
+ Name: name(definition),
+ Link: link(definition),
+ Severity: priority(definition),
+ Description: description(definition),
+ }
+ for _, p := range pkgs {
+ vulnerability.FixedIn = append(vulnerability.FixedIn, p)
+ }
+ vulnerabilities = append(vulnerabilities, vulnerability)
+ }
+ }
+
+ return
+}
+
+func getCriterions(node criteria) [][]criterion {
+ // Filter useless criterions.
+ var criterions []criterion
+ for _, c := range node.Criterions {
+ ignored := false
+
+ for _, ignoredItem := range ignoredCriterions {
+ if strings.Contains(c.Comment, ignoredItem) {
+ ignored = true
+ break
+ }
+ }
+
+ if !ignored {
+ criterions = append(criterions, c)
+ }
+ }
+
+ if node.Operator == "AND" {
+ return [][]criterion{criterions}
+ } else if node.Operator == "OR" {
+ var possibilities [][]criterion
+ for _, c := range criterions {
+ possibilities = append(possibilities, []criterion{c})
+ }
+ return possibilities
+ }
+
+ return [][]criterion{}
+}
+
+func getPossibilities(node criteria) [][]criterion {
+ if len(node.Criterias) == 0 {
+ return getCriterions(node)
+ }
+
+ var possibilitiesToCompose [][][]criterion
+ for _, criteria := range node.Criterias {
+ possibilitiesToCompose = append(possibilitiesToCompose, getPossibilities(*criteria))
+ }
+ if len(node.Criterions) > 0 {
+ possibilitiesToCompose = append(possibilitiesToCompose, getCriterions(node))
+ }
+
+ var possibilities [][]criterion
+ if node.Operator == "AND" {
+ for _, possibility := range possibilitiesToCompose[0] {
+ possibilities = append(possibilities, possibility)
+ }
+
+ for _, possibilityGroup := range possibilitiesToCompose[1:] {
+ var newPossibilities [][]criterion
+
+ for _, possibility := range possibilities {
+ for _, possibilityInGroup := range possibilityGroup {
+ var p []criterion
+ p = append(p, possibility...)
+ p = append(p, possibilityInGroup...)
+ newPossibilities = append(newPossibilities, p)
+ }
+ }
+
+ possibilities = newPossibilities
+ }
+ } else if node.Operator == "OR" {
+ for _, possibilityGroup := range possibilitiesToCompose {
+ for _, possibility := range possibilityGroup {
+ possibilities = append(possibilities, possibility)
+ }
+ }
+ }
+
+ return possibilities
+}
+
+func toFeatureVersions(criteria criteria) []database.FeatureVersion {
+ // There are duplicates in Oracle .xml files.
+ // This map is for deduplication.
+ featureVersionParameters := make(map[string]database.FeatureVersion)
+
+ possibilities := getPossibilities(criteria)
+ for _, criterions := range possibilities {
+ var (
+ featureVersion database.FeatureVersion
+ osVersion int
+ err error
+ )
+
+ // Attempt to parse package data from trees of criterions.
+ for _, c := range criterions {
+ if strings.Contains(c.Comment, " is installed") {
+ const prefixLen = len("Oracle Linux ")
+ osVersion, err = strconv.Atoi(strings.TrimSpace(c.Comment[prefixLen : prefixLen+strings.Index(c.Comment[prefixLen:], " ")]))
+ if err != nil {
+ log.Warningf("could not parse Oracle Linux release version from: '%s'.", c.Comment)
+ }
+ } else if strings.Contains(c.Comment, " is earlier than ") {
+ const prefixLen = len(" is earlier than ")
+ featureVersion.Feature.Name = strings.TrimSpace(c.Comment[:strings.Index(c.Comment, " is earlier than ")])
+ featureVersion.Version, err = types.NewVersion(c.Comment[strings.Index(c.Comment, " is earlier than ")+prefixLen:])
+ if err != nil {
+ log.Warningf("could not parse package version '%s': %s. skipping", c.Comment[strings.Index(c.Comment, " is earlier than ")+prefixLen:], err.Error())
+ }
+ }
+ }
+
+ featureVersion.Feature.Namespace.Name = "oracle" + ":" + strconv.Itoa(osVersion)
+
+ if featureVersion.Feature.Namespace.Name != "" && featureVersion.Feature.Name != "" && featureVersion.Version.String() != "" {
+ featureVersionParameters[featureVersion.Feature.Namespace.Name+":"+featureVersion.Feature.Name] = featureVersion
+ } else {
+ log.Warningf("could not determine a valid package from criterions: %v", criterions)
+ }
+ }
+
+ // Convert the map to slice.
+ var featureVersionParametersArray []database.FeatureVersion
+ for _, fv := range featureVersionParameters {
+ featureVersionParametersArray = append(featureVersionParametersArray, fv)
+ }
+
+ return featureVersionParametersArray
+}
+
+func description(def definition) (desc string) {
+ // It is much more faster to proceed like this than using a Replacer.
+ desc = strings.Replace(def.Description, "\n\n\n", " ", -1)
+ desc = strings.Replace(desc, "\n\n", " ", -1)
+ desc = strings.Replace(desc, "\n", " ", -1)
+ return
+}
+
+func name(def definition) string {
+ return strings.TrimSpace(def.Title[:strings.Index(def.Title, ": ")])
+}
+
+func link(def definition) (link string) {
+ for _, reference := range def.References {
+ if reference.Source == "elsa" {
+ link = reference.URI
+ break
+ }
+ }
+
+ return
+}
+
+func priority(def definition) types.Priority {
+ // Parse the priority.
+ priority := strings.ToLower(def.Severity)
+
+ // Normalize the priority.
+ switch priority {
+ case "n/a":
+ return types.Negligible
+ case "low":
+ return types.Low
+ case "moderate":
+ return types.Medium
+ case "important":
+ return types.High
+ case "critical":
+ return types.Critical
+ default:
+ log.Warningf("could not determine vulnerability priority from: %s.", priority)
+ return types.Unknown
+ }
+}
+
+// Clean deletes any allocated resources.
+func (f *OracleFetcher) Clean() {}
diff --git a/updater/fetchers/oracle/oracle_test.go b/updater/fetchers/oracle/oracle_test.go
new file mode 100644
index 00000000..70855fdf
--- /dev/null
+++ b/updater/fetchers/oracle/oracle_test.go
@@ -0,0 +1,102 @@
+// Copyright 2015 clair authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package oracle
+
+import (
+ "os"
+ "path/filepath"
+ "runtime"
+ "testing"
+
+ "github.com/coreos/clair/database"
+ "github.com/coreos/clair/utils/types"
+ "github.com/stretchr/testify/assert"
+)
+
+func TestOracleParser(t *testing.T) {
+ _, filename, _, _ := runtime.Caller(0)
+ path := filepath.Join(filepath.Dir(filename))
+
+ // Test parsing testdata/fetcher_oracle_test.1.xml
+ testFile, _ := os.Open(path + "/testdata/fetcher_oracle_test.1.xml")
+ defer testFile.Close()
+
+ vulnerabilities, err := parseELSA(testFile)
+ if assert.Nil(t, err) && assert.Len(t, vulnerabilities, 1) {
+ assert.Equal(t, "ELSA-2015-1193", vulnerabilities[0].Name)
+ assert.Equal(t, "http://linux.oracle.com/errata/ELSA-2015-1193.html", vulnerabilities[0].Link)
+ assert.Equal(t, types.Medium, vulnerabilities[0].Severity)
+ assert.Equal(t, ` [3.1.1-7] Resolves: rhbz#1217104 CVE-2015-0252 `, vulnerabilities[0].Description)
+
+ expectedFeatureVersions := []database.FeatureVersion{
+ {
+ Feature: database.Feature{
+ Namespace: database.Namespace{Name: "oracle:7"},
+ Name: "xerces-c",
+ },
+ Version: types.NewVersionUnsafe("3.1.1-7.el7_1"),
+ },
+ {
+ Feature: database.Feature{
+ Namespace: database.Namespace{Name: "oracle:7"},
+ Name: "xerces-c-devel",
+ },
+ Version: types.NewVersionUnsafe("3.1.1-7.el7_1"),
+ },
+ {
+ Feature: database.Feature{
+ Namespace: database.Namespace{Name: "oracle:7"},
+ Name: "xerces-c-doc",
+ },
+ Version: types.NewVersionUnsafe("3.1.1-7.el7_1"),
+ },
+ }
+
+ for _, expectedFeatureVersion := range expectedFeatureVersions {
+ assert.Contains(t, vulnerabilities[0].FixedIn, expectedFeatureVersion)
+ }
+ }
+
+ testFile2, _ := os.Open(path + "/testdata/fetcher_oracle_test.2.xml")
+ defer testFile2.Close()
+
+ vulnerabilities, err = parseELSA(testFile2)
+ if assert.Nil(t, err) && assert.Len(t, vulnerabilities, 1) {
+ assert.Equal(t, "ELSA-2015-1207", vulnerabilities[0].Name)
+ assert.Equal(t, "http://linux.oracle.com/errata/ELSA-2015-1207.html", vulnerabilities[0].Link)
+ assert.Equal(t, types.Critical, vulnerabilities[0].Severity)
+ assert.Equal(t, ` [38.1.0-1.0.1.el7_1] - Add firefox-oracle-default-prefs.js and remove the corresponding Red Hat file [38.1.0-1] - Update to 38.1.0 ESR [38.0.1-2] - Fixed rhbz#1222807 by removing preun section `, vulnerabilities[0].Description)
+ expectedFeatureVersions := []database.FeatureVersion{
+ {
+ Feature: database.Feature{
+ Namespace: database.Namespace{Name: "oracle:6"},
+ Name: "firefox",
+ },
+ Version: types.NewVersionUnsafe("38.1.0-1.0.1.el6_6"),
+ },
+ {
+ Feature: database.Feature{
+ Namespace: database.Namespace{Name: "oracle:7"},
+ Name: "firefox",
+ },
+ Version: types.NewVersionUnsafe("38.1.0-1.0.1.el7_1"),
+ },
+ }
+
+ for _, expectedFeatureVersion := range expectedFeatureVersions {
+ assert.Contains(t, vulnerabilities[0].FixedIn, expectedFeatureVersion)
+ }
+ }
+}
diff --git a/updater/fetchers/oracle/testdata/fetcher_oracle_test.1.xml b/updater/fetchers/oracle/testdata/fetcher_oracle_test.1.xml
new file mode 100644
index 00000000..e1629441
--- /dev/null
+++ b/updater/fetchers/oracle/testdata/fetcher_oracle_test.1.xml
@@ -0,0 +1,120 @@
+
+
+Oracle Errata System
+Oracle Linux
+5.3
+2015-06-29T00:00:00
+
+
+
+
+
+ELSA-2015-1193: xerces-c security update (MODERATE)
+
+
+Oracle Linux 7
+
+
+
+
+
+
+[3.1.1-7]
+Resolves: rhbz#1217104 CVE-2015-0252
+
+
+
+MODERATE
+Copyright 2015 Oracle, Inc.
+
+CVE-2015-0252
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+xerces-c-doc
+
+
+xerces-c-devel
+
+
+xerces-c
+
+
+oraclelinux-release
+
+
+
+
+
+72f97b74ec551f03
+
+^7
+
+0:3.1.1-7.el7_1
+
+
+
+
diff --git a/updater/fetchers/oracle/testdata/fetcher_oracle_test.2.xml b/updater/fetchers/oracle/testdata/fetcher_oracle_test.2.xml
new file mode 100644
index 00000000..89b290e6
--- /dev/null
+++ b/updater/fetchers/oracle/testdata/fetcher_oracle_test.2.xml
@@ -0,0 +1,177 @@
+
+
+Oracle Errata System
+Oracle Linux
+5.3
+2015-07-03T00:00:00
+
+
+
+
+
+ELSA-2015-1207: firefox security update (CRITICAL)
+
+
+Oracle Linux 5
+Oracle Linux 6
+Oracle Linux 7
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+[38.1.0-1.0.1.el7_1]
+- Add firefox-oracle-default-prefs.js and remove the corresponding Red Hat file
+
+[38.1.0-1]
+- Update to 38.1.0 ESR
+
+[38.0.1-2]
+- Fixed rhbz#1222807 by removing preun section
+
+
+
+CRITICAL
+Copyright 2015 Oracle, Inc.
+
+CVE-2015-2722
+CVE-2015-2724
+CVE-2015-2725
+CVE-2015-2727
+CVE-2015-2728
+CVE-2015-2729
+CVE-2015-2731
+CVE-2015-2733
+CVE-2015-2734
+CVE-2015-2735
+CVE-2015-2736
+CVE-2015-2737
+CVE-2015-2738
+CVE-2015-2739
+CVE-2015-2740
+CVE-2015-2741
+CVE-2015-2743
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+firefox
+
+
+oraclelinux-release
+
+
+
+
+
+66ced3de1e5e0159
+
+72f97b74ec551f03
+
+^5
+
+0:38.1.0-1.0.1.el5_11
+
+^6
+
+0:38.1.0-1.0.1.el6_6
+
+^7
+
+0:38.1.0-1.0.1.el7_1
+
+
+
+
diff --git a/worker/detectors/namespace/osrelease/osrelease.go b/worker/detectors/namespace/osrelease/osrelease.go
index b3039629..ad0593f2 100644
--- a/worker/detectors/namespace/osrelease/osrelease.go
+++ b/worker/detectors/namespace/osrelease/osrelease.go
@@ -85,5 +85,5 @@ func (detector *OsReleaseNamespaceDetector) GetRequiredFiles() []string {
// getExcludeFiles returns the list of files that are ought to exclude this detector from Detect()
func (detector *OsReleaseNamespaceDetector) getExcludeFiles() []string {
- return []string{"etc/redhat-release", "usr/lib/centos-release"}
+ return []string{"etc/oracle-release", "etc/redhat-release", "usr/lib/centos-release"}
}
diff --git a/worker/detectors/namespace/redhatrelease/redhatrelease.go b/worker/detectors/namespace/redhatrelease/redhatrelease.go
index 91e236c7..7dcf445e 100644
--- a/worker/detectors/namespace/redhatrelease/redhatrelease.go
+++ b/worker/detectors/namespace/redhatrelease/redhatrelease.go
@@ -26,17 +26,19 @@ import (
var (
log = capnslog.NewPackageLogger("github.com/coreos/clair", "worker/detectors/namespace/redhatrelease")
+ oracleReleaseRegexp = regexp.MustCompile(`(?P[^\s]*) (Linux Server release) (?P[\d]+)`)
centosReleaseRegexp = regexp.MustCompile(`(?P[^\s]*) (Linux release|release) (?P[\d]+)`)
redhatReleaseRegexp = regexp.MustCompile(`(?PRed Hat Enterprise Linux) (Client release|Server release|Workstation release) (?P[\d]+)`)
)
// RedhatReleaseNamespaceDetector implements NamespaceDetector and detects the OS from the
-// /etc/centos-release, /etc/redhat-release and /etc/system-release files.
+// /etc/oracle-release, /etc/centos-release, /etc/redhat-release and /etc/system-release files.
//
// Typically for CentOS and Red-Hat like systems
// eg. CentOS release 5.11 (Final)
// eg. CentOS release 6.6 (Final)
// eg. CentOS Linux release 7.1.1503 (Core)
+// eg. Oracle Linux Server release 7.3
// eg. Red Hat Enterprise Linux Server release 7.2 (Maipo)
type RedhatReleaseNamespaceDetector struct{}
@@ -53,6 +55,12 @@ func (detector *RedhatReleaseNamespaceDetector) Detect(data map[string][]byte) *
var r []string
+ // try for Oracle Linux
+ r = oracleReleaseRegexp.FindStringSubmatch(string(f))
+ if len(r) == 4 {
+ return &database.Namespace{Name: strings.ToLower(r[1]) + ":" + r[3]}
+ }
+
// try for RHEL
r = redhatReleaseRegexp.FindStringSubmatch(string(f))
if len(r) == 4 {
@@ -73,5 +81,5 @@ func (detector *RedhatReleaseNamespaceDetector) Detect(data map[string][]byte) *
// GetRequiredFiles returns the list of files that are required for Detect()
func (detector *RedhatReleaseNamespaceDetector) GetRequiredFiles() []string {
- return []string{"etc/centos-release", "etc/redhat-release", "etc/system-release"}
+ return []string{"etc/oracle-release", "etc/centos-release", "etc/redhat-release", "etc/system-release"}
}
diff --git a/worker/detectors/namespace/redhatrelease/redhatrelease_test.go b/worker/detectors/namespace/redhatrelease/redhatrelease_test.go
index 75e470f6..dc360545 100644
--- a/worker/detectors/namespace/redhatrelease/redhatrelease_test.go
+++ b/worker/detectors/namespace/redhatrelease/redhatrelease_test.go
@@ -23,6 +23,18 @@ import (
func TestRedhatReleaseNamespaceDetector(t *testing.T) {
testData := []namespace.TestData{
+ {
+ ExpectedNamespace: &database.Namespace{Name: "oracle:6"},
+ Data: map[string][]byte{
+ "etc/oracle-release": []byte(`Oracle Linux Server release 6.8`),
+ },
+ },
+ {
+ ExpectedNamespace: &database.Namespace{Name: "oracle:7"},
+ Data: map[string][]byte{
+ "etc/oracle-release": []byte(`Oracle Linux Server release 7.2`),
+ },
+ },
{
ExpectedNamespace: &database.Namespace{Name: "centos:6"},
Data: map[string][]byte{