// verified findings

Real bugs PullLight caught
in real open-source PRs

Every finding below is from a public scan you can verify. These are high and critical severity bugs PullLight found automatically — no manual triage, no curation.

// Each card links to the full scan result — diff, finding context, and AI explanation included.

30 verified findings
8 repos
high & critical only
#1197
feat(eve): publish canonical harness lifecycle events
"`activeTurnId` is read by `toLifecycleEvent` before it is updated for `turn.started` events. On line 27, `toLifecycleEvent` is called with the old (undefined) `activeTurnId`, and only on line 28 is `a…"
logic
#5
Fix deployment ID resolution across environments
"`assert` from `node:assert/strict` throws an `AssertionError` (not a regular `Error`) when `response.ok` is false. The error message only includes the status code but not the response body, making it …"
error-handling
#1
feat: add managed deepagents example
"The `LANGSMITH_API_KEY` is exposed to the browser bundle via Vite's `envPrefix` config. This is acknowledged in comments, but the `getApiKey()` function returns it unconditionally and it is passed dir…"
auth
#165
feat: enforce .openwikiignore rules
"The `allowedIgnoredShellCommands` allowlist uses `allowedCommand.test(trimmedCommand)` with stateful `RegExp` objects. None of the three regexes use the `g` or `y` flag, so `lastIndex` is not an issue…"
logic
#381
fix: auto-frontmatter legacy wiki pages
"Race condition / data inconsistency: `backend.edit` is called with `(filePath, content, repaired)` where `content` is the original file text read moments earlier. If another writer modifies the file b…"
logic
#1
feat: add managed deepagents example
"`getApiKey()` returns `undefined` when `LANGSMITH_API_KEY` is not set, and `createManagedClient()` silently passes `{ apiKey: undefined }` to `ManagedClient`. This means all API calls (fetchThreads, c…"
auth
#280
feat: add Grok Build subscription CLI as a provider
"The `timeout` timer is only cleared on the happy path (`clearTimeout(timeout)` after `await stdoutDone`). If `writeFile` throws, or if `spawn` throws, or if any `await` between the spawn and `clearTim…"
resource-leak
#184
Basic UCP support
"`nextRequestId` is a module-level mutable variable (`let nextRequestId = 1`). In environments where multiple `UcpResource` instances are used concurrently (e.g., multiple parallel requests), this shar…"
race-condition
#51
feat(smithy): add canonical Smithy models for APIs
"`d["components"]["schemas"]` is accessed without checking that `d["components"]` exists. If the generated OpenAPI file has no `components` key (e.g. for a minimal or malformed output), this will raise…"
null-deref
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, `source.type === 'vercel'` and the deployment ID is resolved via the Vercel API — but this entire block is only entered when `config.statusContext` is truthy. If a user supp…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, `source.type === 'vercel'` but the outer guard is still `if (config.statusContext)`. This means if a user sets `vercel-token` but leaves `status-context` empty (or clears it…"
logic
#706
fix(slack): collect thread attachments across recent me…
"The old code had an intentional early-exit `return []` after the first non-bot message with no files, which prevented scanning further back in the thread. The new code removes that guard and continues…"
logic
#710
feat(eve): external cron mode for self-hosted builds (E…
"`timingSafeEqualStrings` short-circuits with `false` when the lengths differ, but this early-exit leaks the length of the expected secret via a timing side-channel. An attacker can binary-search the s…"
auth
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, the `source` is of type `'vercel'`, but the outer guard is still `if (config.statusContext)`. This means that if a user supplies `vercel-token` but leaves `status-context` e…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set but `statusContext` is empty, the `source` is built as `{ type: 'vercel', ... }` but the entire ID-resolution block is skipped because of the `if (config.statusContext)` guar…"
logic
#135
Add redirect URI callback for spend request approval fl…
"`resolveCallback` is called at most once (on the first HTTP request), but the server is never closed after that first callback fires. Subsequent requests keep the server alive indefinitely. The caller…"
resource-leak
#184
Basic UCP support
"The `discoveryCache` and `negotiatedCache` are instance-level Maps, but `UcpResource` instances are created per-CLI-invocation (one per command run). This is fine for the CLI, but in the SDK the cache…"
auth
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, the `source.type` is `'vercel'` and the outer guard is `if (config.statusContext)`. This means `resolveDeploymentIdFromUrl` is only called when `statusContext` is non-empty.…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, `source.type === 'vercel'` and the deployment ID is resolved via the Vercel API — but the outer guard is still `if (config.statusContext)`. This means that if a user supplie…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, `source.type === 'vercel'` but the outer guard is still `if (config.statusContext)`. This means that if `statusContext` is empty (deployment-ID resolution disabled), the Ver…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, `source.type === 'vercel'` but the outer guard is still `if (config.statusContext)`. This means if a user sets `vercel-token` but leaves `status-context` empty (or clears it…"
logic
#5
Fix deployment ID resolution across environments
"When `vercelToken` is set, the `source` is `{ type: 'vercel', ... }` and the guard is `if (config.statusContext)`. This means that if `statusContext` is empty (deployment ID resolution disabled), the …"
logic
#135
Add redirect URI callback for spend request approval fl…
"The `message` string is interpolated directly into an HTML response without escaping: `res.end(`<html><body><p>${message}</p></body></html>`)`. Although `message` comes from the hardcoded `STATUS_MESS…"
injection
#184
Basic UCP support
"The `clientSecret` is passed as a plain string through CLI args (`--client-secret`) and stored in `UcpAuth`. When constructing the Basic auth header via `btoa('clientId:clientSecret')`, if `clientSecr…"
auth
#394
fix(eve): resume duplicate Vercel sandbox creates
"When a concurrent duplicate-name error is caught and the sandbox is fetched via `getNamedVercelSandbox`, `requiresBaseRuntimeSetup` is set to `input.snapshotId === undefined`. This means the concurren…"
logic
#5
Fix deployment ID resolution across environments
"`assert(response.ok, ...)` throws an `AssertionError` (not a plain `Error`) when the Vercel API returns a non-2xx status. The error message includes only the status code, not the response body, making…"
error-handling
#382
fix(eve): Slack follow-ups for legacy scheduled threads
"`namespaceHealthCache` is a module-level `Map` that stores `Promise<boolean>` values and is never evicted. In a long-running server process this means: (1) a failed probe result is cached forever — if…"
race-condition
axios/axios critical
#5968
feat: add fetch adapter for browser and node
"**SSRF via fetch() with request-derived URL**: `const response = await fetch(req.body.callbackUrl)` passes a request-derived URL directly to an HTTP client. An attacker who controls this value can mak…"
injection
#6271
feat(richtext-lexical): add HTML block support with inl…
"XSS via dangerouslySetInnerHTML — blockData.htmlContent is passed directly to dangerouslySetInnerHTML without DOMPurify sanitization. An attacker controlling this rich-text field value can inject scri…"
injection
#1
feat: add managed deepagents example
"`getApiKey()` returns `undefined` when `LANGSMITH_API_KEY` is not set, and `createManagedClient()` silently passes `{ apiKey: undefined }` to `ManagedClient`. This means all API calls (fetchThreads, c…"
auth
// free for public repos

Install PullLight on your repo

Webhook fires on every PR. AI reviews the diff. You approve before anything posts. These are exactly the kinds of bugs it catches — automatically.