From adda1a77b3d98a0972d5b65a143cd0e00a44d0c2 Mon Sep 17 00:00:00 2001 From: Rostislav Raykov Date: Sat, 11 Jan 2025 17:09:57 +0200 Subject: [PATCH] Deleting download logs for deleted files --- .../repository/DownloadLogRepository.java | 5 ++++ .../quickdrop/service/FileService.java | 27 ++++++++----------- .../quickdrop/service/ScheduleService.java | 10 ++++++- src/main/resources/templates/dashboard.html | 3 ++- 4 files changed, 27 insertions(+), 18 deletions(-) diff --git a/src/main/java/org/rostislav/quickdrop/repository/DownloadLogRepository.java b/src/main/java/org/rostislav/quickdrop/repository/DownloadLogRepository.java index 9ceaf72..87cd0e4 100644 --- a/src/main/java/org/rostislav/quickdrop/repository/DownloadLogRepository.java +++ b/src/main/java/org/rostislav/quickdrop/repository/DownloadLogRepository.java @@ -2,6 +2,7 @@ package org.rostislav.quickdrop.repository; import org.rostislav.quickdrop.entity.DownloadLog; import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.data.jpa.repository.Modifying; import org.springframework.data.jpa.repository.Query; import java.util.List; @@ -14,4 +15,8 @@ public interface DownloadLogRepository extends JpaRepository long countDownloadsByFileId(String uuid); List findByFileUuid(String fileUUID); + + @Modifying + @Query("DELETE FROM DownloadLog dl WHERE dl.file.id = :id") + void deleteByFileId(Long id); } diff --git a/src/main/java/org/rostislav/quickdrop/service/FileService.java b/src/main/java/org/rostislav/quickdrop/service/FileService.java index fd1d3ab..ae6025b 100644 --- a/src/main/java/org/rostislav/quickdrop/service/FileService.java +++ b/src/main/java/org/rostislav/quickdrop/service/FileService.java @@ -1,6 +1,7 @@ package org.rostislav.quickdrop.service; import jakarta.servlet.http.HttpServletRequest; +import jakarta.transaction.Transactional; import org.rostislav.quickdrop.entity.DownloadLog; import org.rostislav.quickdrop.entity.FileEntity; import org.rostislav.quickdrop.model.FileEntityView; @@ -20,7 +21,10 @@ import org.springframework.stereotype.Service; import org.springframework.web.multipart.MultipartFile; import org.springframework.web.servlet.mvc.method.annotation.StreamingResponseBody; -import java.io.*; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; import java.net.URLEncoder; import java.nio.charset.StandardCharsets; import java.nio.file.Files; @@ -148,6 +152,10 @@ public class FileService { logger.info("File received: {}", file.getName()); String uuid = UUID.randomUUID().toString(); + while (fileRepository.findByUUID(uuid).isPresent()) { + uuid = UUID.randomUUID().toString(); + } + Path targetPath = Path.of(applicationSettingsService.getFileStoragePath(), uuid); FileEntity fileEntity = populateFileEntity(file, fileUploadRequest, uuid); @@ -215,6 +223,7 @@ public class FileService { return true; } + @Transactional public boolean deleteFile(String uuid) { Optional referenceById = fileRepository.findByUUID(uuid); if (referenceById.isEmpty()) { @@ -223,6 +232,7 @@ public class FileService { FileEntity fileEntity = referenceById.get(); fileRepository.delete(fileEntity); + downloadLogRepository.deleteByFileId(fileEntity.id); return deleteFileFromFileSystem(fileEntity.uuid); } @@ -468,21 +478,6 @@ public class FileService { return false; } - private void writeFileToStream(String uuid, OutputStream outputStream) { - Path path = Path.of(applicationSettingsService.getFileStoragePath(), uuid); - try (FileInputStream inputStream = new FileInputStream(path.toFile())) { - byte[] buffer = new byte[1024]; - int bytesRead; - while ((bytesRead = inputStream.read(buffer)) != -1) { - outputStream.write(buffer, 0, bytesRead); - } - outputStream.flush(); - } catch ( - Exception e) { - logger.error("Error writing file to stream: {}", e.getMessage()); - } - } - private void logDownload(FileEntity fileEntity, HttpServletRequest request) { String forwardedFor = request.getHeader("X-Forwarded-For"); String realIp = request.getHeader("X-Real-IP"); diff --git a/src/main/java/org/rostislav/quickdrop/service/ScheduleService.java b/src/main/java/org/rostislav/quickdrop/service/ScheduleService.java index 0e64bbc..c09b544 100644 --- a/src/main/java/org/rostislav/quickdrop/service/ScheduleService.java +++ b/src/main/java/org/rostislav/quickdrop/service/ScheduleService.java @@ -1,6 +1,8 @@ package org.rostislav.quickdrop.service; +import jakarta.transaction.Transactional; import org.rostislav.quickdrop.entity.FileEntity; +import org.rostislav.quickdrop.repository.DownloadLogRepository; import org.rostislav.quickdrop.repository.FileRepository; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -19,13 +21,15 @@ public class ScheduleService { private final FileRepository fileRepository; private final FileService fileService; private final ThreadPoolTaskScheduler taskScheduler = new ThreadPoolTaskScheduler(); + private final DownloadLogRepository downloadLogRepository; private ScheduledFuture scheduledTask; - public ScheduleService(FileRepository fileRepository, FileService fileService) { + public ScheduleService(FileRepository fileRepository, FileService fileService, DownloadLogRepository downloadLogRepository) { this.fileRepository = fileRepository; this.fileService = fileService; taskScheduler.setPoolSize(1); taskScheduler.initialize(); + this.downloadLogRepository = downloadLogRepository; } public void updateSchedule(String cronExpression, long maxFileLifeTime) { @@ -39,6 +43,7 @@ public class ScheduleService { ); } + @Transactional public void deleteOldFiles(long maxFileLifeTime) { logger.info("Deleting old files"); LocalDate thresholdDate = LocalDate.now().minusDays(maxFileLifeTime); @@ -48,6 +53,7 @@ public class ScheduleService { boolean deleted = fileService.deleteFileFromFileSystem(file.uuid); if (deleted) { fileRepository.delete(file); + downloadLogRepository.deleteByFileId(file.id); } else { logger.error("Failed to delete file: {}", file); } @@ -55,12 +61,14 @@ public class ScheduleService { logger.info("Deleted {} files", filesForDeletion.size()); } + @Transactional @Scheduled(cron = "0 0 3 * * *") public void cleanDatabaseFromDeletedFiles() { logger.info("Cleaning database from deleted files"); fileRepository.findAll().forEach(file -> { if (!fileService.fileExistsInFileSystem(file.uuid)) { fileRepository.delete(file); + downloadLogRepository.deleteByFileId(file.id); } }); } diff --git a/src/main/resources/templates/dashboard.html b/src/main/resources/templates/dashboard.html index 1f97672..34f70dd 100644 --- a/src/main/resources/templates/dashboard.html +++ b/src/main/resources/templates/dashboard.html @@ -43,7 +43,8 @@
-
Total Downloads
+
Total Downloads
+ Doesn't count deleted files

0