mirror of
https://github.com/KevinMidboe/immich.git
synced 2025-10-29 17:40:28 +00:00
chore(server,mobile): remove device info entity (#1527)
* chore(server): remove unused device info code * chore: generate open api * remove any DeviceTypeEnum usage from mobile * chore: coverage * fix: drop device info table --------- Co-authored-by: Fynn Petersen-Frey <zody22@gmail.com>
This commit is contained in:
@@ -1,23 +0,0 @@
|
||||
import { DeviceInfoEntity } from '@app/infra/entities';
|
||||
import { IDeviceInfoRepository } from './device-info.repository';
|
||||
|
||||
type UpsertKeys = Pick<DeviceInfoEntity, 'deviceId' | 'userId'>;
|
||||
type UpsertEntity = UpsertKeys & Partial<DeviceInfoEntity>;
|
||||
|
||||
export class DeviceInfoCore {
|
||||
constructor(private repository: IDeviceInfoRepository) {}
|
||||
|
||||
async upsert(entity: UpsertEntity) {
|
||||
const exists = await this.repository.get(entity.userId, entity.deviceId);
|
||||
if (!exists) {
|
||||
if (!entity.isAutoBackup) {
|
||||
entity.isAutoBackup = false;
|
||||
}
|
||||
return this.repository.save(entity);
|
||||
}
|
||||
|
||||
exists.isAutoBackup = entity.isAutoBackup ?? exists.isAutoBackup;
|
||||
exists.deviceType = entity.deviceType ?? exists.deviceType;
|
||||
return this.repository.save(exists);
|
||||
}
|
||||
}
|
||||
@@ -1,8 +0,0 @@
|
||||
import { DeviceInfoEntity } from '@app/infra/entities';
|
||||
|
||||
export const IDeviceInfoRepository = 'IDeviceInfoRepository';
|
||||
|
||||
export interface IDeviceInfoRepository {
|
||||
get(userId: string, deviceId: string): Promise<DeviceInfoEntity | null>;
|
||||
save(entity: Partial<DeviceInfoEntity>): Promise<DeviceInfoEntity>;
|
||||
}
|
||||
@@ -1,63 +0,0 @@
|
||||
import { DeviceInfoEntity, DeviceType } from '@app/infra/entities';
|
||||
import { authStub, newDeviceInfoRepositoryMock } from '../../test';
|
||||
import { IDeviceInfoRepository } from './device-info.repository';
|
||||
import { DeviceInfoService } from './device-info.service';
|
||||
|
||||
const deviceId = 'device-123';
|
||||
const userId = 'user-123';
|
||||
|
||||
describe('DeviceInfoService', () => {
|
||||
let sut: DeviceInfoService;
|
||||
let repositoryMock: jest.Mocked<IDeviceInfoRepository>;
|
||||
|
||||
beforeEach(async () => {
|
||||
repositoryMock = newDeviceInfoRepositoryMock();
|
||||
|
||||
sut = new DeviceInfoService(repositoryMock);
|
||||
});
|
||||
|
||||
it('should be defined', () => {
|
||||
expect(sut).toBeDefined();
|
||||
});
|
||||
|
||||
describe('upsert', () => {
|
||||
it('should create a new record', async () => {
|
||||
const request = { deviceId, userId, deviceType: DeviceType.IOS } as DeviceInfoEntity;
|
||||
const response = { ...request, id: 1 } as DeviceInfoEntity;
|
||||
|
||||
repositoryMock.get.mockResolvedValue(null);
|
||||
repositoryMock.save.mockResolvedValue(response);
|
||||
|
||||
await expect(sut.upsert(authStub.user1, request)).resolves.toEqual(response);
|
||||
|
||||
expect(repositoryMock.get).toHaveBeenCalledTimes(1);
|
||||
expect(repositoryMock.save).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it('should update an existing record', async () => {
|
||||
const request = { deviceId, userId, deviceType: DeviceType.IOS, isAutoBackup: true } as DeviceInfoEntity;
|
||||
const response = { ...request, id: 1 } as DeviceInfoEntity;
|
||||
|
||||
repositoryMock.get.mockResolvedValue(response);
|
||||
repositoryMock.save.mockResolvedValue(response);
|
||||
|
||||
await expect(sut.upsert(authStub.user1, request)).resolves.toEqual(response);
|
||||
|
||||
expect(repositoryMock.get).toHaveBeenCalledTimes(1);
|
||||
expect(repositoryMock.save).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it('should keep properties that were not updated', async () => {
|
||||
const request = { deviceId, userId } as DeviceInfoEntity;
|
||||
const response = { id: 1, isAutoBackup: true, deviceId, userId, deviceType: DeviceType.WEB } as DeviceInfoEntity;
|
||||
|
||||
repositoryMock.get.mockResolvedValue(response);
|
||||
repositoryMock.save.mockResolvedValue(response);
|
||||
|
||||
await expect(sut.upsert(authStub.user1, request)).resolves.toEqual(response);
|
||||
|
||||
expect(repositoryMock.get).toHaveBeenCalledTimes(1);
|
||||
expect(repositoryMock.save).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1,20 +0,0 @@
|
||||
import { Inject, Injectable } from '@nestjs/common';
|
||||
import { AuthUserDto } from '../auth';
|
||||
import { DeviceInfoCore } from './device-info.core';
|
||||
import { IDeviceInfoRepository } from './device-info.repository';
|
||||
import { UpsertDeviceInfoDto } from './dto';
|
||||
import { DeviceInfoResponseDto, mapDeviceInfoResponse } from './response-dto';
|
||||
|
||||
@Injectable()
|
||||
export class DeviceInfoService {
|
||||
private core: DeviceInfoCore;
|
||||
|
||||
constructor(@Inject(IDeviceInfoRepository) repository: IDeviceInfoRepository) {
|
||||
this.core = new DeviceInfoCore(repository);
|
||||
}
|
||||
|
||||
public async upsert(authUser: AuthUserDto, dto: UpsertDeviceInfoDto): Promise<DeviceInfoResponseDto> {
|
||||
const deviceInfo = await this.core.upsert({ ...dto, userId: authUser.id });
|
||||
return mapDeviceInfoResponse(deviceInfo);
|
||||
}
|
||||
}
|
||||
@@ -1 +0,0 @@
|
||||
export * from './upsert-device-info.dto';
|
||||
@@ -1,15 +0,0 @@
|
||||
import { IsNotEmpty, IsOptional } from 'class-validator';
|
||||
import { DeviceType } from '@app/infra/entities';
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
|
||||
export class UpsertDeviceInfoDto {
|
||||
@IsNotEmpty()
|
||||
deviceId!: string;
|
||||
|
||||
@IsNotEmpty()
|
||||
@ApiProperty({ enumName: 'DeviceTypeEnum', enum: DeviceType })
|
||||
deviceType!: DeviceType;
|
||||
|
||||
@IsOptional()
|
||||
isAutoBackup?: boolean;
|
||||
}
|
||||
@@ -1,4 +0,0 @@
|
||||
export * from './device-info.repository';
|
||||
export * from './device-info.service';
|
||||
export * from './dto';
|
||||
export * from './response-dto';
|
||||
@@ -1,26 +0,0 @@
|
||||
import { DeviceInfoEntity, DeviceType } from '@app/infra/entities';
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
|
||||
export class DeviceInfoResponseDto {
|
||||
@ApiProperty({ type: 'integer' })
|
||||
id!: number;
|
||||
userId!: string;
|
||||
deviceId!: string;
|
||||
|
||||
@ApiProperty({ enumName: 'DeviceTypeEnum', enum: DeviceType })
|
||||
deviceType!: DeviceType;
|
||||
|
||||
createdAt!: string;
|
||||
isAutoBackup!: boolean;
|
||||
}
|
||||
|
||||
export function mapDeviceInfoResponse(entity: DeviceInfoEntity): DeviceInfoResponseDto {
|
||||
return {
|
||||
id: entity.id,
|
||||
userId: entity.userId,
|
||||
deviceId: entity.deviceId,
|
||||
deviceType: entity.deviceType,
|
||||
createdAt: entity.createdAt,
|
||||
isAutoBackup: entity.isAutoBackup,
|
||||
};
|
||||
}
|
||||
@@ -1 +0,0 @@
|
||||
export * from './device-info-response.dto';
|
||||
@@ -3,7 +3,6 @@ import { AlbumService } from './album';
|
||||
import { APIKeyService } from './api-key';
|
||||
import { AssetService } from './asset';
|
||||
import { AuthService } from './auth';
|
||||
import { DeviceInfoService } from './device-info';
|
||||
import { JobService } from './job';
|
||||
import { MediaService } from './media';
|
||||
import { OAuthService } from './oauth';
|
||||
@@ -21,7 +20,6 @@ const providers: Provider[] = [
|
||||
AssetService,
|
||||
APIKeyService,
|
||||
AuthService,
|
||||
DeviceInfoService,
|
||||
JobService,
|
||||
MediaService,
|
||||
OAuthService,
|
||||
|
||||
@@ -4,7 +4,6 @@ export * from './asset';
|
||||
export * from './auth';
|
||||
export * from './communication';
|
||||
export * from './crypto';
|
||||
export * from './device-info';
|
||||
export * from './domain.config';
|
||||
export * from './domain.constant';
|
||||
export * from './domain.module';
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
import { IDeviceInfoRepository } from '../src';
|
||||
|
||||
export const newDeviceInfoRepositoryMock = (): jest.Mocked<IDeviceInfoRepository> => {
|
||||
return {
|
||||
get: jest.fn(),
|
||||
save: jest.fn(),
|
||||
};
|
||||
};
|
||||
@@ -3,7 +3,6 @@ export * from './api-key.repository.mock';
|
||||
export * from './asset.repository.mock';
|
||||
export * from './communication.repository.mock';
|
||||
export * from './crypto.repository.mock';
|
||||
export * from './device-info.repository.mock';
|
||||
export * from './fixtures';
|
||||
export * from './job.repository.mock';
|
||||
export * from './machine-learning.repository.mock';
|
||||
|
||||
Reference in New Issue
Block a user