Skip to content
9 changes: 9 additions & 0 deletions vulnerabilities/importer_yielder.py
Original file line number Diff line number Diff line change
Expand Up @@ -226,6 +226,15 @@
'data_source': 'PostgreSQLDataSource',
'data_source_cfg': {},
},
{
'name': 'elixir_security',
'license': '',
'last_run': None,
'data_source': 'ElixirSecurityDataSource',
'data_source_cfg': {
'repository_url': 'https://github.com/dependabot/elixir-security-advisories'
},
},

]

Expand Down
27 changes: 14 additions & 13 deletions vulnerabilities/importers/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,24 +22,25 @@


from vulnerabilities.importers.alpine_linux import AlpineDataSource
from vulnerabilities.importers.apache_httpd import ApacheHTTPDDataSource
from vulnerabilities.importers.archlinux import ArchlinuxDataSource
from vulnerabilities.importers.debian import DebianDataSource
from vulnerabilities.importers.npm import NpmDataSource
from vulnerabilities.importers.rust import RustDataSource
from vulnerabilities.importers.safety_db import SafetyDbDataSource
from vulnerabilities.importers.ruby import RubyDataSource
from vulnerabilities.importers.ubuntu import UbuntuDataSource
from vulnerabilities.importers.retiredotnet import RetireDotnetDataSource
from vulnerabilities.importers.suse_backports import SUSEBackportsDataSource
from vulnerabilities.importers.debian_oval import DebianOvalDataSource
from vulnerabilities.importers.redhat import RedhatDataSource
from vulnerabilities.importers.elixir_security import ElixirSecurityDataSource
from vulnerabilities.importers.gentoo import GentooDataSource
from vulnerabilities.importers.openssl import OpenSSLDataSource
from vulnerabilities.importers.ubuntu_usn import UbuntuUSNDataSource
from vulnerabilities.importers.github import GitHubAPIDataSource
from vulnerabilities.importers.nvd import NVDDataSource
from vulnerabilities.importers.project_kb_msr2019 import ProjectKBMSRDataSource
from vulnerabilities.importers.apache_httpd import ApacheHTTPDDataSource
from vulnerabilities.importers.kaybee import KaybeeDataSource
from vulnerabilities.importers.nginx import NginxDataSource
from vulnerabilities.importers.npm import NpmDataSource
from vulnerabilities.importers.nvd import NVDDataSource
from vulnerabilities.importers.openssl import OpenSSLDataSource
from vulnerabilities.importers.postgresql import PostgreSQLDataSource
from vulnerabilities.importers.project_kb_msr2019 import ProjectKBMSRDataSource
from vulnerabilities.importers.redhat import RedhatDataSource
from vulnerabilities.importers.retiredotnet import RetireDotnetDataSource
from vulnerabilities.importers.ruby import RubyDataSource
from vulnerabilities.importers.rust import RustDataSource
from vulnerabilities.importers.safety_db import SafetyDbDataSource
from vulnerabilities.importers.suse_backports import SUSEBackportsDataSource
from vulnerabilities.importers.ubuntu import UbuntuDataSource
from vulnerabilities.importers.ubuntu_usn import UbuntuUSNDataSource
120 changes: 120 additions & 0 deletions vulnerabilities/importers/elixir_security.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
# Copyright (c) nexB Inc. and others. All rights reserved.
# http://nexb.com and https://github.com/nexB/vulnerablecode/
# The VulnerableCode software is licensed under the Apache License version 2.0.
# Data generated with VulnerableCode require an acknowledgment.
#
# You may not use this software except in compliance with the License.
# You may obtain a copy of the License at: http://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.
#
# When you publish or redistribute any data created with VulnerableCode or any VulnerableCode
# derivative work, you must accompany this data with the following acknowledgment:
#
# Generated with VulnerableCode and provided on an "AS IS" BASIS, WITHOUT WARRANTIES
# OR CONDITIONS OF ANY KIND, either express or implied. No content created from
# VulnerableCode should be considered or used as legal advice. Consult an Attorney
# for any legal advice.
# VulnerableCode is a free software code scanning tool from nexB Inc. and others.
# Visit https://github.com/nexB/vulnerablecode/ for support and download.

import yaml
Comment thread
tushar912 marked this conversation as resolved.
import re
import json
import requests
Comment thread
tushar912 marked this conversation as resolved.
Outdated
from typing import Set
Comment thread
tushar912 marked this conversation as resolved.
Outdated
from typing import List
from dephell_specifier import RangeSpecifier
from packageurl import PackageURL

from vulnerabilities.data_source import GitDataSource
from vulnerabilities.data_source import GitDataSourceConfiguration

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This import is not required

from vulnerabilities.data_source import Advisory
from vulnerabilities.data_source import Reference


class ElixirSecurityDataSource(GitDataSource):
def __enter__(self):
super(ElixirSecurityDataSource, self).__enter__()

if not getattr(self, "_added_files", None):
self._added_files, self._updated_files = self.file_changes(
recursive=True, file_ext="yml", subdir="./packages"
)

def updated_advisories(self) -> Set[Advisory]:
files = self._updated_files
advisories = []
for f in files:
processed_data = self.process_file(f)
if processed_data:
advisories.append(processed_data)
return self.batch_advisories(advisories)

def added_advisories(self) -> Set[Advisory]:
files = self._added_files
advisories = []
for f in files:
processed_data = self.process_file(f)
if processed_data:
advisories.append(processed_data)
return self.batch_advisories(advisories)

