feat(trash): 优化回收站物品恢复和永久删除逻辑

- 在 GroupingMapper 和 MarkdownFileMapper 中添加物理删除和恢复的 SQL 操作
- 优化 HomePage组件中的删除操作,删除后刷新分组树并回到主视图
- 在 TrashServiceImpl 中实现物品恢复和永久删除的业务逻辑- 为 TrashItemVo 中的 deletedAt 字段添加 JSON 格式化注解
This commit is contained in:
ikmkj
2025-08-01 00:14:34 +08:00
parent c448ababa9
commit b0a714df83
6 changed files with 38 additions and 28 deletions

View File

@@ -1,5 +1,6 @@
package com.test.bijihoudaun.entity; package com.test.bijihoudaun.entity;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.v3.oas.annotations.media.Schema; import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data; import lombok.Data;
@@ -19,6 +20,7 @@ public class TrashItemVo {
private String type; private String type;
@Schema(description = "删除时间") @Schema(description = "删除时间")
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
private Date deletedAt; private Date deletedAt;
@Schema(description = "删除者ID") @Schema(description = "删除者ID")

View File

@@ -2,8 +2,13 @@ package com.test.bijihoudaun.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper; import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.test.bijihoudaun.entity.Grouping; import com.test.bijihoudaun.entity.Grouping;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Mapper; import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select; import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update;
import java.util.List; import java.util.List;
@@ -12,4 +17,10 @@ public interface GroupingMapper extends BaseMapper<Grouping> {
@Select("SELECT * FROM grouping WHERE is_deleted = 1") @Select("SELECT * FROM grouping WHERE is_deleted = 1")
List<Grouping> selectDeleted(); List<Grouping> selectDeleted();
@Delete("DELETE FROM grouping WHERE id = #{id}")
void physicalDeleteById(@Param("id") Long id);
@Update("UPDATE grouping SET is_deleted = 0, deleted_at = NULL, deleted_by = NULL WHERE id = #{id}")
void restoreById(@Param("id") Long id);
} }

View File

@@ -9,6 +9,9 @@ import org.apache.ibatis.annotations.Select;
import java.util.List; import java.util.List;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Update;
@Mapper @Mapper
public interface MarkdownFileMapper extends BaseMapper<MarkdownFile> { public interface MarkdownFileMapper extends BaseMapper<MarkdownFile> {
@@ -29,4 +32,13 @@ public interface MarkdownFileMapper extends BaseMapper<MarkdownFile> {
@Select("SELECT * FROM markdown_file WHERE is_deleted = 1") @Select("SELECT * FROM markdown_file WHERE is_deleted = 1")
List<MarkdownFile> selectDeleted(); List<MarkdownFile> selectDeleted();
@Delete("DELETE FROM markdown_file WHERE id = #{id}")
void physicalDeleteById(@Param("id") Long id);
@Delete("DELETE FROM markdown_file WHERE grouping_id = #{groupingId}")
void physicalDeleteByGroupingId(@Param("groupingId") Long groupingId);
@Update("UPDATE markdown_file SET is_deleted = 0, deleted_at = NULL, deleted_by = NULL WHERE id = #{id}")
void restoreById(@Param("id") Long id);
} }

View File

@@ -1,6 +1,7 @@
package com.test.bijihoudaun.service.impl; package com.test.bijihoudaun.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.test.bijihoudaun.entity.Grouping; import com.test.bijihoudaun.entity.Grouping;
import com.test.bijihoudaun.entity.MarkdownFile; import com.test.bijihoudaun.entity.MarkdownFile;
import com.test.bijihoudaun.entity.TrashItemVo; import com.test.bijihoudaun.entity.TrashItemVo;
@@ -62,19 +63,9 @@ public class TrashServiceImpl implements TrashService {
@Transactional @Transactional
public void restoreItem(String id, String type) { public void restoreItem(String id, String type) {
if ("note".equals(type)) { if ("note".equals(type)) {
MarkdownFile file = new MarkdownFile(); markdownFileMapper.restoreById(Long.parseLong(id));
file.setId(Long.parseLong(id));
file.setIsDeleted(0);
file.setDeletedAt(null);
file.setDeletedBy(null);
markdownFileMapper.updateById(file);
} else if ("group".equals(type)) { } else if ("group".equals(type)) {
Grouping group = new Grouping(); groupingMapper.restoreById(Long.parseLong(id));
group.setId(Long.parseLong(id));
group.setIsDeleted(0);
group.setDeletedAt(null);
group.setDeletedBy(null);
groupingMapper.updateById(group);
} }
} }
@@ -82,11 +73,11 @@ public class TrashServiceImpl implements TrashService {
@Transactional @Transactional
public void permanentlyDeleteItem(String id, String type) { public void permanentlyDeleteItem(String id, String type) {
if ("note".equals(type)) { if ("note".equals(type)) {
markdownFileMapper.deleteById(Long.parseLong(id)); markdownFileMapper.physicalDeleteById(Long.parseLong(id));
} else if ("group".equals(type)) { } else if ("group".equals(type)) {
// 删除分组时,也删除其下的所有笔记 // 永久删除分组时,也永久删除其下的所有笔记
groupingMapper.deleteById(Long.parseLong(id)); groupingMapper.physicalDeleteById(Long.parseLong(id));
markdownFileMapper.delete(new QueryWrapper<MarkdownFile>().eq("grouping_id", id)); markdownFileMapper.physicalDeleteByGroupingId(Long.parseLong(id));
} }
} }

View File

@@ -639,12 +639,9 @@ const handleDeleteGroup = (group) => {
try { try {
await apiDeleteGrouping(group.id); await apiDeleteGrouping(group.id);
ElMessage.success('分类已删除'); ElMessage.success('分类已删除');
// 删除分类后,刷新分组树并回到主视图
await fetchGroupings(); await fetchGroupings();
await fetchMarkdownFiles(); await resetToHomeView();
if (activeMenu.value.startsWith('group-') && activeMenu.value.endsWith(group.id)) {
activeMenu.value = 'all';
groupMarkdownFiles.value = markdownFiles.value;
}
} catch (error) { } catch (error) {
ElMessage.error('删除分类失败: ' + error.message); ElMessage.error('删除分类失败: ' + error.message);
} }
@@ -666,13 +663,10 @@ const deleteNote = (file) => {
try { try {
await deleteMarkdown(file.id); await deleteMarkdown(file.id);
ElMessage.success('笔记已删除'); ElMessage.success('笔记已删除');
selectedFile.value = null; selectedFile.value = null; // 关闭预览
await fetchMarkdownFiles(); // 刷新分组和主视图
// Optionally, refresh the current group's file list await fetchGroupings();
if (activeMenu.value.startsWith('group-')) { await resetToHomeView();
const groupId = activeMenu.value.split('-');
await selectFile({ id: groupId });
}
} catch (error) { } catch (error) {
ElMessage.error('删除笔记失败: ' + error.message); ElMessage.error('删除笔记失败: ' + error.message);
} }

Binary file not shown.