Поиск по сайту
Ctrl + K
Вопросы по Nest.js

Как реализовать «мягкое» удаление в NestJS с использованием TypeORM и почему «мягкое» удаление может быть предпочтительнее «жесткого»?

Что такое «мягкое» и «жесткое» удаление?

  • Жесткое удаление (hard delete) подразумевает полное удаление записи из базы данных. После выполнения этой операции вы не можете восстановить удаленные данные.
  • Мягкое удаление (soft delete) при этом сохраняет запись в базе данных, но отмечает её как удалённую, например, с помощью флага (колонки), что позволяет скрыть её от обычных запросов. Это обеспечивает возможность восстановления данных.

Как реализовать «мягкое» удаление в NestJS с помощью TypeORM?

Для упрощенной демонстрации давайте создадим простой сервис с использованием Router и TypeORM.

  • Создаем сущность с флагом для «мягкого» удаления:
  • import { Entity, Column, PrimaryGeneratedColumn, CreateDateColumn, UpdateDateColumn } from 'typeorm';
    
    @Entity()
    export class User {
      @PrimaryGeneratedColumn()
      id: number;
    
      @Column()
      name: string;
    
      @Column({ default: false })
      isDeleted: boolean;
    
      @CreateDateColumn()
      createdAt: Date;
    
      @UpdateDateColumn()
      updatedAt: Date;
    }
    
  • Создаем репозиторий и сервис для работы с пользователями:
  • import { Injectable } from '@nestjs/common';
    import { InjectRepository } from '@nestjs/typeorm';
    import { Repository } from 'typeorm';
    import { User } from './user.entity';
    
    @Injectable()
    export class UserService {
      constructor(
        @InjectRepository(User)
        private userRepository: Repository<User>,
      ) {}
    
      async findAll(): Promise<User[]> {
        // Мы выбираем только тех пользователей, которые не удалены
        return this.userRepository.find({ where: { isDeleted: false } });
      }
    
      async softDelete(id: number): Promise<void> {
        // Отметка пользователя как удаленного
        await this.userRepository.update(id, { isDeleted: true });
      }
    
      async restore(id: number): Promise<void> {
        // Восстановление пользователя
        await this.userRepository.update(id, { isDeleted: false });
      }
    }
    
  • Создаем контроллер для обработки запросов:
  • import { Controller, Get, Param, Post, Delete } from '@nestjs/common';
    import { UserService } from './user.service';
    
    @Controller('users')
    export class UserController {
      constructor(private readonly userService: UserService) {}
    
      @Get()
      async findAll() {
        return this.userService.findAll();
      }
    
      @Post('soft-delete/:id')
      async softDelete(@Param('id') id: number) {
        await this.userService.softDelete(id);
      }
    
      @Post('restore/:id')
      async restore(@Param('id') id: number) {
        await this.userService.restore(id);
      }
    }
    

    Почему «мягкое» удаление может быть предпочтительнее?

  • Восстановление данных: Легкость восстановления удаленных данных.
  • Логирование и аудит: Сохранение истории изменений и состояние данных.
  • Отладка: Возможность работы с тестовыми данными без потери содержимого.
  • Безопасность: Устранение риска случайного полного удаления важных данных.
  • Таким образом, мягкое удаление является полезной стратегией, особенно в приложениях, где сохранение целостности данных и возможность восстановления информации имеют критическое значение.