Skip to content

fix(admin): judge a stuck scan by updated_at, like the recovery cron and the rescan tool - #470

Open
deanrie wants to merge 1 commit into
cursor:mainfrom
deanrie:stuck-scans-by-updated-at
Open

deanrie wants to merge 1 commit into
cursor:mainfrom
deanrie:stuck-scans-by-updated-at

Conversation

@deanrie

@deanrie deanrie commented Oct 24, 2026

Copy link
Copy Markdown

What

Three places apply what is meant to be one 15-minute staleness rule for plugin scans:

  • /api/cron/recover-stuck-scans: scan_status in (pending, scanning) and updated_at older than 15 minutes, then re-enqueue. Its commit says it uses "the same 15-min staleness threshold getStuckScans uses".
  • MCP rescan_plugin in lib/mcp/tools.ts: refuses while pending/scanning and updated_at is younger than 15 minutes, with the comment "Matches the stuck-scan threshold in getStuckScans()".
  • getStuckScans() in data/queries.ts, which feeds the admin Stuck tab and list_moderation_queue scan_issues: pending/scanning and created_at older than 15 minutes.

created_at is when the plugin row was created, not when the scan started. So a re-scan of any plugin older than 15 minutes (admin rescan_plugin, the recovery cron's own re-enqueue, or an owner re-scan once #458 lands) shows up in the Stuck tab the moment it is set to pending, while the cron considers it healthy and rescan_plugin answers that a scan is already pending. The plugins_set_updated_at trigger bumps updated_at on every status write, which is why the other two rely on it.

Fix

getStuckScans() filters on updated_at instead of created_at, with a comment naming the two siblings. The error branch of the filter and the tab's created_at desc ordering are unchanged.

The repo has no test runner. The filter is the same PostgREST shape the cron already uses with .lt("updated_at", cutoff). tsc --noEmit -p apps/cursor/tsconfig.json reports the same single pre-existing error as main (platform in AgentOptions in scan.ts) and nothing new; biome check on the file is clean.

…an tool

getStuckScans() treated a pending or scanning plugin as stuck once its
created_at was older than 15 minutes. The recover-stuck-scans cron, added
to use "the same 15-min staleness threshold getStuckScans uses", and the
MCP rescan_plugin guard both measure from updated_at, which the
plugins_set_updated_at trigger bumps on every status write. So a re-scan of
any plugin older than 15 minutes showed up in the admin Stuck tab and in
list_moderation_queue scan_issues the moment it was queued, while the cron
left it alone, and the rescan tool refused to re-queue it as in progress.

The query now uses updated_at, so the three agree.
@vercel

vercel Bot commented Oct 24, 2026

Copy link
Copy Markdown

@deanrie is attempting to deploy a commit to the Anysphere Team on Vercel.

A member of the Team first needs to authorize it.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant