Skip to content

Commit

Permalink
refactor: orientation
Browse files Browse the repository at this point in the history
  • Loading branch information
jrasm91 committed Sep 19, 2024
1 parent 0b02fda commit ec48359
Show file tree
Hide file tree
Showing 12 changed files with 229 additions and 45 deletions.
98 changes: 96 additions & 2 deletions mobile/openapi/lib/model/exif_response_dto.dart

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

12 changes: 11 additions & 1 deletion open-api/immich-openapi-specs.json
Original file line number Diff line number Diff line change
Expand Up @@ -9074,8 +9074,18 @@
},
"orientation": {
"default": null,
"enum": [
1,
2,
8,
7,
3,
4,
6,
5
],
"nullable": true,
"type": "string"
"type": "number"
},
"projectionType": {
"default": null,
Expand Down
12 changes: 11 additions & 1 deletion open-api/typescript-sdk/src/fetch-client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,7 @@ export type ExifResponseDto = {
make?: string | null;
model?: string | null;
modifyDate?: string | null;
orientation?: string | null;
orientation?: Orientation | null;
projectionType?: string | null;
rating?: number | null;
state?: string | null;
Expand Down Expand Up @@ -3266,6 +3266,16 @@ export enum AlbumUserRole {
Editor = "editor",
Viewer = "viewer"
}
export enum Orientation {
$1 = 1,
$2 = 2,
$8 = 8,
$7 = 7,
$3 = 3,
$4 = 4,
$6 = 6,
$5 = 5
}
export enum SourceType {
MachineLearning = "machine-learning",
Exif = "exif"
Expand Down
12 changes: 12 additions & 0 deletions open-api/typescript-sdk/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { defaults } from './fetch-client.js';
export { Orientation as LameGeneratedOrientation } from './fetch-client.js';

export * from './fetch-client.js';
export * from './fetch-errors.js';
Expand All @@ -8,6 +9,17 @@ export interface InitOptions {
apiKey: string;
}

export enum Orientation {
Rotate0 = 1,
Rotate0Mirrored = 2,
Rotate90 = 8,
Rotate90Mirrored = 7,
Rotate180 = 3,
Rotate180Mirrored = 4,
Rotate270 = 6,
Rotate270Mirrored = 5,
}

export const init = ({ baseUrl, apiKey }: InitOptions) => {
setBaseUrl(baseUrl);
setApiKey(apiKey);
Expand Down
5 changes: 4 additions & 1 deletion server/src/dtos/exif.dto.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { ApiProperty } from '@nestjs/swagger';
import { ExifEntity } from 'src/entities/exif.entity';
import { Orientation } from 'src/enum';

export class ExifResponseDto {
make?: string | null = null;
Expand All @@ -9,7 +10,9 @@ export class ExifResponseDto {

@ApiProperty({ type: 'integer', format: 'int64' })
fileSizeInByte?: number | null = null;
orientation?: string | null = null;

@ApiProperty({ enum: Orientation })
orientation?: Orientation | null = null;
dateTimeOriginal?: Date | null = null;
modifyDate?: Date | null = null;
timeZone?: string | null = null;
Expand Down
5 changes: 3 additions & 2 deletions server/src/entities/exif.entity.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { AssetEntity } from 'src/entities/asset.entity';
import { Orientation } from 'src/enum';
import { Index, JoinColumn, OneToOne, PrimaryColumn } from 'typeorm';
import { Column } from 'typeorm/decorator/columns/Column.js';
import { Entity } from 'typeorm/decorator/entity/Entity.js';
Expand All @@ -25,8 +26,8 @@ export class ExifEntity {
@Column({ type: 'bigint', nullable: true })
fileSizeInByte!: number | null;

@Column({ type: 'varchar', nullable: true })
orientation!: string | null;
@Column({ type: 'enum', enum: Orientation, nullable: true })
orientation!: Orientation | null;

@Column({ type: 'timestamptz', nullable: true })
dateTimeOriginal!: Date | null;
Expand Down
11 changes: 11 additions & 0 deletions server/src/enum.ts
Original file line number Diff line number Diff line change
Expand Up @@ -198,3 +198,14 @@ export enum ManualJobName {
TAG_CLEANUP = 'tag-cleanup',
USER_CLEANUP = 'user-cleanup',
}

export enum Orientation {
Rotate0 = 1,
Rotate0Mirrored = 2,
Rotate90 = 8,
Rotate90Mirrored = 7,
Rotate180 = 3,
Rotate180Mirrored = 4,
Rotate270 = 6,
Rotate270Mirrored = 5,
}
31 changes: 31 additions & 0 deletions server/src/migrations/1726754669860-AddOrientationEnum.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { MigrationInterface, QueryRunner } from "typeorm";

export class AddOrientationEnum1726754669860 implements MigrationInterface {
name = 'AddOrientationEnum1726754669860'

public async up(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`CREATE TYPE "exif_orientation_enum" AS ENUM('1', '2', '3', '4', '5', '6', '7', '8')`)
await queryRunner.query(`
UPDATE "exif" SET "orientation" = CASE
WHEN "orientation" = '0' THEN '1'
WHEN "orientation" = '1' THEN '1'
WHEN "orientation" = '2' THEN '2'
WHEN "orientation" = '3' THEN '3'
WHEN "orientation" = '4' THEN '4'
WHEN "orientation" = '5' THEN '5'
WHEN "orientation" = '6' THEN '6'
WHEN "orientation" = '7' THEN '7'
WHEN "orientation" = '8' THEN '8'
WHEN "orientation" = '-90' THEN '6'
WHEN "orientation" = '90' THEN '8'
WHEN "orientation" = '180' THEN '3'
ELSE NULL
END`);
await queryRunner.query(`ALTER TABLE "exif" ALTER COLUMN "orientation" TYPE "exif_orientation_enum" USING "orientation"::"exif_orientation_enum"`);
}

public async down(queryRunner: QueryRunner): Promise<void> {
await queryRunner.query(`ALTER TABLE "exif" ALTER COLUMN "orientation" TYPE character varying USING "orientation"::text`);
await queryRunner.query(`DROP TYPE "exif_orientation_enum"`);
}
}
12 changes: 5 additions & 7 deletions server/src/services/metadata.service.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { randomBytes } from 'node:crypto';
import { Stats } from 'node:fs';
import { constants } from 'node:fs/promises';
import { ExifEntity } from 'src/entities/exif.entity';
import { AssetType, SourceType } from 'src/enum';
import { AssetType, Orientation, SourceType } from 'src/enum';
import { IAlbumRepository } from 'src/interfaces/album.interface';
import { IAssetRepository, WithoutProperty } from 'src/interfaces/asset.interface';
import { ICryptoRepository } from 'src/interfaces/crypto.interface';
Expand All @@ -20,7 +20,7 @@ import { IStorageRepository } from 'src/interfaces/storage.interface';
import { ISystemMetadataRepository } from 'src/interfaces/system-metadata.interface';
import { ITagRepository } from 'src/interfaces/tag.interface';
import { IUserRepository } from 'src/interfaces/user.interface';
import { MetadataService, Orientation } from 'src/services/metadata.service';
import { MetadataService } from 'src/services/metadata.service';
import { assetStub } from 'test/fixtures/asset.stub';
import { fileStub } from 'test/fixtures/file.stub';
import { probeStub } from 'test/fixtures/media.stub';
Expand Down Expand Up @@ -537,9 +537,7 @@ describe(MetadataService.name, () => {
await sut.handleMetadataExtraction({ id: assetStub.video.id });

expect(assetMock.getByIds).toHaveBeenCalledWith([assetStub.video.id]);
expect(assetMock.upsertExif).toHaveBeenCalledWith(
expect.objectContaining({ orientation: Orientation.Rotate270CW.toString() }),
);
expect(assetMock.upsertExif).toHaveBeenCalledWith(expect.objectContaining({ orientation: Orientation.Rotate90 }));
});

it('should extract the MotionPhotoVideo tag from Samsung HEIC motion photos', async () => {
Expand Down Expand Up @@ -786,7 +784,7 @@ describe(MetadataService.name, () => {
Make: 'test-factory',
Model: "'mockel'",
ModifyDate: ExifDateTime.fromISO(dateForTest.toISOString()),
Orientation: 0,
Orientation: 1,
ProfileDescription: 'extensive description',
ProjectionType: 'equirectangular',
tz: 'UTC-11:30',
Expand Down Expand Up @@ -819,7 +817,7 @@ describe(MetadataService.name, () => {
make: tags.Make,
model: tags.Model,
modifyDate: expect.any(Date),
orientation: tags.Orientation?.toString(),
orientation: 1,
profileDescription: tags.ProfileDescription,
projectionType: 'EQUIRECTANGULAR',
timeZone: tags.tz,
Expand Down
Loading

0 comments on commit ec48359

Please sign in to comment.