95 أسطر
3.3 KiB
TypeScript
95 أسطر
3.3 KiB
TypeScript
import { FollowsService } from './follows.service';
|
|
|
|
describe('FollowsService', () => {
|
|
it('keeps follow successful even if notification creation fails and resyncs counters', async () => {
|
|
const currentUserId = '507f1f77bcf86cd799439011';
|
|
const targetUserId = '507f191e810c19729de860ea';
|
|
|
|
const followsRepository = {
|
|
findOne: jest.fn().mockResolvedValue(null),
|
|
create: jest.fn().mockResolvedValue({ id: 'follow-1' }),
|
|
count: jest
|
|
.fn()
|
|
.mockResolvedValueOnce(6)
|
|
.mockResolvedValueOnce(14),
|
|
};
|
|
const usersRepository = {
|
|
findById: jest.fn().mockResolvedValue({ id: targetUserId }),
|
|
setFollowingCount: jest.fn().mockResolvedValue(undefined),
|
|
setFollowersCount: jest.fn().mockResolvedValue(undefined),
|
|
};
|
|
const outboxService = {
|
|
enqueueFollowNotification: jest.fn().mockRejectedValue(new Error('socket down')),
|
|
};
|
|
const blocksRepository = {
|
|
findAnyBetween: jest.fn().mockResolvedValue(null),
|
|
};
|
|
|
|
const service = new FollowsService(
|
|
followsRepository as any,
|
|
usersRepository as any,
|
|
outboxService as any,
|
|
{ bumpGlobalVersion: jest.fn().mockResolvedValue(1) } as any,
|
|
blocksRepository as any,
|
|
);
|
|
|
|
await expect(service.toggleFollow(currentUserId, { targetUserId })).resolves.toEqual({
|
|
following: true,
|
|
});
|
|
expect(usersRepository.setFollowingCount).toHaveBeenCalledWith(currentUserId, 6);
|
|
expect(usersRepository.setFollowersCount).toHaveBeenCalledWith(targetUserId, 14);
|
|
expect(outboxService.enqueueFollowNotification).toHaveBeenCalledWith(
|
|
currentUserId,
|
|
targetUserId,
|
|
'follow-1',
|
|
);
|
|
});
|
|
|
|
it('prevents users from following themselves', async () => {
|
|
const userId = '507f1f77bcf86cd799439011';
|
|
const service = new FollowsService(
|
|
{} as any,
|
|
{} as any,
|
|
{} as any,
|
|
{ bumpGlobalVersion: jest.fn() } as any,
|
|
{ findAnyBetween: jest.fn() } as any,
|
|
);
|
|
|
|
await expect(service.followUser(userId, userId)).rejects.toThrow('You cannot follow yourself');
|
|
});
|
|
|
|
it('returns already-following response without creating duplicate notification', async () => {
|
|
const currentUserId = '507f1f77bcf86cd799439011';
|
|
const targetUserId = '507f191e810c19729de860ea';
|
|
const followsRepository = {
|
|
findOne: jest.fn().mockResolvedValue({ id: 'existing-follow' }),
|
|
count: jest.fn().mockResolvedValueOnce(1).mockResolvedValueOnce(2),
|
|
create: jest.fn(),
|
|
};
|
|
const usersRepository = {
|
|
findById: jest.fn().mockResolvedValue({ id: targetUserId, isDisabled: false, isPrivate: false }),
|
|
setFollowingCount: jest.fn(),
|
|
setFollowersCount: jest.fn(),
|
|
};
|
|
const outboxService = {
|
|
enqueueFollowNotification: jest.fn(),
|
|
};
|
|
const service = new FollowsService(
|
|
followsRepository as any,
|
|
usersRepository as any,
|
|
outboxService as any,
|
|
{ bumpGlobalVersion: jest.fn() } as any,
|
|
{ findAnyBetween: jest.fn().mockResolvedValue(null) } as any,
|
|
);
|
|
|
|
await expect(service.followUser(currentUserId, targetUserId)).resolves.toMatchObject({
|
|
message: 'Already following user',
|
|
isFollowing: true,
|
|
followersCount: 2,
|
|
followingCount: 1,
|
|
});
|
|
expect(followsRepository.create).not.toHaveBeenCalled();
|
|
expect(outboxService.enqueueFollowNotification).not.toHaveBeenCalled();
|
|
});
|
|
});
|