refactor: asset files entity (#17527)

This commit is contained in:
Jason Rasmussen 2025-04-10 13:26:27 -04:00 committed by GitHub
parent 9fd2c5220d
commit eaa0e07329
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
7 changed files with 19 additions and 44 deletions

View File

@ -1,6 +1,6 @@
import { Selectable } from 'kysely'; import { Selectable } from 'kysely';
import { Exif as DatabaseExif } from 'src/db'; import { Exif as DatabaseExif } from 'src/db';
import { AlbumUserRole, AssetStatus, AssetType, MemoryType, Permission, UserStatus } from 'src/enum'; import { AlbumUserRole, AssetFileType, AssetStatus, AssetType, MemoryType, Permission, UserStatus } from 'src/enum';
import { OnThisDayData, UserMetadataItem } from 'src/types'; import { OnThisDayData, UserMetadataItem } from 'src/types';
export type AuthUser = { export type AuthUser = {
@ -17,6 +17,12 @@ export type AlbumUser = {
role: AlbumUserRole; role: AlbumUserRole;
}; };
export type AssetFile = {
id: string;
type: AssetFileType;
path: string;
};
export type Library = { export type Library = {
id: string; id: string;
ownerId: string; ownerId: string;

View File

@ -1,13 +0,0 @@
import { AssetEntity } from 'src/entities/asset.entity';
import { AssetFileType } from 'src/enum';
export class AssetFileEntity {
id!: string;
assetId!: string;
asset?: AssetEntity;
createdAt!: Date;
updatedAt!: Date;
updateId?: string;
type!: AssetFileType;
path!: string;
}

View File

@ -1,10 +1,9 @@
import { DeduplicateJoinsPlugin, ExpressionBuilder, Kysely, SelectQueryBuilder, sql } from 'kysely'; import { DeduplicateJoinsPlugin, ExpressionBuilder, Kysely, SelectQueryBuilder, sql } from 'kysely';
import { jsonArrayFrom, jsonObjectFrom } from 'kysely/helpers/postgres'; import { jsonArrayFrom, jsonObjectFrom } from 'kysely/helpers/postgres';
import { Exif, Tag, User } from 'src/database'; import { AssetFile, Exif, Tag, User } from 'src/database';
import { DB } from 'src/db'; import { DB } from 'src/db';
import { AlbumEntity } from 'src/entities/album.entity'; import { AlbumEntity } from 'src/entities/album.entity';
import { AssetFaceEntity } from 'src/entities/asset-face.entity'; import { AssetFaceEntity } from 'src/entities/asset-face.entity';
import { AssetFileEntity } from 'src/entities/asset-files.entity';
import { AssetJobStatusEntity } from 'src/entities/asset-job-status.entity'; import { AssetJobStatusEntity } from 'src/entities/asset-job-status.entity';
import { SharedLinkEntity } from 'src/entities/shared-link.entity'; import { SharedLinkEntity } from 'src/entities/shared-link.entity';
import { StackEntity } from 'src/entities/stack.entity'; import { StackEntity } from 'src/entities/stack.entity';
@ -25,7 +24,7 @@ export class AssetEntity {
type!: AssetType; type!: AssetType;
status!: AssetStatus; status!: AssetStatus;
originalPath!: string; originalPath!: string;
files!: AssetFileEntity[]; files!: AssetFile[];
thumbhash!: Buffer | null; thumbhash!: Buffer | null;
encodedVideoPath!: string | null; encodedVideoPath!: string | null;
createdAt!: Date; createdAt!: Date;

View File

@ -5,9 +5,9 @@ import {
UnauthorizedException, UnauthorizedException,
} from '@nestjs/common'; } from '@nestjs/common';
import { Stats } from 'node:fs'; import { Stats } from 'node:fs';
import { AssetFile } from 'src/database';
import { AssetMediaStatus, AssetRejectReason, AssetUploadAction } from 'src/dtos/asset-media-response.dto'; import { AssetMediaStatus, AssetRejectReason, AssetUploadAction } from 'src/dtos/asset-media-response.dto';
import { AssetMediaCreateDto, AssetMediaReplaceDto, AssetMediaSize, UploadFieldName } from 'src/dtos/asset-media.dto'; import { AssetMediaCreateDto, AssetMediaReplaceDto, AssetMediaSize, UploadFieldName } from 'src/dtos/asset-media.dto';
import { AssetFileEntity } from 'src/entities/asset-files.entity';
import { ASSET_CHECKSUM_CONSTRAINT, AssetEntity } from 'src/entities/asset.entity'; import { ASSET_CHECKSUM_CONSTRAINT, AssetEntity } from 'src/entities/asset.entity';
import { AssetFileType, AssetStatus, AssetType, CacheControl, JobName } from 'src/enum'; import { AssetFileType, AssetStatus, AssetType, CacheControl, JobName } from 'src/enum';
import { AuthRequest } from 'src/middleware/auth.guard'; import { AuthRequest } from 'src/middleware/auth.guard';
@ -166,7 +166,7 @@ const assetEntity = Object.freeze({
isArchived: false, isArchived: false,
encodedVideoPath: '', encodedVideoPath: '',
duration: '0:00:00.000000', duration: '0:00:00.000000',
files: [] as AssetFileEntity[], files: [] as AssetFile[],
exifInfo: { exifInfo: {
latitude: 49.533_547, latitude: 49.533_547,
longitude: 10.703_075, longitude: 10.703_075,
@ -535,12 +535,9 @@ describe(AssetMediaService.name, () => {
...assetStub.image, ...assetStub.image,
files: [ files: [
{ {
assetId: assetStub.image.id,
createdAt: assetStub.image.fileCreatedAt,
id: '42', id: '42',
path: '/path/to/preview', path: '/path/to/preview',
type: AssetFileType.THUMBNAIL, type: AssetFileType.THUMBNAIL,
updatedAt: new Date(),
}, },
], ],
}); });
@ -555,12 +552,9 @@ describe(AssetMediaService.name, () => {
...assetStub.image, ...assetStub.image,
files: [ files: [
{ {
assetId: assetStub.image.id,
createdAt: assetStub.image.fileCreatedAt,
id: '42', id: '42',
path: '/path/to/preview.jpg', path: '/path/to/preview.jpg',
type: AssetFileType.PREVIEW, type: AssetFileType.PREVIEW,
updatedAt: new Date(),
}, },
], ],
}); });

View File

@ -2,7 +2,6 @@ import { plainToInstance } from 'class-transformer';
import { defaults, SystemConfig } from 'src/config'; import { defaults, SystemConfig } from 'src/config';
import { AlbumUser } from 'src/database'; import { AlbumUser } from 'src/database';
import { SystemConfigDto } from 'src/dtos/system-config.dto'; import { SystemConfigDto } from 'src/dtos/system-config.dto';
import { AssetFileEntity } from 'src/entities/asset-files.entity';
import { AssetFileType, JobName, JobStatus, UserMetadataKey } from 'src/enum'; import { AssetFileType, JobName, JobStatus, UserMetadataKey } from 'src/enum';
import { EmailTemplate } from 'src/repositories/notification.repository'; import { EmailTemplate } from 'src/repositories/notification.repository';
import { NotificationService } from 'src/services/notification.service'; import { NotificationService } from 'src/services/notification.service';
@ -442,7 +441,7 @@ describe(NotificationService.name, () => {
mocks.notification.renderEmail.mockResolvedValue({ html: '', text: '' }); mocks.notification.renderEmail.mockResolvedValue({ html: '', text: '' });
mocks.asset.getById.mockResolvedValue({ mocks.asset.getById.mockResolvedValue({
...assetStub.image, ...assetStub.image,
files: [{ assetId: 'asset-id', type: AssetFileType.THUMBNAIL, path: 'path-to-thumb.jpg' } as AssetFileEntity], files: [{ id: '1', type: AssetFileType.THUMBNAIL, path: 'path-to-thumb.jpg' }],
}); });
await expect(sut.handleAlbumInvite({ id: '', recipientId: '' })).resolves.toBe(JobStatus.SUCCESS); await expect(sut.handleAlbumInvite({ id: '', recipientId: '' })).resolves.toBe(JobStatus.SUCCESS);

View File

@ -1,9 +1,9 @@
import { BadRequestException } from '@nestjs/common'; import { BadRequestException } from '@nestjs/common';
import { GeneratedImageType, StorageCore } from 'src/cores/storage.core'; import { GeneratedImageType, StorageCore } from 'src/cores/storage.core';
import { AssetFile } from 'src/database';
import { BulkIdErrorReason, BulkIdResponseDto } from 'src/dtos/asset-ids.response.dto'; import { BulkIdErrorReason, BulkIdResponseDto } from 'src/dtos/asset-ids.response.dto';
import { UploadFieldName } from 'src/dtos/asset-media.dto'; import { UploadFieldName } from 'src/dtos/asset-media.dto';
import { AuthDto } from 'src/dtos/auth.dto'; import { AuthDto } from 'src/dtos/auth.dto';
import { AssetFileEntity } from 'src/entities/asset-files.entity';
import { AssetFileType, AssetType, Permission } from 'src/enum'; import { AssetFileType, AssetType, Permission } from 'src/enum';
import { AuthRequest } from 'src/middleware/auth.guard'; import { AuthRequest } from 'src/middleware/auth.guard';
import { AccessRepository } from 'src/repositories/access.repository'; import { AccessRepository } from 'src/repositories/access.repository';
@ -20,7 +20,7 @@ export const getAssetFile = <T extends { type: AssetFileType }>(
return (files || []).find((file) => file.type === type); return (files || []).find((file) => file.type === type);
}; };
export const getAssetFiles = (files: AssetFileEntity[]) => ({ export const getAssetFiles = (files: AssetFile[]) => ({
fullsizeFile: getAssetFile(files, AssetFileType.FULLSIZE), fullsizeFile: getAssetFile(files, AssetFileType.FULLSIZE),
previewFile: getAssetFile(files, AssetFileType.PREVIEW), previewFile: getAssetFile(files, AssetFileType.PREVIEW),
thumbnailFile: getAssetFile(files, AssetFileType.THUMBNAIL), thumbnailFile: getAssetFile(files, AssetFileType.THUMBNAIL),

View File

@ -1,5 +1,4 @@
import { Exif } from 'src/database'; import { AssetFile, Exif } from 'src/database';
import { AssetFileEntity } from 'src/entities/asset-files.entity';
import { AssetEntity } from 'src/entities/asset.entity'; import { AssetEntity } from 'src/entities/asset.entity';
import { StackEntity } from 'src/entities/stack.entity'; import { StackEntity } from 'src/entities/stack.entity';
import { AssetFileType, AssetStatus, AssetType } from 'src/enum'; import { AssetFileType, AssetStatus, AssetType } from 'src/enum';
@ -8,34 +7,25 @@ import { authStub } from 'test/fixtures/auth.stub';
import { fileStub } from 'test/fixtures/file.stub'; import { fileStub } from 'test/fixtures/file.stub';
import { userStub } from 'test/fixtures/user.stub'; import { userStub } from 'test/fixtures/user.stub';
const previewFile: AssetFileEntity = { const previewFile: AssetFile = {
id: 'file-1', id: 'file-1',
assetId: 'asset-id',
type: AssetFileType.PREVIEW, type: AssetFileType.PREVIEW,
path: '/uploads/user-id/thumbs/path.jpg', path: '/uploads/user-id/thumbs/path.jpg',
createdAt: new Date('2023-02-23T05:06:29.716Z'),
updatedAt: new Date('2023-02-23T05:06:29.716Z'),
}; };
const thumbnailFile: AssetFileEntity = { const thumbnailFile: AssetFile = {
id: 'file-2', id: 'file-2',
assetId: 'asset-id',
type: AssetFileType.THUMBNAIL, type: AssetFileType.THUMBNAIL,
path: '/uploads/user-id/webp/path.ext', path: '/uploads/user-id/webp/path.ext',
createdAt: new Date('2023-02-23T05:06:29.716Z'),
updatedAt: new Date('2023-02-23T05:06:29.716Z'),
}; };
const fullsizeFile: AssetFileEntity = { const fullsizeFile: AssetFile = {
id: 'file-3', id: 'file-3',
assetId: 'asset-id',
type: AssetFileType.FULLSIZE, type: AssetFileType.FULLSIZE,
path: '/uploads/user-id/fullsize/path.webp', path: '/uploads/user-id/fullsize/path.webp',
createdAt: new Date('2023-02-23T05:06:29.716Z'),
updatedAt: new Date('2023-02-23T05:06:29.716Z'),
}; };
const files: AssetFileEntity[] = [fullsizeFile, previewFile, thumbnailFile]; const files: AssetFile[] = [fullsizeFile, previewFile, thumbnailFile];
export const stackStub = (stackId: string, assets: AssetEntity[]): StackEntity => { export const stackStub = (stackId: string, assets: AssetEntity[]): StackEntity => {
return { return {