Skip to content

Commit 216d936

Browse files
authored
Retain empty group for npm to perform strict search (#193)
* Retain empty group for npm to perform strict search Signed-off-by: Prabhu Subramanian <[email protected]> * Fix tests Signed-off-by: Prabhu Subramanian <[email protected]> --------- Signed-off-by: Prabhu Subramanian <[email protected]>
1 parent f1e49bc commit 216d936

File tree

4 files changed

+102
-59
lines changed

4 files changed

+102
-59
lines changed

README.md

Lines changed: 52 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,12 @@ OWASP dep-scan is a next-generation security and risk audit tool based on known
99

1010
## Features
1111

12-
- Scan most application code - local repos, Linux container images, Kubernetes manifests, and OS - to identify known CVEs with prioritization
13-
- Perform advanced reachability analysis for multiple languages (See reachability analysis)
14-
- Package vulnerability scanning is performed locally and is quite fast. No server is used!
15-
- Generate Software Bill-of-Materials (SBOM) with Vulnerability Disclosure Report (VDR) information
16-
- Generate a Common Security Advisory Framework (CSAF) 2.0 VEX document (check out the [CSAF Readme](contrib/CSAF_README.md))
17-
- Perform deep packages risk audit for dependency confusion attacks and maintenance risks (See risk audit)
12+
- Scan most application code - local repos, Linux container images, Kubernetes manifests, and OS - to identify known CVEs with prioritization
13+
- Perform advanced reachability analysis for multiple languages (See reachability analysis)
14+
- Package vulnerability scanning is performed locally and is quite fast. No server is used!
15+
- Generate Software Bill-of-Materials (SBOM) with Vulnerability Disclosure Report (VDR) information
16+
- Generate a Common Security Advisory Framework (CSAF) 2.0 VEX document (check out the [CSAF Readme](contrib/CSAF_README.md))
17+
- Perform deep packages risk audit for dependency confusion attacks and maintenance risks (See risk audit)
1818

1919
![Reachable Flows](docs/depscan-flows.png)
2020

@@ -24,26 +24,26 @@ OWASP dep-scan is a next-generation security and risk audit tool based on known
2424

2525
### Vulnerability Data sources
2626

27-
- OSV
28-
- NVD
29-
- GitHub
30-
- NPM
31-
- Linux [vuln-list](https://github.com/appthreat/vuln-list)
27+
- OSV
28+
- NVD
29+
- GitHub
30+
- NPM
31+
- Linux [vuln-list](https://github.com/appthreat/vuln-list)
3232

3333
### Linux distros
3434

35-
- AlmaLinux
36-
- Debian
37-
- Alpine
38-
- Amazon Linux
39-
- Arch Linux
40-
- RHEL/CentOS
41-
- Rocky Linux
42-
- Ubuntu
43-
- OpenSUSE/SLES
44-
- Photon
45-
- Chainguard
46-
- Wolfi OS
35+
- AlmaLinux
36+
- Debian
37+
- Alpine
38+
- Amazon Linux
39+
- Arch Linux
40+
- RHEL/CentOS
41+
- Rocky Linux
42+
- Ubuntu
43+
- OpenSUSE/SLES
44+
- Photon
45+
- Chainguard
46+
- Wolfi OS
4747

4848
Application vulnerabilities would be reported for all Linux distros and Windows. To download the full vulnerability database suitable for scanning OS, invoke dep-scan with `--cache` for the first time. dep-scan would also download the appropriate database based on project type automatically.
4949

@@ -66,9 +66,9 @@ oras pull ghcr.io/owasp-dep-scan/depscan:v4 -o $VDB_HOME
6666

6767
Download the executable binary for your operating system from the [releases page](https://github.com/owasp-dep-scan/depscan-bin/releases). These binary bundle the following:
6868

69-
- dep-scan with Python 3.10
70-
- cdxgen with Node.js 18
71-
- cdxgen binary plugins
69+
- dep-scan with Python 3.10
70+
- cdxgen with Node.js 18
71+
- cdxgen binary plugins
7272

7373
```bash
7474
curl -LO https://github.com/owasp-dep-scan/depscan-bin/releases/latest/download/depscan-linux-amd64
@@ -108,25 +108,25 @@ Use the `/scan` endpoint to perform scans.
108108
> [!NOTE]
109109
> The `type` parameter is mandatory in server mode.
110110
111-
- Scanning a local directory.
111+
- Scanning a local directory.
112112

113113
```bash
114114
curl --json '{"path": "/tmp/vulnerable-aws-koa-app", "type": "js"}' http://0.0.0.0:7070/scan
115115
```
116116

117-
- Scanning a SBOM file (present locally).
117+
- Scanning a SBOM file (present locally).
118118

119119
```bash
120120
curl --json '{"path": "/tmp/vulnerable-aws-koa-app/sbom_file.json", "type": "js"}' http://0.0.0.0:7070/scan
121121
```
122122

123-
- Scanning a GitHub repo.
123+
- Scanning a GitHub repo.
124124

125125
```bash
126126
curl --json '{"url": "https://github.com/HooliCorp/vulnerable-aws-koa-app", "type": "js"}' http://0.0.0.0:7070/scan -o app.vdr.json
127127
```
128128

129-
- Uploading a SBOM file and generating results based on it.
129+
- Uploading a SBOM file and generating results based on it.
130130

131131
```bash
132132
curl -X POST -H 'Content-Type: multipart/form-data' -F 'file=@/tmp/app/sbom_file.json' http://0.0.0.0:7070/scan?type=js
@@ -315,14 +315,14 @@ depscan --profile research -t js -i <source directory> --reports-dir <reports di
315315
316316
The following environment variables can be used to customise the behaviour.
317317
318-
- VDB_HOME - Directory to use for caching database. For docker based execution, this directory should get mounted as a volume from the host
318+
- VDB_HOME - Directory to use for caching database. For docker based execution, this directory should get mounted as a volume from the host
319319
320320
## GitHub Security Advisory
321321
322322
To download security advisories from GitHub, a personal access token with minimal permissions is necessary.
323323
324-
- Fine-grained token: Grant no permissions and select the following for repository access: `Public Repositories (read-only)`
325-
- Token (classic): Grant no permissions
324+
- Fine-grained token: Grant no permissions and select the following for repository access: `Public Repositories (read-only)`
325+
- Token (classic): Grant no permissions
326326
327327
```bash
328328
export GITHUB_TOKEN="<PAT token>"
@@ -444,19 +444,32 @@ Severity counts:
444444
* Unspecified: {{ summary.UNSPECIFIED }}
445445
```
446446
447-
The objects available are taken from the CycloneDX *.vdr.json BOM file generated, just have a look to the file for its full structure:
447+
The objects available are taken from the CycloneDX \*.vdr.json BOM file generated, just have a look to the file for its full structure:
448448
449-
* `metadata`
450-
* `vulnerabilities`
451-
* `components`
452-
* `dependencies`
453-
* `services`
449+
- `metadata`
450+
- `vulnerabilities`
451+
- `components`
452+
- `dependencies`
453+
- `services`
454454
455455
`summary` is a dictionary type with vulnerability severity quantities as shown in the example above.
456456
Furthermore insights are imaginably to be made available to the template, please reach out or contribute on demand.
457457
458458
We appreciate if you like to contribute your report templates as examples, please add/find them [here](contrib/report-templates/).
459459
460+
## Performance tuning
461+
462+
### Use nydus to speed up the initial vdb download
463+
464+
vdb v5 is published in RAFS (Registry Accelerated File System) format with better de-duplication and packing. depscan would automatically use this image if `nydus-static` binary is available in the PATH.
465+
466+
```shell
467+
curl -LO https://github.com/dragonflyoss/nydus/releases/download/v2.2.4/nydus-static-v2.2.4-linux-amd64.tgz
468+
tar -xvf nydus-static-v2.2.4-linux-amd64.tgz
469+
chmod +x nydus-static/*
470+
mv nydus-static/* /usr/local/bin/
471+
```
472+
460473
## Discord support
461474
462475
The developers could be reached via the [discord](https://discord.gg/DCNxzaeUpd) channel for enterprise support.

depscan/lib/normalize.py

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,11 @@ def create_pkg_variations(pkg_dict):
5454
if purl_obj:
5555
pkg_type = purl_obj.get("type")
5656
qualifiers = purl_obj.get("qualifiers", {})
57+
namespace = purl_obj.get("namespace")
58+
# npm is known for packages with no group
59+
# To reduce false positives we retain such empty groups here
60+
if pkg_type in ("npm",) and namespace is None:
61+
vendor_aliases.add("")
5762
if qualifiers and qualifiers.get("distro_name"):
5863
os_distro_name = qualifiers.get("distro_name")
5964
name_aliases.add(f"""{os_distro_name}/{name}""")
@@ -62,7 +67,9 @@ def create_pkg_variations(pkg_dict):
6267
name_aliases.add(f"""{os_distro}/{name}""")
6368
# almalinux-9.2 becomes almalinux-9
6469
if "-" in os_distro and "." in os_distro:
65-
name_aliases.add(f"""{os_distro.rsplit(".", 1)[0]}/{name}""")
70+
name_aliases.add(
71+
f"""{os_distro.rsplit(".", 1)[0]}/{name}"""
72+
)
6673
except Exception:
6774
tmp_parts = purl.split(":")
6875
if tmp_parts and len(tmp_parts) > 1:
@@ -94,7 +101,6 @@ def create_pkg_variations(pkg_dict):
94101
]:
95102
vendor_aliases.add("golang")
96103
if pkg_type not in config.OS_PKG_TYPES:
97-
name_aliases.add("package_" + name)
98104
if purl.startswith("pkg:composer"):
99105
vendor_aliases.add("get" + name)
100106
vendor_aliases.add(name + "_project")
@@ -118,8 +124,6 @@ def create_pkg_variations(pkg_dict):
118124
vendor_aliases.add("python-" + name)
119125
vendor_aliases.add(name + "project")
120126
elif purl.startswith("pkg:npm"):
121-
if not name.startswith("node-"):
122-
name_aliases.add("node-" + name)
123127
# pg-promise CVE is filed as pg
124128
if name.endswith("-promise"):
125129
name_aliases.add(name.replace("-promise", ""))
@@ -158,7 +162,11 @@ def create_pkg_variations(pkg_dict):
158162
# The below aliasing is resulting in several false positives for npm
159163
if pkg_type not in ("npm",):
160164
for k, v in config.package_alias.items():
161-
if name.startswith(k) or k.startswith(name) or v.startswith(name):
165+
if (
166+
name.startswith(k)
167+
or k.startswith(name)
168+
or v.startswith(name)
169+
):
162170
name_aliases.add(k)
163171
name_aliases.add(v)
164172
if pkg_type in config.OS_PKG_TYPES:
@@ -170,14 +178,20 @@ def create_pkg_variations(pkg_dict):
170178
name_aliases.add(name + "-bin")
171179
else:
172180
# Filter vendor aliases that are also name aliases
173-
vendor_aliases = [x for x in vendor_aliases if x not in name_aliases or x == vendor]
174-
if len(vendor_aliases) > 0:
181+
vendor_aliases = [
182+
x for x in vendor_aliases if x not in name_aliases or x == vendor
183+
]
184+
if len(vendor_aliases) > 1:
175185
for vvar in list(vendor_aliases):
176186
for nvar in list(name_aliases):
177187
pkg_list.append(
178-
{"vendor": vvar, "name": nvar, "version": pkg_dict["version"]}
188+
{
189+
"vendor": vvar,
190+
"name": nvar,
191+
"version": pkg_dict["version"],
192+
}
179193
)
180-
else:
194+
elif len(name_aliases) > 1:
181195
for nvar in list(name_aliases):
182196
pkg_list.append(
183197
{

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[project]
22
name = "owasp-depscan"
3-
version = "5.1.1"
3+
version = "5.1.2"
44
description = "Fully open-source security audit for project dependencies based on known vulnerabilities and advisories."
55
authors = [
66
{name = "Team AppThreat", email = "[email protected]"},

test/test_norm.py

Lines changed: 26 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -31,15 +31,27 @@ def test_pkg_variations():
3131
)
3232
assert len(pkg_list) > 1
3333
pkg_list = create_pkg_variations(
34-
{"vendor": "io.undertow", "name": "undertow-core", "version": "2.0.27.Final"}
34+
{
35+
"vendor": "io.undertow",
36+
"name": "undertow-core",
37+
"version": "2.0.27.Final",
38+
}
3539
)
3640
assert len(pkg_list) > 1
3741
pkg_list = create_pkg_variations(
38-
{"vendor": "io.undertow", "name": "undertow-core", "version": "2.0.27.Final"}
42+
{
43+
"vendor": "io.undertow",
44+
"name": "undertow-core",
45+
"version": "2.0.27.Final",
46+
}
3947
)
4048
assert len(pkg_list) > 1
4149
pkg_list = create_pkg_variations(
42-
{"vendor": "org.apache.logging.log4j", "name": "log4j-api", "version": "2.12.1"}
50+
{
51+
"vendor": "org.apache.logging.log4j",
52+
"name": "log4j-api",
53+
"version": "2.12.1",
54+
}
4355
)
4456
assert len(pkg_list) > 1
4557
pkg_list = create_pkg_variations(
@@ -59,7 +71,11 @@ def test_pkg_variations():
5971
)
6072
assert len(pkg_list) > 1
6173
pkg_list = create_pkg_variations(
62-
{"vendor": "github.com/go-sql-driver", "name": "mysql", "version": "v1.4.1"}
74+
{
75+
"vendor": "github.com/go-sql-driver",
76+
"name": "mysql",
77+
"version": "v1.4.1",
78+
}
6379
)
6480
assert len(pkg_list) > 1
6581
pkg_list = create_pkg_variations(
@@ -69,44 +85,44 @@ def test_pkg_variations():
6985
"version": "0.0.0-20200220183623-bac4c82f6975",
7086
}
7187
)
72-
assert len(pkg_list) > 1
88+
assert pkg_list
7389
pkg_list = create_pkg_variations(
7490
{
7591
"vendor": "github.com/mitchellh",
7692
"name": "cli",
7793
"version": "6.14.1",
7894
}
7995
)
80-
assert len(pkg_list) > 1
96+
assert pkg_list
8197
pkg_list = create_pkg_variations(
8298
{
8399
"vendor": "github.com/jacobsa",
84100
"name": "crypto",
85101
"version": "6.14.1",
86102
}
87103
)
88-
assert len(pkg_list) > 1
104+
assert pkg_list
89105
pkg_list = create_pkg_variations(
90106
{
91107
"vendor": "org.hibernate",
92108
"name": "hibernate-core",
93109
"version": "5.4.18.Final",
94110
}
95111
)
96-
assert len(pkg_list) > 1
112+
assert pkg_list
97113
pkg_list = create_pkg_variations(
98114
{
99115
"vendor": "org.springframework.security",
100116
"name": "spring-security-crypto",
101117
"version": "5.3.3.RELEASE",
102118
}
103119
)
104-
assert len(pkg_list) > 1
120+
assert pkg_list
105121
pkg_list = create_pkg_variations(
106122
{
107123
"vendor": "deb",
108124
"name": "gnome-accessibility-themes",
109125
"version": "3.28-1ubuntu3",
110126
}
111127
)
112-
assert len(pkg_list) > 1
128+
assert pkg_list

0 commit comments

Comments
 (0)