diff --git a/convex/skills.ts b/convex/skills.ts index f2a3e5724..3f962f61a 100644 --- a/convex/skills.ts +++ b/convex/skills.ts @@ -1987,6 +1987,7 @@ export const getActiveSkillBatchForRescanInternal = internalQuery({ versionId: Id<'skillVersions'> sha256hash: string slug: string + wasFlagged: boolean }> = [] let nextCursor = cursor @@ -2007,6 +2008,8 @@ export const getActiveSkillBatchForRescanInternal = internalQuery({ versionId: version._id, sha256hash: version.sha256hash, slug: skill.slug, + wasFlagged: + (skill.moderationFlags as string[] | undefined)?.includes('flagged.suspicious') ?? false, }) } @@ -2608,8 +2611,8 @@ export const approveSkillByHashInternal = internalMutation({ if (isMalicious || alreadyBlocked) { // Malicious from ANY scanner → blocked.malware (upgrade from suspicious) newFlags = ['blocked.malware'] - } else if ((isSuspicious || alreadyFlagged) && !bypassSuspicious) { - // Suspicious from ANY scanner → flagged.suspicious + } else if (isSuspicious && !bypassSuspicious) { + // Suspicious from this scanner → flagged.suspicious newFlags = ['flagged.suspicious'] } else if (isClean) { // Clean from this scanner — only clear if no other scanner has flagged diff --git a/convex/vt.ts b/convex/vt.ts index 2838bcb87..6f45e8683 100644 --- a/convex/vt.ts +++ b/convex/vt.ts @@ -787,7 +787,7 @@ export const rescanActiveSkills = internalAction({ `[vt:rescan] Processing batch of ${batch.skills.length} skills (cursor=${cursor}, accumulated=${accTotal})`, ) - for (const { versionId, sha256hash, slug } of batch.skills) { + for (const { versionId, sha256hash, slug, wasFlagged } of batch.skills) { try { const vtResult = await checkExistingFile(apiKey, sha256hash) @@ -834,6 +834,15 @@ export const rescanActiveSkills = internalAction({ status, }) accUpdated++ + } else if (wasFlagged && status === 'clean') { + // Verdict improved from suspicious → clean: clear the stale moderation flag + console.log(`[vt:rescan] ${slug}: verdict improved to clean, clearing suspicious flag`) + await ctx.runMutation(internal.skills.approveSkillByHashInternal, { + sha256hash, + scanner: 'vt', + status, + }) + accUpdated++ } else { accUnchanged++ }