1
0
mirror of https://gitee.com/bookshelfplus/bookshelfplus synced 2025-09-01 22:53:29 +08:00
Code Issues Projects Releases Wiki Activity GitHub Gitee

导出系统数据初步完成(可以输出到控制台)

This commit is contained in:
2022-04-18 23:08:08 +08:00
parent 883a245058
commit 93c499cb6e
3 changed files with 288 additions and 0 deletions

View File

@@ -0,0 +1,273 @@
package plus.bookshelf.Controller.Controller;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.Data;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import plus.bookshelf.Common.Error.BusinessException;
import plus.bookshelf.Common.Response.CommonReturnType;
import plus.bookshelf.Dao.DO.BookDO;
import plus.bookshelf.Dao.DO.CategoryDO;
import plus.bookshelf.Dao.DO.FileDO;
import plus.bookshelf.Dao.DO.FileObjectDO;
import plus.bookshelf.Dao.Mapper.BookDOMapper;
import plus.bookshelf.Dao.Mapper.CategoryDOMapper;
import plus.bookshelf.Dao.Mapper.FileDOMapper;
import plus.bookshelf.Dao.Mapper.FileObjectDOMapper;
import plus.bookshelf.Service.Impl.UserServiceImpl;
import plus.bookshelf.Service.Model.UserModel;
import java.util.ArrayList;
import java.util.List;
@Api(tags = "导出数据")
@Controller("export")
@RequestMapping("/export")
public class ExportController extends BaseController {
@Autowired
UserServiceImpl userService;
@Autowired
CategoryDOMapper categoryDOMapper;
@Data
private class CategoryNode {
public CategoryDO current;
public List<BookNode> children;
public List<CategoryNode> subCategory;
public CategoryNode(CategoryDO current) {
this.current = current;
this.children = new ArrayList<>();
this.subCategory = new ArrayList<>();
}
}
private List<CategoryNode> convertToCategoryNode(CategoryDO[] categoryDOList) {
List<CategoryNode> categoryNodeList = new ArrayList<>();
for (CategoryDO categoryDO : categoryDOList) {
CategoryNode categoryNode = new CategoryNode(categoryDO);
categoryNodeList.add(categoryNode);
}
return categoryNodeList;
}
@Autowired
BookDOMapper bookDOMapper;
@Data
private class BookNode {
public BookDO current;
public List<FileNode> children;
public BookNode(BookDO current) {
this.current = current;
this.children = new ArrayList<>();
}
}
private List<BookNode> convertToBookNode(BookDO[] bookDOList) {
List<BookNode> bookNodeList = new ArrayList<>();
for (BookDO bookDO : bookDOList) {
BookNode bookNode = new BookNode(bookDO);
bookNodeList.add(bookNode);
}
return bookNodeList;
}
@Autowired
FileDOMapper fileDOMapper;
@Data
private class FileNode {
public FileDO current;
public List<FileObjectNode> children;
public FileNode(FileDO current) {
this.current = current;
this.children = new ArrayList<>();
}
}
private List<FileNode> convertToFileNode(FileDO[] fileDOList) {
List<FileNode> fileNodeList = new ArrayList<>();
for (FileDO fileDO : fileDOList) {
FileNode fileNode = new FileNode(fileDO);
fileNodeList.add(fileNode);
}
return fileNodeList;
}
@Autowired
FileObjectDOMapper fileObjectDOMapper;
@Data
private class FileObjectNode {
public FileObjectDO current;
public FileObjectNode(FileObjectDO current) {
this.current = current;
}
}
private List<FileObjectNode> convertToFileObjectNode(FileObjectDO[] fileObjectDOList) {
List<FileObjectNode> fileObjectNodeList = new ArrayList<>();
for (FileObjectDO fileObjectDO : fileObjectDOList) {
FileObjectNode fileObjectNode = new FileObjectNode(fileObjectDO);
fileObjectNodeList.add(fileObjectNode);
}
return fileObjectNodeList;
}
/**
* 导出为 Markdown
*
* @param token 用户 token
* @return
* @throws BusinessException
*/
@ApiOperation(value = "【管理员】导出系统数据", notes = "将系统中的所有数据导出为markdown")
@RequestMapping(value = "markdown", method = {RequestMethod.POST}, consumes = {CONTENT_TYPE_FORMED})
@ResponseBody
public CommonReturnType deleteBook(@RequestParam(value = "token", required = false) String token) throws BusinessException {
// 查询出系统中所有的分类、书籍、文件、文件对象数据
CategoryDO[] allCategorys = categoryDOMapper.selectAll();
BookDO[] allBooks = bookDOMapper.selectAll();
FileDO[] allFiles = fileDOMapper.selectAll();
FileObjectDO[] allFileObjects = fileObjectDOMapper.selectAll();
// 转换为 Node 对象,并保存在列表中,便于接下来的遍历
List<CategoryNode> categoryNodeList = convertToCategoryNode(allCategorys);
List<BookNode> bookNodeList = convertToBookNode(allBooks);
List<FileNode> fileNodeList = convertToFileNode(allFiles);
List<FileObjectNode> fileObjectNodeList = convertToFileObjectNode(allFileObjects);
// 基本思路:
// 先不管分类的层级,将 文件对象挂到文件下,文件挂到书籍下,书籍挂到分类下
// 然后在形成分类的层级结构
// 将文件对象挂到文件上去
for (FileObjectNode fileObjectNode : fileObjectNodeList) {
for (FileNode fileNode : fileNodeList) {
if (fileObjectNode.current.getFileId().equals(fileNode.current.getId())) {
fileNode.children.add(fileObjectNode);
break;
}
}
}
// 将文件挂到书籍上去
for (FileNode fileNode : fileNodeList) {
for (BookNode bookNode : bookNodeList) {
if (fileNode.current.getBookId().equals(bookNode.current.getId())) {
bookNode.children.add(fileNode);
}
}
}
// 将书籍挂到分类上去
for (BookNode bookNode : bookNodeList) {
for (CategoryNode categoryNode : categoryNodeList) {
if (bookNode.current.getCategoryId().equals(categoryNode.current.getId())) {
categoryNode.children.add(bookNode);
}
}
}
// 创建一个 Category 父分类,用于保存所有的一级分类
// 思路:每遍历到一个节点,就将其保存在 rootCategoryNodeList 中
List<CategoryNode> rootCategoryNodeList = new ArrayList<>();
// 再创建一个虚拟的顶级分类,用于保存所有的一级分类
CategoryNode rootCategoryNode = new CategoryNode(new CategoryDO());
rootCategoryNode.subCategory = categoryNodeList;
// 分类形成树状结构
for (CategoryNode categoryNode : categoryNodeList) {
for (CategoryNode parentCategoryNode : categoryNodeList) {
if (categoryNode.current.getParentId().equals(parentCategoryNode.current.getId())) {
parentCategoryNode.subCategory.add(categoryNode);
// 将子节点从 rootCategoryNodeList 中移除
if (rootCategoryNodeList.contains(categoryNode)) {
rootCategoryNodeList.remove(categoryNode);
}
// 将父节点添加到 rootCategoryNodeList 中
if (!rootCategoryNodeList.contains(parentCategoryNode)) {
rootCategoryNodeList.add(parentCategoryNode);
}
}
}
}
// 打印出这个复杂的树状结构
traverseCategory(rootCategoryNode, 1);
StringBuilder markdown = new StringBuilder();
// 形成 markdown 格式的文件
// 添加 markdown 头部以及尾部
// 返回 markdown 文件
return CommonReturnType.create(null);
}
// 递归打印出分类树状结构
private void traverseCategory(CategoryNode parentCategoryNode, Integer level) {
// 如果这个分类为空,则直接返回
if (parentCategoryNode == null) {
return;
}
// 如果这个分类下有书籍,则遍历打印书籍信息
traverseBook(parentCategoryNode, level);
// 遍历父级分类的孩子们
for (CategoryNode categoryNode : parentCategoryNode.subCategory) {
// 打印出当前子分类的名称
System.out.println(getSpace(level - 1) + "[" + level + "级分类] \t" + categoryNode.current.getName());
// 如果当前子分类还有子分类,则递归他
traverseCategory(categoryNode, level + 1);
}
}
// 递归打印出一本书的书籍信息
private void traverseBook(CategoryNode categoryNode, Integer level) {
// 如果这个分类为空,则直接返回
if (categoryNode == null) {
return;
}
List<BookNode> bookNodeList = categoryNode.children;
// 遍历打印出书籍信息
for (BookNode bookNode : bookNodeList) {
// 打印出当前书籍的名称
System.out.println(getSpace(level - 1) + "\t[书籍] " + bookNode.current.getId() + "\t" + bookNode.current.getBookName());
for (FileNode fileNode : bookNode.children) {
// 打印出当前书籍的文件信息
System.out.println(getSpace(level - 1) + "\t\t[文件] " + fileNode.current.getId() + "\t" + fileNode.current.getFileName());
for (FileObjectNode fileObjectNode : fileNode.children) {
// 打印出当前书籍的文件对象信息
System.out.println(getSpace(level - 1) + "\t\t\t[文件对象] " + fileObjectNode.current.getId() + "\t" + fileObjectNode.current.getFileName());
}
}
}
}
public String getSpace(Integer count) {
StringBuilder space = new StringBuilder();
for (int i = 0; i < count; i++) {
space.append("\t");
}
return space.toString();
}
}

View File

@@ -82,8 +82,16 @@ public interface BookDOMapper {
/**
* 通过用户id获取用户收藏书籍列表
*
* @param userId
* @return
*/
BookDO[] selectFavoritesListByUserId(Integer userId);
/**
* 查询所有书籍
*
* @return
*/
BookDO[] selectAll();
}