Add manual outreach funnel clearing
This commit is contained in:
1 parent
6b2e1bc380
commit
4798385d8b
16 files changed
+319
-17
No files matched your search
@@ -164,6 +164,39 @@ describe('CandidateQueueRepository', () => {
|
||||
expect(queue.getStats().byStatus.discovered).toBe(1);
|
||||
});
|
||||
|
||||
it('manually clears every unsent stage while retaining an in-flight send', () => {
|
||||
queue.enqueue([post('sending', 'alice')], 'image', 1, 1_000);
|
||||
const sendingScreen = queue.claimForScreening('screen-sending', 1_000, 1_001)!;
|
||||
queue.markReady(sendingScreen.postId, 'screen-sending', prepared(sendingScreen.post), 1_002);
|
||||
queue.claimReady('account-a', 'send-worker', 1_000, 1_003);
|
||||
|
||||
queue.enqueue([post('retryable', 'bob')], 'image', 1, 1_004);
|
||||
const retryScreen = queue.claimForScreening('screen-retry', 1_000, 1_005)!;
|
||||
queue.markReady(retryScreen.postId, 'screen-retry', prepared(retryScreen.post), 1_006);
|
||||
queue.claimReady('account-b', 'retry-worker', 1_000, 1_007);
|
||||
queue.deferDelivery('retryable', 'retry-worker', 'rate limited', 2_000, 1_008);
|
||||
|
||||
queue.enqueue([post('ready', 'carol')], 'image', 1, 1_009);
|
||||
const readyScreen = queue.claimForScreening('screen-ready', 1_000, 1_010)!;
|
||||
queue.markReady(readyScreen.postId, 'screen-ready', prepared(readyScreen.post), 1_011);
|
||||
queue.enqueue([post('screening', 'dana')], 'image', 1, 1_012);
|
||||
queue.claimForScreening('screen-active', 1_000, 1_013);
|
||||
queue.enqueue([post('discovered', 'erin')], 'image', 1, 1_014);
|
||||
|
||||
expect(queue.clearUnsent(1_020)).toEqual({
|
||||
discovered: 1, screening: 1, ready: 1, retryable: 1, total: 4, retainedSending: 1,
|
||||
});
|
||||
expect(queue.listActive()).toEqual([
|
||||
expect.objectContaining({ postId: 'sending', status: 'sending', leaseOwner: 'send-worker' }),
|
||||
]);
|
||||
expect(queue.markReady('screening', 'screen-active', prepared(post('screening', 'dana')), 1_021)).toBe(false);
|
||||
expect(queue.markSent('sending', 'send-worker', 1_022)).toBe(true);
|
||||
expect(queue.getStats()).toMatchObject({ byStatus: { rejected: 4, sent: 1 } });
|
||||
const reasons = db.prepare(`SELECT DISTINCT last_error FROM candidate_queue WHERE status = 'rejected'`)
|
||||
.all() as Array<{ last_error: string }>;
|
||||
expect(reasons).toEqual([{ last_error: 'Cleared manually by operator' }]);
|
||||
});
|
||||
|
||||
it('retries a rate-limited prepared candidate and preserves its generated message', () => {
|
||||
queue.enqueue([post('p1', 'alice')], 'image', 1, 1_000);
|
||||
const screening = queue.claimForScreening('screen', 100, 1_001)!;
|
||||
|
||||
Reference in new issue
Block a user