Bumblebee — Perplexity's Supply-Chain Security Scanner for Developer Machines
Bumblebee — Perplexity's Supply-Chain Security Scanner for Developer Machines
When a supply-chain attack is disclosed — a compromised npm package, a malicious PyPI release, a tampered VS Code extension — the first question security teams ask is: "Are any of our developer machines affected, right now?"
Traditional tools answer different questions. SBOMs tell you what shipped in your artifacts. EDR tells you what ran or touched the network. But nobody tells you about the messy on-disk state across lockfiles, package manager metadata, extension manifests, and developer tool configs on every engineer's laptop.
Bumblebee is a read-only inventory collector from Perplexity AI that fills exactly this gap. Released in May 2026, it scans macOS and Linux developer endpoints for package metadata, extension manifests, and MCP configs — then matches findings against exposure catalogs of known compromises. It's a single static Go binary with zero dependencies. No telemetry. No package manager execution. Just structured NDJSON output you can pipe anywhere.
What is Bumblebee?
Bumblebee turns scattered on-disk state into structured records. It answers one narrow question: when an advisory names a package, extension, or version, which developer machines show a match in their on-disk metadata?
Key capabilities:
- Three scan profiles —
baseline(global/user package roots),project(dev workspaces),deep(on-demand incident response) - 14+ ecosystems — npm, pnpm, Yarn, Bun, PyPI, Go modules, RubyGems, Composer, MCP configs, VS Code/Cursor/Windsurf extensions, and Chromium/Firefox browser extensions
- Exposure catalog matching — supply a JSON catalog of known compromises, get NDJSON findings for every exact match
- NDJSON output — structured records with stable content-addressed IDs for deduplication
- Self-test mode — built-in end-to-end smoke test against embedded fixtures (no network calls)
- No dependencies — Go 1.25+, stdlib only. Single static binary.
- Read-only — scans lockfiles and metadata only. Never executes
npm install,pip show, or any package manager command.
Why is it Trending?
Bumblebee hit 3,800+ GitHub stars in its first week for several reasons:
- The supply-chain crisis is real — XZ backdoor (CVE-2024-3094),
es5-extsabotage, Polyfill.io CDN takeover. Teams need practical response tools. - A focused niche — SBOM tools miss developer machines. EDR is too heavy. Bumblebee fits between them perfectly.
- Perplexity's credibility — shipped by Perplexity AI, built with real incident-response experience from the team behind Xint Code
- Zero dependency, single binary — deploy via MDM, cron, or launchd in seconds, not hours
- Open-source, Apache 2.0 — inspect the code, contribute catalogs, own your data
Prerequisites
- A Linux (x86_64, aarch64) or macOS (Intel, Apple Silicon) machine
- Go 1.25+ if installing from source (recommended:
go install) - Optional:
cron,launchd,systemd, or an MDM solution for fleet deployment - Optional: a directory of threat-intel exposure catalogs (sample catalogs ship in the repo's
threat_intel/)
Installation
Via Go install
go install github.com/perplexityai/bumblebee/cmd/bumblebee@latest
Pin a specific version
go install github.com/perplexityai/bumblebee/cmd/bumblebee@v0.1.1
Build from source
git clone https://github.com/perplexityai/bumblebee.git
cd bumblebee
go build -o bumblebee ./cmd/bumblebee
Stamp an explicit version at build time:
go build -ldflags "-X main.Version=v0.1.1" -o bumblebee ./cmd/bumblebee
Verify the installation
bumblebee selftest
# selftest OK (2 findings in 1ms)
A non-zero exit means your install can no longer detect what it should — a fast pre-deployment smoke test for fleet rollouts.
Quick Start
Baseline inventory scan
bumblebee scan --profile baseline > inventory.ndjson
This scans common global and user package roots (Homebrew, Python, Go, cargo, asdf, nvm), editor extensions (VS Code, Cursor, Windsurf), browser extensions, and MCP configs.
Project workspace scan
bumblebee scan --profile project \
--root "$HOME/code" \
--root "$HOME/Developer" > project-inventory.ndjson
Limit to specific ecosystems
bumblebee scan --profile baseline \
--ecosystem npm,pypi \
--ecosystem go
On-demand exposure scan
bumblebee scan --profile deep \
--root "$HOME" \
--exposure-catalog ./catalog.json \
--findings-only
This scans $HOME recursively, matches every package against your exposure catalog, and emits only finding records.
Preview scan roots
bumblebee roots --profile baseline
# prints "<root_kind>\t<path>" lines
Architecture Overview
Bumblebee follows a clean three-stage pipeline: inventory collection → optional exposure matching → structured output.
The pipeline works as follows:
-
Root Resolution — Based on the chosen profile (
baseline,project, ordeep), Bumblebee resolves filesystem paths to scan. Baseline discovers common global roots (Homebrew lib prefixes,/Library/Python,~/.local,~/.cargo,~/go, editor config dirs, browser profile dirs). Project profiles accept explicit--rootpaths. Deep profiles accept any path including$HOME(with safeguards). -
Ecosystem Parsers — Each supported ecosystem has a dedicated parser that reads the relevant on-disk files. npm/pnpm/Yarn/Bun lockfiles produce
ecosystem: npmrecords. PyPI readsMETADATAandINSTALLERfiles fromdist-infodirectories. Go modules parsego.sumandgo.mod. MCP configs parse JSON host configs (mcp.json,claude_desktop_config.json, etc.). Each parser emits structured NDJSON records withconfidencelevels (high/medium/low) based on reliability of the source. -
Exposure Catalog Engine — When
--exposure-catalogis provided, Bumblebee loads one or more JSON catalog files and performs exact(ecosystem, name, version)matching against every package record. Findings are emitted as separate NDJSONfindingrecords with severity, catalog ID, and evidence details. -
Output Serializer — All records are written as NDJSON (newline-delimited JSON) to stdout. Diagnostics go to stderr, also as NDJSON. Each run closes with a
scan_summaryrecord that receivers use to determine whether to promote the run to current state. Optional HTTPS and file output modes are documented in the transport docs.
Output Format
Package Record
Each package found during inventory is emitted as an NDJSON record:
| Field | Description |
|---|---|
record_type |
Always "package" |
ecosystem |
npm, pypi, go, rubygems, packagist, mcp, editor-extension, browser-extension |
package_name |
The package name from the source |
version |
Installed version |
confidence |
high (canonical metadata), medium (reliable but partial), low (config/spec only) |
source_type |
pnpm-lockfile, yarn-lockfile, go.sum, pip-metadata, etc. |
package_manager |
npm/pnpm/yarn/bun/pip/go/etc. |
endpoint |
Hostname, OS, arch, username, UID, device_id |
record_id |
Content-addressed hash, stable across runs |
Finding Record
When a package matches an exposure catalog entry:
| Field | Description |
|---|---|
record_type |
Always "finding" |
finding_type |
"package_exposure" |
severity |
Matches the catalog entry's severity |
catalog_id |
Reference to the advisory |
catalog_name |
Human-readable advisory name |
evidence |
Description of what matched |
Exposure Catalogs
Bumblebee ships with maintained exposure catalogs in the threat_intel/ directory, built from public threat-intelligence reporting on recent supply-chain campaigns. To use them:
# Download and use the bundled catalogs
git clone https://github.com/perplexityai/bumblebee.git
bumblebee scan --profile deep \
--root "$HOME/code" \
--exposure-catalog ./threat_intel/ \
--findings-only
Catalog format:
{
"schema_version": "0.1.0",
"entries": [
{
"id": "advisory-2026-0042",
"name": "example-pkg 1.2.3 (compromised release)",
"ecosystem": "npm",
"package": "example-pkg",
"versions": ["1.2.3"],
"severity": "critical"
}
]
}
Fleet Deployment
Cron (Linux daily inventory)
# /etc/cron.d/bumblebee
0 6 * * * root bumblebee scan --profile baseline > /var/log/bumblebee/$(date +\%Y\%m\%d).ndjson
Launchd (macOS recurring scan)
Save as ~/Library/LaunchAgents/com.perplexity.bumblebee.plist:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Label</key>
<string>com.perplexity.bumblebee</string>
<key>ProgramArguments</key>
<array>
<string>/usr/local/bin/bumblebee</string>
<string>scan</string>
<string>--profile</string>
<string>baseline</string>
</array>
<key>StartCalendarInterval</key>
<dict>
<key>Hour</key>
<integer>6</integer>
<key>Minute</key>
<integer>0</integer>
</dict>
<key>StandardOutPath</key>
<string>/var/log/bumblebee/daily.ndjson</string>
<key>StandardErrorPath</key>
<string>/var/log/bumblebee/error.log</string>
</dict>
</plist>
Systemd timer (Linux)
# /etc/systemd/system/bumblebee.service
[Unit]
Description=Bumblebee supply-chain inventory scan
[Service]
Type=oneshot
ExecStart=/usr/local/bin/bumblebee scan --profile baseline
StandardOutput=append:/var/log/bumblebee/daily.ndjson
StandardError=append:/var/log/bumblebee/error.log
# /etc/systemd/system/bumblebee.timer
[Unit]
Description=Daily Bumblebee scan
[Timer]
OnCalendar=daily
Persistent=true
[Install]
WantedBy=timers.target
Comparison with Alternatives
- SBOM generators (Syft, Trivy) — focus on container and build artifacts, not developer machines. Don't scan MCP configs, editor extensions, or browser addons.
- EDR agents (CrowdStrike, SentinelOne) — heavy, expensive, network-telemetry focused. Bumblebee is read-only, free, and developer-machine-specific.
npm audit/pip-audit— package-registry-specific, require the toolchain to be installed, execute package manager commands. Bumblebee never executes package managers.- Manual inventory — grepping
node_modulesacross hundreds of machines isn't scalable. Bumblebee produces structured, stable-id records.
Resources
- GitHub: github.com/perplexityai/bumblebee
- Documentation: built-in via
bumblebee --help, plusdocs/in the repo (inventory-sources.md, state-model.md, transport.md) - Threat Intel Catalogs:
threat_intel/directory in the repo — maintained exposure catalogs from public reporting - License: Apache 2.0