Skip to content

Commit

Permalink
Feature: delete asset within edit form
Browse files Browse the repository at this point in the history
  • Loading branch information
TIL-EBP committed Nov 6, 2024
1 parent b602148 commit df60950
Show file tree
Hide file tree
Showing 34 changed files with 554 additions and 264 deletions.
3 changes: 3 additions & 0 deletions apps/client-asset-sg/src/app/i18n/de.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,9 @@ export const deAppTranslations = {
ok: 'OK',
submit: 'Absenden',
cancel: 'Abbrechen',
confirm: 'Bestätigen',
confirmDelete: 'Sind Sie sicher, dass Sie dieses Asset löschen wollen?',
deleteSuccess: 'Das Asset wurde erfolgreich gelöscht.',
login: 'Anmelden',
logout: 'Abmelden',
yes: 'Ja',
Expand Down
3 changes: 3 additions & 0 deletions apps/client-asset-sg/src/app/i18n/en.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ export const enAppTranslations: AppTranslations = {
ok: 'OK',
submit: 'Submit',
cancel: 'Cancel',
confirm: 'Confirm',
confirmDelete: 'Are you sure you want to delete this asset?',
deleteSuccess: 'The asset was successfully deleted.',
login: 'Login',
logout: 'Logout',
yes: 'Yes',
Expand Down
3 changes: 3 additions & 0 deletions apps/client-asset-sg/src/app/i18n/fr.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ export const frAppTranslations: AppTranslations = {
ok: 'OK',
submit: 'Envoyer',
cancel: 'Annuler',
confirm: 'Confirmer',
confirmDelete: 'Êtes-vous sûr de vouloir supprimer cet asset',
deleteSuccess: "L'asset a été supprimé avec succès.",
login: 'Login',
logout: 'Déconnecter',
yes: 'Oui',
Expand Down
3 changes: 3 additions & 0 deletions apps/client-asset-sg/src/app/i18n/it.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ export const itAppTranslations: AppTranslations = {
ok: 'OK',
submit: 'IT Absenden',
cancel: 'IT Abbrechen',
confirm: 'IT Bestätigen',
confirmDelete: 'IT Sind Sie sicher, dass Sie dieses Asset löschen möchten?',
deleteSuccess: 'IT Das Asset wurde erfolgreich gelöscht.',
login: 'Login',
logout: 'IT Abmelden',
yes: 'Sì',
Expand Down
3 changes: 3 additions & 0 deletions apps/client-asset-sg/src/app/i18n/rm.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ export const rmAppTranslations: AppTranslations = {
ok: 'OK',
submit: 'RM Absenden',
cancel: 'RM Abbrechen',
confirm: 'RM Bestätigen',
confirmDelete: 'RM Sind Sie sicher, dass Sie dieses Asset löschen möchten?',
deleteSuccess: 'RM Das Asset wurde erfolgreich gelöscht.',
login: 'Login',
logout: 'RM Abmelden',
yes: 'Sì',
Expand Down
2 changes: 0 additions & 2 deletions apps/server-asset-sg/src/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import { JwtMiddleware } from '@/core/middleware/jwt.middleware';
import { PrismaService } from '@/core/prisma.service';
import { AssetEditController } from '@/features/asset-edit/asset-edit.controller';
import { AssetEditRepo } from '@/features/asset-edit/asset-edit.repo';
import { AssetEditService } from '@/features/asset-edit/asset-edit.service';
import { AssetInfoRepo } from '@/features/assets/asset-info.repo';
import { AssetRepo } from '@/features/assets/asset.repo';
import { AssetsController } from '@/features/assets/assets.controller';
Expand Down Expand Up @@ -51,7 +50,6 @@ import { WorkgroupsController } from '@/features/workgroups/workgroups.controlle
providers: [
provideElasticsearch,
AssetEditRepo,
AssetEditService,
AssetInfoRepo,
AssetRepo,
AssetSearchService,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,17 +1,27 @@
import { PatchAsset } from '@asset-sg/shared';
import { AssetEditDetail, PatchAsset } from '@asset-sg/shared';
import { AssetEditPolicy, Role, User } from '@asset-sg/shared/v2';
import { Controller, Get, HttpException, HttpStatus, Param, ParseIntPipe, Post, Put } from '@nestjs/common';
import * as E from 'fp-ts/Either';
import {
Controller,
Delete,
Get,
HttpCode,
HttpException,
HttpStatus,
Param,
ParseIntPipe,
Post,
Put,
} from '@nestjs/common';
import * as O from 'fp-ts/Option';
import { authorize } from '@/core/authorize';
import { CurrentUser } from '@/core/decorators/current-user.decorator';
import { ParseBody } from '@/core/decorators/parse.decorator';
import { AssetEditRepo } from '@/features/asset-edit/asset-edit.repo';
import { AssetEditDetail, AssetEditService } from '@/features/asset-edit/asset-edit.service';
import { AssetSearchService } from '@/features/assets/search/asset-search.service';

@Controller('/asset-edit')
export class AssetEditController {
constructor(private readonly assetEditRepo: AssetEditRepo, private readonly assetEditService: AssetEditService) {}
constructor(private readonly assetEditRepo: AssetEditRepo, private readonly assetSearchService: AssetSearchService) {}

@Get('/:id')
async show(@Param('id', ParseIntPipe) id: number, @CurrentUser() user: User): Promise<unknown> {
Expand All @@ -27,11 +37,10 @@ export class AssetEditController {
async create(@ParseBody(PatchAsset) patch: PatchAsset, @CurrentUser() user: User) {
authorize(AssetEditPolicy, user).canCreate();
validatePatch(user, patch);
const result = await this.assetEditService.createAsset(user, patch)();
if (E.isLeft(result)) {
throw new HttpException(result.left.message, 500);
}
return result.right;

const asset = await this.assetEditRepo.create({ user, patch });
await this.assetSearchService.register(asset);
return AssetEditDetail.encode(asset);
}

@Put('/:id')
Expand All @@ -48,11 +57,27 @@ export class AssetEditController {
authorize(AssetEditPolicy, user).canUpdate(record);
validatePatch(user, patch, record);

const result = await this.assetEditService.updateAsset(user, record.assetId, patch)();
if (E.isLeft(result)) {
throw new HttpException(result.left.message, 500);
const asset = await this.assetEditRepo.update(record.assetId, { user, patch });
if (asset === null) {
throw new HttpException('not found', 404);
}
await this.assetSearchService.register(asset);
return AssetEditDetail.encode(asset);
}

@Delete('/:id')
@HttpCode(HttpStatus.NO_CONTENT)
async delete(@Param('id', ParseIntPipe) id: number, @CurrentUser() user: User): Promise<void> {
const record = await this.assetEditRepo.find(id);
if (record == null) {
throw new HttpException('not found', HttpStatus.NOT_FOUND);
}
authorize(AssetEditPolicy, user).canDelete(record);
const success = await this.assetEditRepo.delete(record.assetId);
if (!success) {
throw new HttpException('could not delete', HttpStatus.INTERNAL_SERVER_ERROR);
}
return result.right;
await this.assetSearchService.deleteFromIndex(record.assetId);
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import { AssetUsage, Contact, PatchAsset, dateIdFromDate } from '@asset-sg/shared';
import { User, WorkgroupId } from '@asset-sg/shared/v2';
import { Role } from '@asset-sg/shared/v2';
import { AssetEditDetail, AssetUsage, Contact, dateIdFromDate, PatchAsset } from '@asset-sg/shared';
import { Role, User, WorkgroupId } from '@asset-sg/shared/v2';
import { fakerDE_CH as faker } from '@faker-js/faker';
import * as O from 'fp-ts/Option';

Expand All @@ -11,8 +10,6 @@ import { fakeAssetKindItemCode } from '../../../../../test/data/asset-kind-item'
// eslint-disable-next-line @nx/enforce-module-boundaries
import { fakeContactKindItem } from '../../../../../test/data/contact-kind-item';

import { AssetEditDetail } from './asset-edit.service';

import { define } from '@/utils/define';

let nextUniqueId = 0;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,12 @@ import { fakeAssetPatch, fakeUser } from './asset-edit.fake';
import { AssetEditRepo } from './asset-edit.repo';

import { PrismaService } from '@/core/prisma.service';
import { FileRepo } from '@/features/files/file.repo';

describe(AssetEditRepo, () => {
const prisma = new PrismaService();
const repo = new AssetEditRepo(prisma);
const fileRepo = new FileRepo(prisma);
const repo = new AssetEditRepo(prisma, fileRepo);

beforeAll(async () => {
await setupDB(prisma);
Expand Down
95 changes: 46 additions & 49 deletions apps/server-asset-sg/src/features/asset-edit/asset-edit.repo.ts
Original file line number Diff line number Diff line change
@@ -1,26 +1,26 @@
import { decodeError, isNotNull } from '@asset-sg/core';
import { AssetUsage, dateFromDateId, DateIdFromDate, PatchAsset } from '@asset-sg/shared';
import { AssetEditDetail, AssetUsage, dateFromDateId, DateIdFromDate, PatchAsset } from '@asset-sg/shared';
import { User } from '@asset-sg/shared/v2';
import { Injectable } from '@nestjs/common';
import { Prisma } from '@prisma/client';
import * as E from 'fp-ts/Either';
import * as O from 'fp-ts/Option';

import { AssetEditDetail } from './asset-edit.service';

import { PrismaService } from '@/core/prisma.service';
import { Repo, RepoListOptions } from '@/core/repo';
import { FileRepo } from '@/features/files/file.repo';
import { AssetEditDetailFromPostgres } from '@/models/asset-edit-detail';
import {
createStudies,
deleteStudies,
postgresStudiesByAssetId,
updateStudies,
} from '@/utils/postgres-studies/postgres-studies';
import { handlePrismaMutationError } from '@/utils/prisma';

@Injectable()
export class AssetEditRepo implements Repo<AssetEditDetail, number, AssetEditData> {
constructor(private readonly prismaService: PrismaService) {}
constructor(private readonly prismaService: PrismaService, private readonly fileRepo: FileRepo) {}

async find(id: number): Promise<AssetEditDetail | null> {
const asset = await this.prismaService.asset.findUnique({
Expand Down Expand Up @@ -256,55 +256,52 @@ export class AssetEditRepo implements Repo<AssetEditDetail, number, AssetEditDat
return false;
}

await this.prismaService.$transaction(async () => {
// Delete the record's `manCatLabelRef` records.
await this.prismaService.manCatLabelRef.deleteMany({
where: { assetId: id },
});

// Delete the record's `assetContact` records.
await this.prismaService.assetContact.deleteMany({
where: { assetId: id },
});

// Delete the record's `assetLanguage` records.
await this.prismaService.assetLanguage.deleteMany({
where: { assetId: id },
});

// Delete the record's `id` records.
await this.prismaService.id.deleteMany({
where: { assetId: id },
});

// Delete the record's `typeNatRel` records.
await this.prismaService.typeNatRel.deleteMany({
where: { assetId: id },
});

// Delete the record's `statusWork` records.
await this.prismaService.statusWork.deleteMany({
where: { assetId: id },
});
try {
await this.prismaService.$transaction(async () => {
// Delete the record's `file` records.
const assetFileIds = await this.prismaService.assetFile.findMany({
where: { assetId: id },
select: { fileId: true },
});

for (const { fileId } of assetFileIds) {
// Placeholder email
await this.fileRepo.delete({ id: fileId, assetId: id, user: { email: '[email protected]' } });
}

// Delete the record.
await this.prismaService.asset.delete({ where: { assetId: id } });

// Delete all `internalUse` records that are not in use anymore.
await this.prismaService.internalUse.deleteMany({
where: {
Asset: { none: {} },
},
});

// Delete the record.
await this.prismaService.asset.delete({ where: { assetId: id } });
// Delete all `publicUse` records that are not in use anymore.
await this.prismaService.publicUse.deleteMany({
where: {
Asset: { none: {} },
},
});

// Delete all `internalUse` records that are not in use anymore.
await this.prismaService.internalUse.deleteMany({
where: {
Asset: { none: {} },
},
});
await this.prismaService.assetFormatItem.deleteMany({
where: {
assets: { none: {} },
},
});

// Delete all `publicUse` records that are not in use anymore.
await this.prismaService.publicUse.deleteMany({
where: {
Asset: { none: {} },
},
await this.prismaService.assetKindItem.deleteMany({
where: {
assets: { none: {} },
},
});
});
});
return true;
return true;
} catch (e) {
return handlePrismaMutationError(e) ?? false;
}
}

private async loadDetail(asset: PrismaAsset): Promise<AssetEditDetail> {
Expand Down
41 changes: 0 additions & 41 deletions apps/server-asset-sg/src/features/asset-edit/asset-edit.service.ts

This file was deleted.

Loading

0 comments on commit df60950

Please sign in to comment.