feat: add conversation image previews and sharing
This commit is contained in:
1 parent
488145340d
commit
b573b88b08
20 files changed
+634
-26
No files matched your search
@@ -133,6 +133,72 @@ describe('conversations route', () => {
|
||||
expect(first.resources.activityLogRepo.insert).not.toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('lists and sends only request-matched library media through the owning runtime', async () => {
|
||||
const accountId = '@t2_one:reddit.com';
|
||||
const assetId = '11111111-1111-4111-8111-111111111111';
|
||||
const conversation = {
|
||||
username: 'alice', roomName: 'alice', roomId: 'room-one', url: '/room/room-one',
|
||||
lastMessageTime: 2, lastMessageSnippet: 'send a selfie', isFromUs: false, unread: true,
|
||||
messages: [
|
||||
{ sender: 'me', text: 'hello', timestamp: 1, isSelf: true },
|
||||
{ eventId: '$request', sender: 'alice', text: 'send a selfie', timestamp: 2, isSelf: false },
|
||||
],
|
||||
};
|
||||
const asset = {
|
||||
id: assetId, tags: ['selfie'], safety: 'sfw', classificationStatus: 'ready', description: 'selfie', confidence: 1,
|
||||
fileName: 'selfie.jpg', relativePath: 'nested/selfie.jpg', mimeType: 'image/jpeg', sizeBytes: 4,
|
||||
width: 10, height: 10, enabled: true, consentConfirmedAt: 1, createdAt: 1, updatedAt: 1,
|
||||
sendCount: 0, lastSentAt: null,
|
||||
};
|
||||
const mediaExchange = {
|
||||
listShareable: vi.fn().mockReturnValue({ requestKind: 'selfie', assets: [asset] }),
|
||||
handleSelected: vi.fn().mockResolvedValue({ kind: 'sent', assetId, requestKind: 'selfie' }),
|
||||
};
|
||||
const runtime = {
|
||||
snapshot: () => ({ state: 'running' }),
|
||||
resources: {
|
||||
chatService: {
|
||||
getCachedConversations: vi.fn().mockResolvedValue([conversation]),
|
||||
loadConversationDetails: vi.fn().mockResolvedValue(undefined),
|
||||
refreshTopChats: vi.fn().mockResolvedValue(undefined),
|
||||
},
|
||||
conversationStateRepo: { get: vi.fn(), save: vi.fn() },
|
||||
activityLogRepo: { insert: vi.fn() },
|
||||
mediaExchange,
|
||||
rateLimiter: { throttle: vi.fn((work: () => Promise<unknown>) => work()) },
|
||||
},
|
||||
};
|
||||
const context = {
|
||||
logger: { error: vi.fn() }, activity: { push: vi.fn() }, broadcaster: { push: vi.fn() },
|
||||
services: {
|
||||
chat: {},
|
||||
accountRuntimes: {
|
||||
list: () => [{ accountId, redditUsername: 'owner-one', state: 'running' }],
|
||||
get: (requested: string) => requested === accountId ? runtime : null,
|
||||
},
|
||||
},
|
||||
} as unknown as WebContext;
|
||||
const app = express().use(express.json()).use('/api', createConversationsRouter(context));
|
||||
const ownedId = `${encodeURIComponent(accountId)}~room-one`;
|
||||
|
||||
const optionsResponse = await request(app, `/api/conversations/${encodeURIComponent(ownedId)}/shareable-media`);
|
||||
expect(optionsResponse.status).toBe(200);
|
||||
expect(await optionsResponse.json()).toEqual({
|
||||
requestKind: 'selfie', reason: null,
|
||||
assets: [expect.objectContaining({ id: assetId, urlPath: '/library-media/nested/selfie.jpg' })],
|
||||
});
|
||||
|
||||
const sendResponse = await request(app, `/api/conversations/${encodeURIComponent(ownedId)}/share-media`, {
|
||||
method: 'POST', headers: { 'content-type': 'application/json' }, body: JSON.stringify({ assetId }),
|
||||
});
|
||||
expect(sendResponse.status).toBe(200);
|
||||
expect(await sendResponse.json()).toEqual({ success: true });
|
||||
expect(mediaExchange.handleSelected).toHaveBeenCalledWith('room-one', '$request', 'send a selfie', assetId);
|
||||
expect(runtime.resources.conversationStateRepo.save).toHaveBeenCalledWith('room-one', expect.objectContaining({
|
||||
automation: expect.objectContaining({ status: 'user-overridden' }),
|
||||
}));
|
||||
});
|
||||
|
||||
it('rejects an unowned conversation ID while account runtimes are active', async () => {
|
||||
const context = {
|
||||
logger: { error: vi.fn() },
|
||||
|
||||
Reference in new issue
Block a user