@staticmethod
def generate_all_version_list(pkg_name):
Comment thread
tushar912 marked this conversation as resolved.
Outdated
resp = requests.get(f"https://hex.pm/api/packages/{pkg_name}")
resp = resp.content
json_resp = json.loads(resp)
Comment thread
tushar912 marked this conversation as resolved.
Outdated
version_list = []
for release in json_resp["releases"]:
version_list.append(release["version"])
return version_list

def get_pkg_from_range(self, version_list, pkg_name):

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The function says get_pkg_from_range but returns a version list

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is get_versions_from_range better

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes

pkg_versions = []
all_version_list = self.generate_all_version_list(pkg_name)
if version_list is None:
Comment thread
sbs2001 marked this conversation as resolved.
Outdated
Comment thread
sbs2001 marked this conversation as resolved.
Outdated
return
Comment thread
sbs2001 marked this conversation as resolved.
Outdated
version_ranges = {RangeSpecifier(r) for r in version_list}
for version in all_version_list:
if any([version in v for v in version_ranges]):
pkg_versions.append(version)
return pkg_versions

def process_file(self, path):
with open(path) as f:
Comment thread
tushar912 marked this conversation as resolved.
Outdated
yaml_file = yaml.safe_load(f)
pkg_name = yaml_file["package"]
safe_pkg_versions = []
if yaml_file.get("unaffected_versions"):
safe_pkg_versions = self.get_pkg_from_range(
yaml_file["patched_versions"] + yaml_file["unaffected_versions"],
pkg_name,
)
else:
safe_pkg_versions = self.get_pkg_from_range(
yaml_file["patched_versions"], pkg_name
)
cve_id = yaml_file["cve"]
Comment thread
tushar912 marked this conversation as resolved.
Outdated
safe_purls = []
if safe_pkg_versions is not None:
safe_purls = {
PackageURL(name=pkg_name, type="hex", version=version)
for version in safe_pkg_versions
}

vuln_reference = [
Comment thread
sbs2001 marked this conversation as resolved.
Outdated
Reference(
url=yaml_file["link"],
)
]

return Advisory(
summary=yaml_file["description"],
impacted_package_urls=[],
resolved_package_urls=safe_purls,
cve_id=cve_id,
vuln_references=vuln_reference,
)
12 changes: 12 additions & 0 deletions vulnerabilities/tests/test_data/elixir_security/test_file.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
---
id: 2aae6e3a-24a3-4d5f-86ff-b964eaf7c6d1
package: coherence
disclosure_date: 2017-08-02
cve: 2018-20301
link: https://github.com/smpallen99/coherence/issues/270
title: |
Permissive parameters and privilege escalation
description: |
The Coherence library has "Mass Assignment"-like vulnerabilities.
patched_versions:
- ">= 0.5.2"
85 changes: 85 additions & 0 deletions vulnerabilities/tests/test_elixir_security.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
# Copyright (c) nexB Inc. and others. All rights reserved.
# http://nexb.com and https://github.com/nexB/vulnerablecode/
# The VulnerableCode software is licensed under the Apache License version 2.0.
# Data generated with VulnerableCode require an acknowledgment.
#
# You may not use this software except in compliance with the License.
# You may obtain a copy of the License at: http://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.
#
# When you publish or redistribute any data created with VulnerableCode or any VulnerableCode
# derivative work, you must accompany this data with the following acknowledgment:
#
# Generated with VulnerableCode and provided on an "AS IS" BASIS, WITHOUT WARRANTIES
# OR CONDITIONS OF ANY KIND, either express or implied. No content created from
# VulnerableCode should be considered or used as legal advice. Consult an Attorney
# for any legal advice.
# VulnerableCode is a free software code scanning tool from nexB Inc. and others.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are trying correct the old headers by replacing VulnerableCode is a free software code scanning tool to
VulnerableCode is a free software tool

# Visit https://github.com/nexB/vulnerablecode/ for support and download.

import os
from unittest import TestCase
from collections import OrderedDict

from vulnerabilities.data_source import Reference
Comment thread
tushar912 marked this conversation as resolved.
Outdated
from packageurl import PackageURL

from vulnerabilities.importers.elixir_security import ElixirSecurityDataSource
from vulnerabilities.data_source import Advisory
Comment thread
sbs2001 marked this conversation as resolved.
Outdated

BASE_DIR = os.path.dirname(os.path.abspath(__file__))


class TestElixirSecurityDataSource(TestCase):
@classmethod
def setUpClass(cls):
data_source_cfg = {
"repository_url": "https://test.net",
}
cls.data_src = ElixirSecurityDataSource(1, config=data_source_cfg)

def test_generate_all_version_list(self):
Comment thread
sbs2001 marked this conversation as resolved.
Outdated
package = "coherence"
actual_list = self.data_src.generate_all_version_list(package)
expected_list = [
"0.5.2",
"0.5.1",
"0.5.0",
"0.4.0",
"0.3.1",
"0.3.0",
"0.2.0",
"0.1.3",
"0.1.2",
"0.1.1",
"0.1.0",
]
assert actual_list == expected_list

def test_process_file(self):

path = os.path.join(BASE_DIR, "test_data/elixir_security/test_file.yml")
expected_data = Advisory(
summary=(
'The Coherence library has "Mass Assignment"-like vulnerabilities.\n'
),
impacted_package_urls=[],
resolved_package_urls={
PackageURL(
type="hex",
name="coherence",
version="0.5.2",
),
},
vuln_references=[
Reference(url="https://github.com/smpallen99/coherence/issues/270")
],
cve_id="2018-20301",
)

found_data = self.data_src.process_file(path)

assert expected_data == found_data