Filter unattributed successful messages

This commit is contained in:
jjbrunton committed 2026-08-08 18:28:46 +01:00
1 parent 2c100d72b6
commit 7bcdbe236a
3 files changed
+62 -1

No files matched your search

+17
View File
@@ -664,6 +664,7 @@ export class MessagesRepository {
export class SuccessfulMessagesRepository { export class SuccessfulMessagesRepository {
private insertStmt: Database.Statement; private insertStmt: Database.Statement;
private getRecentStmt: Database.Statement; private getRecentStmt: Database.Statement;
private getAttributedRecentStmt: Database.Statement;
private getBySubredditStmt: Database.Statement; private getBySubredditStmt: Database.Statement;
private countStmt: Database.Statement; private countStmt: Database.Statement;
private existsByMessageStmt: Database.Statement; private existsByMessageStmt: Database.Statement;
@@ -678,6 +679,17 @@ export class SuccessfulMessagesRepository {
SELECT * FROM successful_messages ORDER BY created_at DESC, id DESC LIMIT ? SELECT * FROM successful_messages ORDER BY created_at DESC, id DESC LIMIT ?
`); `);
this.getAttributedRecentStmt = db.prepare(`
SELECT successful_messages.*
FROM successful_messages
LEFT JOIN sent_messages sm ON sm.id = successful_messages.sent_message_id
WHERE successful_messages.subreddit IS NOT NULL
OR sm.post_id IS NOT NULL
OR sm.strategy_id IS NOT NULL
ORDER BY successful_messages.created_at DESC, successful_messages.id DESC
LIMIT ?
`);
// Get examples prioritizing same subreddit, then falling back to others // Get examples prioritizing same subreddit, then falling back to others
this.getBySubredditStmt = db.prepare(` this.getBySubredditStmt = db.prepare(`
SELECT *, SELECT *,
@@ -722,6 +734,11 @@ export class SuccessfulMessagesRepository {
return rows.map((row) => this.mapRow(row)); return rows.map((row) => this.mapRow(row));
} }
getAttributedRecent(limit: number = 5): SuccessfulMessageRecord[] {
const rows = this.getAttributedRecentStmt.all(limit) as Record<string, unknown>[];
return rows.map((row) => this.mapRow(row));
}
getWeightedExamples(subreddit: string | null, limit: number = 3): SuccessfulMessageRecord[] { getWeightedExamples(subreddit: string | null, limit: number = 3): SuccessfulMessageRecord[] {
if (subreddit) { if (subreddit) {
const rows = this.getBySubredditStmt.all(subreddit, limit) as Record<string, unknown>[]; const rows = this.getBySubredditStmt.all(subreddit, limit) as Record<string, unknown>[];
+1 -1
View File
@@ -50,7 +50,7 @@ export function createStatsRouter(ctx: WebContext): Router {
}); });
router.get('/successful', (_req, res) => { router.get('/successful', (_req, res) => {
res.json(ctx.repos.successful.getRecent(10)); res.json(ctx.repos.successful.getAttributedRecent(10));
}); });
return router; return router;
+44
View File
@@ -431,11 +431,15 @@ describe('MessagesRepository', () => {
describe('SuccessfulMessagesRepository', () => { describe('SuccessfulMessagesRepository', () => {
let successfulMessagesRepo: SuccessfulMessagesRepository; let successfulMessagesRepo: SuccessfulMessagesRepository;
let postsRepo: PostsRepository;
let messagesRepo: MessagesRepository;
let db: Database; let db: Database;
beforeEach(() => { beforeEach(() => {
const repos = createTestRepositories(); const repos = createTestRepositories();
successfulMessagesRepo = repos.successfulMessagesRepo; successfulMessagesRepo = repos.successfulMessagesRepo;
postsRepo = repos.postsRepo;
messagesRepo = repos.messagesRepo;
db = repos.db; db = repos.db;
}); });
@@ -520,6 +524,46 @@ describe('SuccessfulMessagesRepository', () => {
expect(recent[0].subreddit).toBeNull(); expect(recent[0].subreddit).toBeNull();
}); });
it('returns only examples attributable to a post, strategy, or subreddit', () => {
postsRepo.insert({
id: 'source-post',
subreddit: 'example',
author: 'alice',
title: 'Source post',
imageUrl: null,
processedAt: Date.now(),
});
const sentMessageId = messagesRepo.insert({
postId: 'source-post',
recipient: 'alice',
subject: 'alice',
message: 'Attributed opener',
sentAt: Date.now(),
strategyId: 'direct',
});
successfulMessagesRepo.insert({
sentMessageId,
originalMessage: 'Attributed opener',
imageAnalysis: null,
postTitle: 'Source post',
responseSnippet: 'Hello',
subreddit: null,
});
successfulMessagesRepo.insert({
sentMessageId: null,
originalMessage: 'Legacy unknown opener',
imageAnalysis: null,
postTitle: 'Chat with t2_unknown',
responseSnippet: 'Hello',
subreddit: null,
});
expect(successfulMessagesRepo.getAttributedRecent(10)).toEqual([
expect.objectContaining({ originalMessage: 'Attributed opener' }),
]);
expect(successfulMessagesRepo.getRecent(10)).toHaveLength(2);
});
it('returns most recent examples first', () => { it('returns most recent examples first', () => {
for (let i = 0; i < 5; i++) { for (let i = 0; i < 5; i++) {
successfulMessagesRepo.insert({ successfulMessagesRepo.insert({