Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@ require (
github.com/jfrog/build-info-go v1.13.1-0.20260528065004-80409c046540
github.com/jfrog/froggit-go v1.22.0
github.com/jfrog/gofrog v1.7.6
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260528123948-61478692b94e
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260528061115-b41c87af0194
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260603105750-3886c0f01286
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260601130310-8d52a530da18
github.com/jfrog/jfrog-cli-security v1.29.3
github.com/jfrog/jfrog-client-go v1.55.1-0.20260528115006-6ca9682a3255
github.com/jfrog/jfrog-client-go v1.55.1-0.20260603130552-af1dd449b994
github.com/jordan-wright/email v4.0.1-0.20210109023952-943e75fe5223+incompatible
github.com/owenrumney/go-sarif/v3 v3.2.3
github.com/stretchr/testify v1.11.1
Expand Down
12 changes: 6 additions & 6 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -146,14 +146,14 @@ github.com/jfrog/gofrog v1.7.6 h1:QmfAiRzVyaI7JYGsB7cxfAJePAZTzFz0gRWZSE27c6s=
github.com/jfrog/gofrog v1.7.6/go.mod h1:ntr1txqNOZtHplmaNd7rS4f8jpA5Apx8em70oYEe7+4=
github.com/jfrog/jfrog-apps-config v1.0.1 h1:mtv6k7g8A8BVhlHGlSveapqf4mJfonwvXYLipdsOFMY=
github.com/jfrog/jfrog-apps-config v1.0.1/go.mod h1:8AIIr1oY9JuH5dylz2S6f8Ym2MaadPLR6noCBO4C22w=
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260528123948-61478692b94e h1:qTfCvRAo4zO7Oid0ILz4LaJna5xbQjBOmOlw+23XkN4=
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260528123948-61478692b94e/go.mod h1:GQEGVW3wT1XPykXNsEiPQrF8/+01JvDVcGGYb5vqJuE=
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260528061115-b41c87af0194 h1:cwppCKLitT0XBqYGQimW00qyx1ej88sY+rIjXAWNvAU=
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260528061115-b41c87af0194/go.mod h1:9R90mhbczGXwW5EGlDs7F08ejQU/xdoDhYHMvzBiqgE=
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260603105750-3886c0f01286 h1:IF9Fyhfd7hilnuHO2AezV3lE9SF2FSxRxs4gfcU3f1U=
github.com/jfrog/jfrog-cli-artifactory v0.8.1-0.20260603105750-3886c0f01286/go.mod h1:GQEGVW3wT1XPykXNsEiPQrF8/+01JvDVcGGYb5vqJuE=
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260601130310-8d52a530da18 h1:tPv7XscDFAZaijVwMQNb+HmuucUMYQdjuA5frdGzhF0=
github.com/jfrog/jfrog-cli-core/v2 v2.60.1-0.20260601130310-8d52a530da18/go.mod h1:9R90mhbczGXwW5EGlDs7F08ejQU/xdoDhYHMvzBiqgE=
github.com/jfrog/jfrog-cli-security v1.29.3 h1:cIoDn5NkhmrVANUr22H2IVwYjqeFTA+e61lb4qE+8X8=
github.com/jfrog/jfrog-cli-security v1.29.3/go.mod h1:wTdl1sSLyq+TzOPnncxBBhqCKEqF2kp9l86k+Y5E3mM=
github.com/jfrog/jfrog-client-go v1.55.1-0.20260528115006-6ca9682a3255 h1:CIOMO1Hj5N6PaIu7sJZ9bPowcibkcaWDulM2R6LHO9o=
github.com/jfrog/jfrog-client-go v1.55.1-0.20260528115006-6ca9682a3255/go.mod h1:FHpjN1nTDoj96xd6obe27EOgGErqzU0rQgC96L3Ch9E=
github.com/jfrog/jfrog-client-go v1.55.1-0.20260603130552-af1dd449b994 h1:z1/WjItD4X9z1VkYhzrnbd0NWXp6+0I/LoP7XmsHl4U=
github.com/jfrog/jfrog-client-go v1.55.1-0.20260603130552-af1dd449b994/go.mod h1:FHpjN1nTDoj96xd6obe27EOgGErqzU0rQgC96L3Ch9E=
github.com/jhump/protoreflect v1.15.1 h1:HUMERORf3I3ZdX05WaQ6MIpd/NJ434hTp5YiKgfCL6c=
github.com/jhump/protoreflect v1.15.1/go.mod h1:jD/2GMKKE6OqX8qTjhADU1e6DShO+gavG9e0Q693nKo=
github.com/jordan-wright/email v4.0.1-0.20210109023952-943e75fe5223+incompatible h1:jdpOPRN1zP63Td1hDQbZW73xKmzDvZHzVdNYxhnTMDA=
Expand Down
2 changes: 1 addition & 1 deletion scanrepository/scanrepository_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ func TestScanRepositoryCmd_Run(t *testing.T) {
{
testName: "aggregate-multi-project",
expectedPackagesInBranch: map[string][]string{"frogbot-update-68d9dee2475e5986e783d85dfa11baa0-dependencies-master": {"uuid", "minimatch", "mpath"}, "frogbot-update-e8fa179873704bb1362147aff9c40040-dependencies-master": {"pyjwt", "pexpect"}},
expectedVersionUpdatesInBranch: map[string][]string{"frogbot-update-68d9dee2475e5986e783d85dfa11baa0-dependencies-master": {"^9.0.0", "^0.8.4", "^10.2.3"}, "frogbot-update-e8fa179873704bb1362147aff9c40040-dependencies-master": {"2.12.0"}},
expectedVersionUpdatesInBranch: map[string][]string{"frogbot-update-68d9dee2475e5986e783d85dfa11baa0-dependencies-master": {"^9.0.0", "^0.8.4", "^10.2.3"}, "frogbot-update-e8fa179873704bb1362147aff9c40040-dependencies-master": {"2.13.0"}},
expectedMissingFilesInBranch: map[string][]string{"frogbot-update-68d9dee2475e5986e783d85dfa11baa0-dependencies-master": {"npm/package-lock.json"}},
packageDescriptorPaths: []string{"npm/package.json", "pip/requirements.txt"},
aggregateFixes: true,
Expand Down
46 changes: 44 additions & 2 deletions testdata/messages/integration/test_proj_pip_with_vulnerability.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,11 @@


## 📗 Scan Summary
- Frogbot scanned for vulnerabilities and found 3 issues
- Frogbot scanned for vulnerabilities and found 6 issues

| Scan Category | Status | Security Issues |
| --------------------- | :-----------------------------------: | ----------------------------------- |
| **Software Composition Analysis** | ✅ Done | <details><summary><b>3 Issues Found</b></summary><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallHigh.svg" alt=""/> 3 High<br></details> |
| **Software Composition Analysis** | ✅ Done | <details><summary><b>6 Issues Found</b></summary><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallHigh.svg" alt=""/> 4 High<br><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallMedium.svg" alt=""/> 1 Medium<br><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallLow.svg" alt=""/> 1 Low<br></details> |
| **Contextual Analysis** | ✅ Done | - |
| **Static Application Security Testing (SAST)** | ✅ Done | Not Found |
| **Secrets** | ✅ Done | - |
Expand All @@ -27,7 +27,10 @@

| Severity | ID | Contextual Analysis | Direct Dependencies | Impacted Dependency | Fixed Versions |
| :---------------------: | :-----------------------------------: | :-----------------------------------: | :-----------------------------------: | :-----------------------------------: | :-----------------------------------: |
| ![high](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableHighSeverity.png)<br> High | CVE-2026-48526 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![high](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableHighSeverity.png)<br> High | CVE-2022-29217 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.4.0] |
| ![medium](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableMediumSeverity.png)<br> Medium | CVE-2026-48522 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![low](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableLowSeverity.png)<br> Low | CVE-2026-48524 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2026-32597 | Not Applicable | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.12.0] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2025-45768 | Not Applicable | pyjwt:1.7.1 | pyjwt 1.7.1 | - |

Expand All @@ -37,6 +40,19 @@
### 🔖 Details


<details><summary><b>[ CVE-2026-48526 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 7.4 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, when the verifier is decoding JSON Web Tokens, while supporting both asymmetric and HMAC algorithms, the library does not validate use of JSON Web Keys in HMAC algorithm, allowing attacker to use the issuer public key as the secret key for HMAC algorithm. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2022-29217 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
Expand Down Expand Up @@ -82,6 +98,32 @@ With -
`jwt.decode(encoded_jwt, pub_key_bytes, algorithms=["ES256"])`
<br></details>

<details><summary><b>[ CVE-2026-48522 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 4.2 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, PyJWKClient passes its uri argument directly to urllib.request.urlopen() which uses Python stdlib's default OpenerDirector registering HTTPHandler, HTTPSHandler, FTPHandler, FileHandler, and DataHandler. There is currently no documented option to restrict which schemes PyJWKClient will fetch. If an application's jku URL ingestion path accepts attacker-influenced URLs (e.g., from JWT header, configuration file, OAuth flow parameter), the attacker can cause PyJWKClient to read arbitrary local files via file:// (SSRF on local filesystem), cause PyJWKClient to attempt FTP / data-URI fetches (broader SSRF surface), or forge tokens that PyJWT verifies as valid. The library does not directly return non-HTTP(S) URI contents to the attacker; the chained "plant a JWKS to forge tokens" scenario described in the original report requires additional application-layer flaws (attacker write access to a filesystem path, untrusted jku derivation) that this fix does not address. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2026-48524 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 3.7 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, PyJWKClient.get_signing_key() forces a fresh HTTP request to the JWKS endpoint for every JWT with an unknown kid value, with no rate limiting. Since kid comes from the unverified token header, an attacker can trigger unlimited outbound requests. The vulnerability surfaces only when a JWKS fetch fails; an attacker can attempt to provoke that with sustained unknown-kid traffic, but the outcome depends on upstream JWKS-endpoint behavior (rate limiting, transient errors) which is beyond the attacker's control. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2026-32597 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
Expand Down
46 changes: 44 additions & 2 deletions testdata/scanpullrequest/expected_response_multi_dir.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,11 @@


## 📗 Scan Summary
- Frogbot scanned for vulnerabilities and found 7 issues
- Frogbot scanned for vulnerabilities and found 10 issues

| Scan Category | Status | Security Issues |
| --------------------- | :-----------------------------------: | ----------------------------------- |
| **Software Composition Analysis** | ✅ Done | <details><summary><b>7 Issues Found</b></summary><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallHigh.svg" alt=""/> 7 High<br></details> |
| **Software Composition Analysis** | ✅ Done | <details><summary><b>10 Issues Found</b></summary><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallHigh.svg" alt=""/> 8 High<br><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallMedium.svg" alt=""/> 1 Medium<br><img src="https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/smallLow.svg" alt=""/> 1 Low<br></details> |
| **Contextual Analysis** | ✅ Done | - |
| **Static Application Security Testing (SAST)** | ✅ Done | Not Found |
| **Secrets** | ✅ Done | - |
Expand All @@ -31,7 +31,10 @@
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2026-27903 | Not Applicable | minimatch:3.0.4 | minimatch 3.0.4 | [3.1.3]<br>[4.2.5]<br>[5.1.8]<br>[6.2.2]<br>[7.4.8]<br>[8.0.6]<br>[9.0.7]<br>[10.2.3] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2026-26996 | Not Applicable | minimatch:3.0.4 | minimatch 3.0.4 | [3.1.3]<br>[4.2.4]<br>[5.1.7]<br>[6.2.1]<br>[7.4.7]<br>[8.0.5]<br>[9.0.6]<br>[10.2.1] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2022-3517 | Not Applicable | minimatch:3.0.4 | minimatch 3.0.4 | [3.0.5] |
| ![high](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableHighSeverity.png)<br> High | CVE-2026-48526 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![high](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableHighSeverity.png)<br> High | CVE-2022-29217 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.4.0] |
| ![medium](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableMediumSeverity.png)<br> Medium | CVE-2026-48522 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![low](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/applicableLowSeverity.png)<br> Low | CVE-2026-48524 | Not Covered | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.13.0] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2026-32597 | Not Applicable | pyjwt:1.7.1 | pyjwt 1.7.1 | [2.12.0] |
| ![high (not applicable)](https://raw.githubusercontent.com/jfrog/frogbot/master/resources/v2/notApplicableHigh.png)<br> High | CVE-2025-45768 | Not Applicable | pyjwt:1.7.1 | pyjwt 1.7.1 | - |

Expand Down Expand Up @@ -194,6 +197,19 @@ function redosDetector(input_string, limit) {

A vulnerability was found in the minimatch package. This flaw allows a Regular Expression Denial of Service (ReDoS) when calling the braceExpand function with specific arguments, resulting in a Denial of Service.<br></details>

<details><summary><b>[ CVE-2026-48526 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 7.4 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, when the verifier is decoding JSON Web Tokens, while supporting both asymmetric and HMAC algorithms, the library does not validate use of JSON Web Keys in HMAC algorithm, allowing attacker to use the issuer public key as the secret key for HMAC algorithm. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2022-29217 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
Expand Down Expand Up @@ -239,6 +255,32 @@ With -
`jwt.decode(encoded_jwt, pub_key_bytes, algorithms=["ES256"])`
<br></details>

<details><summary><b>[ CVE-2026-48522 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 4.2 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, PyJWKClient passes its uri argument directly to urllib.request.urlopen() which uses Python stdlib's default OpenerDirector registering HTTPHandler, HTTPSHandler, FTPHandler, FileHandler, and DataHandler. There is currently no documented option to restrict which schemes PyJWKClient will fetch. If an application's jku URL ingestion path accepts attacker-influenced URLs (e.g., from JWT header, configuration file, OAuth flow parameter), the attacker can cause PyJWKClient to read arbitrary local files via file:// (SSRF on local filesystem), cause PyJWKClient to attempt FTP / data-URI fetches (broader SSRF surface), or forge tokens that PyJWT verifies as valid. The library does not directly return non-HTTP(S) URI contents to the attacker; the chained "plant a JWKS to forge tokens" scenario described in the original report requires additional application-layer flaws (attacker write access to a filesystem path, untrusted jku derivation) that this fix does not address. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2026-48524 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
| | |
| --------------------- | :-----------------------------------: |
| **Contextual Analysis:** | Not Covered |
| **Direct Dependencies:** | pyjwt:1.7.1 |
| **Impacted Dependency:** | pyjwt:1.7.1 |
| **Fixed Versions:** | [2.13.0] |
| **CVSS V3:** | 3.7 |

PyJWT is a JSON Web Token implementation in Python. Prior to 2.13.0, PyJWKClient.get_signing_key() forces a fresh HTTP request to the JWKS endpoint for every JWT with an unknown kid value, with no rate limiting. Since kid comes from the unverified token header, an attacker can trigger unlimited outbound requests. The vulnerability surfaces only when a JWKS fetch fails; an attacker can attempt to provoke that with sustained unknown-kid traffic, but the outcome depends on upstream JWKS-endpoint behavior (rate limiting, transient errors) which is beyond the attacker's control. This vulnerability is fixed in 2.13.0.<br></details>

<details><summary><b>[ CVE-2026-32597 ] pyjwt 1.7.1</b></summary>

### Vulnerability Details
Expand Down
Loading