chore(web,server): run code coverage reports (#1313)

* chore(web,server): run code coverage reports

* chore(tests): fail test check if coverage drops

* chore: disable e2e until they are fixed

* chore(web): coverage threshold
This commit is contained in:
Jason Rasmussen
2023-01-12 17:07:57 -05:00
committed by GitHub
parent 6db541c89b
commit 755a1331da
6 changed files with 233 additions and 86 deletions

View File

@@ -6,64 +6,77 @@ import { when } from 'jest-when';
import { UserService } from './user.service';
import { UpdateUserDto } from './dto/update-user.dto';
const adminUserAuth: AuthUserDto = Object.freeze({
id: 'admin_id',
email: 'admin@test.com',
isAdmin: true,
});
const immichUserAuth: AuthUserDto = Object.freeze({
id: 'immich_id',
email: 'immich@test.com',
isAdmin: false,
});
const adminUser: UserEntity = Object.freeze({
id: adminUserAuth.id,
email: 'admin@test.com',
password: 'admin_password',
firstName: 'admin_first_name',
lastName: 'admin_last_name',
isAdmin: true,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
const immichUser: UserEntity = Object.freeze({
id: immichUserAuth.id,
email: 'immich@test.com',
password: 'immich_password',
firstName: 'immich_first_name',
lastName: 'immich_last_name',
isAdmin: false,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
const updatedImmichUser: UserEntity = Object.freeze({
id: immichUserAuth.id,
email: 'immich@test.com',
password: 'immich_password',
firstName: 'updated_immich_first_name',
lastName: 'updated_immich_last_name',
isAdmin: false,
oauthId: '',
shouldChangePassword: true,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
const adminUserResponse = Object.freeze({
id: adminUserAuth.id,
email: 'admin@test.com',
deletedAt: undefined,
firstName: 'admin_first_name',
lastName: 'admin_last_name',
isAdmin: true,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
});
describe('UserService', () => {
let sut: UserService;
let userRepositoryMock: jest.Mocked<IUserRepository>;
const adminUserAuth: AuthUserDto = Object.freeze({
id: 'admin_id',
email: 'admin@test.com',
isAdmin: true,
});
const immichUserAuth: AuthUserDto = Object.freeze({
id: 'immich_id',
email: 'immich@test.com',
isAdmin: false,
});
const adminUser: UserEntity = Object.freeze({
id: adminUserAuth.id,
email: 'admin@test.com',
password: 'admin_password',
firstName: 'admin_first_name',
lastName: 'admin_last_name',
isAdmin: true,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
const immichUser: UserEntity = Object.freeze({
id: immichUserAuth.id,
email: 'immich@test.com',
password: 'immich_password',
firstName: 'immich_first_name',
lastName: 'immich_last_name',
isAdmin: false,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
const updatedImmichUser: UserEntity = Object.freeze({
id: immichUserAuth.id,
email: 'immich@test.com',
password: 'immich_password',
firstName: 'updated_immich_first_name',
lastName: 'updated_immich_last_name',
isAdmin: false,
oauthId: '',
shouldChangePassword: true,
profileImagePath: '',
createdAt: '2021-01-01',
tags: [],
});
beforeEach(() => {
userRepositoryMock = {
get: jest.fn(),
@@ -78,12 +91,86 @@ describe('UserService', () => {
};
when(userRepositoryMock.get).calledWith(adminUser.id).mockResolvedValue(adminUser);
when(userRepositoryMock.get).calledWith(adminUser.id, undefined).mockResolvedValue(adminUser);
when(userRepositoryMock.get).calledWith(immichUser.id).mockResolvedValue(immichUser);
when(userRepositoryMock.get).calledWith(immichUser.id, undefined).mockResolvedValue(immichUser);
sut = new UserService(userRepositoryMock);
});
describe('Update user', () => {
describe('getAllUsers', () => {
it('should get all users', async () => {
userRepositoryMock.getList.mockResolvedValue([adminUser]);
const response = await sut.getAllUsers(adminUserAuth, false);
expect(userRepositoryMock.getList).toHaveBeenCalledWith({ excludeId: adminUser.id });
expect(response).toEqual([
{
id: adminUserAuth.id,
email: 'admin@test.com',
deletedAt: undefined,
firstName: 'admin_first_name',
lastName: 'admin_last_name',
isAdmin: true,
oauthId: '',
shouldChangePassword: false,
profileImagePath: '',
createdAt: '2021-01-01',
},
]);
});
});
describe('getUserById', () => {
it('should get a user by id', async () => {
userRepositoryMock.get.mockResolvedValue(adminUser);
const response = await sut.getUserById(adminUser.id);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUser.id, false);
expect(response).toEqual(adminUserResponse);
});
it('should throw an error if a user is not found', async () => {
userRepositoryMock.get.mockResolvedValue(null);
await expect(sut.getUserById(adminUser.id)).rejects.toBeInstanceOf(NotFoundException);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUser.id, false);
});
});
describe('getUserInfo', () => {
it("should get the auth user's info", async () => {
userRepositoryMock.get.mockResolvedValue(adminUser);
const response = await sut.getUserInfo(adminUser);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUser.id, undefined);
expect(response).toEqual(adminUserResponse);
});
it('should throw an error if a user is not found', async () => {
userRepositoryMock.get.mockResolvedValue(null);
await expect(sut.getUserInfo(adminUser)).rejects.toBeInstanceOf(BadRequestException);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUser.id, undefined);
});
});
describe('getUserCount', () => {
it('should get the user count', async () => {
userRepositoryMock.getList.mockResolvedValue([adminUser]);
const response = await sut.getUserCount({});
expect(userRepositoryMock.getList).toHaveBeenCalled();
expect(response).toEqual({ userCount: 1 });
});
});
describe('update', () => {
it('should update user', async () => {
const update: UpdateUserDto = {
id: immichUser.id,
@@ -161,17 +248,7 @@ describe('UserService', () => {
await expect(result).rejects.toBeInstanceOf(NotFoundException);
});
});
describe('Delete user', () => {
it('cannot delete admin user', async () => {
const result = sut.deleteUser(adminUserAuth, adminUserAuth.id);
await expect(result).rejects.toBeInstanceOf(ForbiddenException);
});
});
describe('Create user', () => {
it('should let the admin update himself', async () => {
const dto = { id: adminUser.id, shouldChangePassword: true, isAdmin: true };
@@ -190,7 +267,37 @@ describe('UserService', () => {
await expect(sut.updateUser(adminUser, dto)).rejects.toBeInstanceOf(BadRequestException);
});
});
describe('restoreUser', () => {
it('should require an admin', async () => {
when(userRepositoryMock.get).calledWith(adminUser.id, true).mockResolvedValue(adminUser);
await expect(sut.restoreUser(immichUserAuth, adminUser.id)).rejects.toBeInstanceOf(ForbiddenException);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUser.id, true);
});
it('should require the auth user be an admin', async () => {
await expect(sut.deleteUser(immichUserAuth, adminUserAuth.id)).rejects.toBeInstanceOf(ForbiddenException);
expect(userRepositoryMock.delete).not.toHaveBeenCalled();
});
});
describe('deleteUser', () => {
it('cannot delete admin user', async () => {
const result = sut.deleteUser(adminUserAuth, adminUserAuth.id);
await expect(result).rejects.toBeInstanceOf(ForbiddenException);
});
it('should require the auth user be an admin', async () => {
await expect(sut.deleteUser(immichUserAuth, adminUserAuth.id)).rejects.toBeInstanceOf(ForbiddenException);
expect(userRepositoryMock.delete).not.toHaveBeenCalled();
});
});
describe('update', () => {
it('should not create a user if there is no local admin account', async () => {
when(userRepositoryMock.getAdmin).calledWith().mockResolvedValueOnce(null);
@@ -204,4 +311,33 @@ describe('UserService', () => {
).rejects.toBeInstanceOf(BadRequestException);
});
});
describe('createProfileImage', () => {
it('should throw an error if the user does not exist', async () => {
const file = { path: '/profile/path' } as Express.Multer.File;
userRepositoryMock.update.mockResolvedValue({ ...adminUser, profileImagePath: file.path });
await sut.createProfileImage(adminUserAuth, file);
expect(userRepositoryMock.update).toHaveBeenCalledWith(adminUserAuth.id, { profileImagePath: file.path });
});
});
describe('getUserProfileImage', () => {
it('should throw an error if the user does not exist', async () => {
userRepositoryMock.get.mockResolvedValue(null);
await expect(sut.getUserProfileImage(adminUserAuth.id)).rejects.toBeInstanceOf(NotFoundException);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUserAuth.id, undefined);
});
it('should throw an error if the user does not have a picture', async () => {
userRepositoryMock.get.mockResolvedValue(adminUser);
await expect(sut.getUserProfileImage(adminUserAuth.id)).rejects.toBeInstanceOf(NotFoundException);
expect(userRepositoryMock.get).toHaveBeenCalledWith(adminUserAuth.id, undefined);
});
});
});