import { afterEach, beforeEach, describe, expect, it } from 'vitest'; import Database from 'better-sqlite3'; import { runMigrations } from '../src/database/client.js'; import { CommentSourceWatchRepository } from '../src/database/comment-source-watch-repository.js'; import type { BrowsingThing, RedditPost } from '../src/reddit/api.js'; function post(id: string, createdAtMs: number): RedditPost { return { id, name: id, subreddit: 'scene', author: `author-${id}`, title: id, url: `https://example.test/${id}.jpg`, permalink: `/r/scene/comments/${id}/`, thumbnail: '', is_self: false, created_utc: createdAtMs / 1_000, over_18: true, spoiler: false, }; } function comment(text: string): BrowsingThing { return { fullname: 't1_comment', kind: 'comment', subreddit: 'scene', author: 'reader', permalink: '/r/scene/comments/source/post/comment/', createdAt: 2_000, score: 1, text, nsfw: true, parentPostId: 'source', distinguished: null, removed: false, }; } describe('CommentSourceWatchRepository', () => { let db: Database.Database; let repo: CommentSourceWatchRepository; beforeEach(() => { db = new Database(':memory:'); runMigrations(db); repo = new CommentSourceWatchRepository(db); }); afterEach(() => db.close()); it('durably rotates source posts until their configured watch window expires', () => { expect(repo.refreshSources([post('older', 1_000), post('newer', 2_000)], 10_000, 3_000)) .toEqual({ added: 2, active: 2, expired: 0 }); expect(repo.nextSource('SCENE', 3_000)?.id).toBe('newer'); repo.markChecked('newer', 3_100); expect(repo.nextSource('scene', 3_200)?.id).toBe('older'); const restored = new CommentSourceWatchRepository(db); expect(restored.nextSource('scene', 3_200)?.id).toBe('older'); expect(restored.refreshSources([], 10_000, 12_001)).toEqual({ added: 0, active: 0, expired: 2 }); }); it('reuses unchanged verdicts across restarts and reclassifies edited bodies', () => { const original = comment('I would love that done to me'); const verdict = { id: original.fullname, qualifies: true, expressedGender: 'female' as const, confidence: 0.94, evidence: 'recipient role', }; repo.recordVerdict(original, verdict, 4_000); expect(new CommentSourceWatchRepository(db).getVerdict(original)).toEqual({ ...verdict, evidence: '' }); const stored = db.prepare(` SELECT body_sha256, verdict_json FROM comment_source_comment_observations WHERE comment_id = ? `).get(original.fullname); expect(JSON.stringify(stored)).not.toContain(original.text); expect(JSON.stringify(stored)).not.toContain(verdict.evidence); expect(repo.getVerdict(comment('Edited: I would really love that done to me'))).toBeNull(); }); });