Add varied messaging experiments
This commit is contained in:
1 parent
43f459a024
commit
23d4c3a320
12 files changed
+217
-72
No files matched your search
@@ -33,6 +33,7 @@ export function isSkip(result: ProcessResult): result is SkipResult {
|
||||
}
|
||||
|
||||
export type ImageFetcher = (url: string, userAgent: string) => Promise<DownloadedImage>;
|
||||
export type RecentMessageProvider = (sourceType: 'image' | 'chat') => readonly string[];
|
||||
|
||||
export class ProcessorService {
|
||||
private successfulExamples: string[] = [];
|
||||
@@ -46,6 +47,7 @@ export class ProcessorService {
|
||||
private config: Config,
|
||||
private logger: Logger,
|
||||
fetchImage?: ImageFetcher,
|
||||
private readonly recentMessageProvider: RecentMessageProvider = () => [],
|
||||
) {
|
||||
this.fetchImage = fetchImage ?? downloadImage;
|
||||
}
|
||||
@@ -183,7 +185,8 @@ export class ProcessorService {
|
||||
this.successfulExamples,
|
||||
scriptedPrompt,
|
||||
post.link_flair_text ?? undefined,
|
||||
undefined
|
||||
undefined,
|
||||
this.recentMessageProvider('image'),
|
||||
));
|
||||
} else {
|
||||
({ analysis, message } = await this.aiClient.analyzeAndGenerateMessage(
|
||||
@@ -195,6 +198,7 @@ export class ProcessorService {
|
||||
selectedStrategy?.promptOverride,
|
||||
post.link_flair_text ?? undefined,
|
||||
tone.profile.promptGuidance || undefined,
|
||||
this.recentMessageProvider('image'),
|
||||
));
|
||||
}
|
||||
} catch (error) {
|
||||
@@ -268,7 +272,8 @@ export class ProcessorService {
|
||||
this.successfulExamples,
|
||||
scriptedPrompt,
|
||||
post.link_flair_text ?? undefined,
|
||||
undefined
|
||||
undefined,
|
||||
this.recentMessageProvider('chat'),
|
||||
);
|
||||
} else {
|
||||
message = await this.aiClient.generateChatOpener(
|
||||
@@ -280,6 +285,7 @@ export class ProcessorService {
|
||||
selectedStrategy?.promptOverride,
|
||||
post.link_flair_text ?? undefined,
|
||||
tone.profile.promptGuidance || undefined,
|
||||
this.recentMessageProvider('chat'),
|
||||
);
|
||||
}
|
||||
} catch (error) {
|
||||
|
||||
@@ -127,7 +127,17 @@ async function buildRuntime(
|
||||
redditApi, postsRepo, recipientDeduplicator, accountConfig, logger,
|
||||
1000, createConfigBackedSubredditPollingControl(config, new ConfigStore(db), logger),
|
||||
);
|
||||
const processorService = new ProcessorService(redditApi, aiClient, accountConfig, logger);
|
||||
const processorService = new ProcessorService(
|
||||
redditApi,
|
||||
aiClient,
|
||||
accountConfig,
|
||||
logger,
|
||||
undefined,
|
||||
(sourceType) => messagesRepo
|
||||
.getRecent(20)
|
||||
.filter((message) => message.sourceType === sourceType || (sourceType === 'image' && !message.sourceType))
|
||||
.map((message) => message.message),
|
||||
);
|
||||
processorService.setStrategySelector(new StrategySelector(accountConfig, messagesRepo, logger));
|
||||
processorService.setChatStrategySelector(new StrategySelector(accountConfig, messagesRepo, logger, 'chatStrategies'));
|
||||
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import { createHash } from 'node:crypto';
|
||||
import type { Config } from '../config/index.js';
|
||||
import type { MessagesRepository, StrategyStats } from '../database/repositories.js';
|
||||
import type { Logger } from '../utils/logger.js';
|
||||
@@ -54,7 +55,13 @@ export class StrategySelector {
|
||||
});
|
||||
|
||||
if (unexplored.length > 0) {
|
||||
const variant = this.weightedChoice(unexplored);
|
||||
const observedCount = (variant: Config['strategies']['variants'][number]): number => {
|
||||
const stats = statsMap.get(variant.id);
|
||||
return (stats?.totalSent ?? 0) + (stats?.pendingSent ?? 0);
|
||||
};
|
||||
const smallestSample = Math.min(...unexplored.map(observedCount));
|
||||
const leastSampled = unexplored.filter((variant) => observedCount(variant) === smallestSample);
|
||||
const variant = this.weightedChoice(leastSampled);
|
||||
this.logger.debug(`Strategy selected (under-sampled): ${variant.id}`);
|
||||
return this.selected(variant, 'explore');
|
||||
}
|
||||
@@ -137,4 +144,3 @@ export class StrategySelector {
|
||||
return variants[variants.length - 1];
|
||||
}
|
||||
}
|
||||
import { createHash } from 'node:crypto';
|
||||
Reference in new issue
Block a user