Skip to content

SC4 silent fallback: hardcoded 10s timeout causes OSV.dev lookups to fail silently in high-latency environments #102

Description

@karma-devops

Summary

The SC4 (Known Vulnerable Dependencies) analyzer silently falls back to the 24-package static list when the OSV.dev API call exceeds the hardcoded 10-second timeout. This happens in containerized/high-latency environments where connections to api.osv.dev take 10-15+ seconds. Users get scan results that look successful but have no idea SC4 is running on a tiny fallback list instead of the full OSV database.

Problem

In src/skillspector/nodes/analyzers/osv_client.py:

_REQUEST_TIMEOUT = 10.0  # Line 39

And the connectivity check:

# is_available() uses timeout=5.0 (Line 283)
with httpx.Client(timeout=5.0) as client:

When the timeout is hit, the code logs a WARNING and returns empty lists:

except (httpx.HTTPError, httpx.TimeoutException, ValueError, KeyError) as exc:
    logger.warning("OSV.dev API request failed, falling back to static data: %s", exc)
    return [[] for _ in packages]

The warning goes to logs (only visible with --verbose), but the scan still completes and shows a risk score. The user has no visible indication that SC4 is running on the 24-package fallback list rather than the full OSV database.

Environment

  • Containerized deployment (Docker/EasyPanel with Traefik reverse proxy)
  • Connection to api.osv.dev resolves correctly (74.125.68.121) but takes 10-15 seconds to connect
  • curl with 15s+ timeout works consistently; httpx with 10s fails consistently
  • IPv6 fails immediately (network unreachable), IPv4 times out at 10s

Reproduction

  1. Deploy SkillSpector in an environment with >10s latency to api.osv.dev
  2. Scan a directory with a requirements.txt containing a package with known CVEs (e.g. jinja2==2.4.1)
  3. Run skillspector scan ./test-dir --no-llm --verbose
  4. Observe: WARNING [skillspector.nodes.analyzers.osv_client] OSV.dev API request failed, falling back to static data: [Errno 101] Network is unreachable
  5. SC4 either returns nothing (if the package is not in the 24-entry fallback list) or returns a subset (if it is)

With a 30s timeout, the same scan succeeds and returns 14 vulnerabilities for jinja2==2.4.1.

Impact

  • False confidence: Users believe SC4 is checking against the full OSV database when it is actually using a 24-package static list
  • Missed vulnerabilities: Any package not in _FALLBACK_VULNERABLE_PYPI / _FALLBACK_VULNERABLE_NPM passes undetected
  • Silent failure: The fallback warning only appears in logs, not in the scan output/report

Suggested improvements

  1. Make timeout configurable via env var (SKILLSPECTOR_OSV_TIMEOUT) or CLI flag, defaulting to 30s
  2. Increase the default timeout from 10s to 30s (the is_available() check from 5s to 15s)
  3. Surface the fallback in scan output: When SC4 falls back to static data, show a visible warning in the terminal report (not just logs), e.g. ⚠ SC4: OSV.dev unreachable, using static fallback (24 packages). Results may be incomplete.
  4. Log when OSV.dev returns no vulnerabilities (currently silent — a package with no advisories looks identical to a package that was never checked)

Workaround

Patch osv_client.py locally:

_REQUEST_TIMEOUT = 60.0  # was 10.0
# is_available():
with httpx.Client(timeout=15.0) as client:  # was 5.0

Additional improvement we made locally

Added an info log when OSV.dev returns no vulnerabilities for a package, so a clean pass is distinguishable from a failed lookup:

if not vulns_raw:
    name, version = packages[idx]
    _put_cache(_cache_key(name, version, ecosystem), [])
    logger.info("OSV.dev: no vulnerabilities found for %s==%s (passed)", name, version or "unspecified")
    continue

Happy to submit a PR if that would be preferred.


SkillSpector version: 2.2.3
Python: 3.12
Platform: Linux (Docker container)

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions