网站内容管理系统 上传word(环境搭建克隆项目通过以下命令即可将项目克隆到本地)
优采云 发布时间: 2022-04-01 10:26网站内容管理系统 上传word(环境搭建克隆项目通过以下命令即可将项目克隆到本地)
昨晚搭建环境花了很长时间,主要浪费在安装openoffice的依赖环境上(Mac需要手动安装)。
然后,我做了一步一步的功能演示,记录、调试了项目,并在写这篇文章之前简要研究了核心代码。因此,在本篇文章中我也会简单分析一下项目的核心代码。
项目介绍
kkFileView官方介绍如下:
kkFileView是一个使用spring boot创建文件文档在线预览的项目解决方案,支持doc、docx、ppt、pptx、xls、xlsx、zip、rar、mp4、mp3以及txt、html、 xml、java、properties、sql、js、md、json、conf、ini、vue、php、py、bat、gitignore等文件在线预览
简单来说,kkFileView 是针对常见文件类型的在线预览解决方案。
总的来说,我认为kkFileView是一个很棒的开源项目,在线文件预览的需求非常普遍。感谢开源!
下面,我将从一个“上帝”的角度,从多个维度评价kkFileView:
代码质量一般,有很多地方可以优化。比如controller层代码嵌套太多逻辑没有全局异常处理(错误信息的json数据在代码中直接返回到前端,我不推荐)返回值不需要转换成JSON格式通过ObjectMapper(ResponseEntity+@RestController就可以了)...有很多公司在用,说明项目整体功能比较稳定成熟!代码的整体逻辑比较清晰易懂。给作者竖起大拇指!环境搭建克隆项目
可以使用以下命令将项目克隆到本地:
git clone https://gitee.com/kekingcn/file-online-preview.git
安装 OpenOffice
办公类文件的预览依赖于OpenOffice,所以我们首先要安装OpenOffice(Windows下是内置的,Linux下会自动安装,Mac OS下需要手动安装)。
下面演示如何在 Mac 上安装 OpenOffice。
您可以使用以下命令安装最新版本的 OpenOffice:
brew cask install openoffice
不过这种方法可能下载比较慢,可以直接去官网下载dmg安装包。
官方下载地址:
很多朋友会问:什么是OpenOffice?
OpenOffice是Apache下的一款开源免费文字处理软件,支持Windows、Linux、OS X等主流操作系统。
OpenOffice有点类似于Windows下的办公软件,但实际上是开源免费的。
启动项目
运行 FilePreviewApplication 的 main 方法。服务启动后,访问:8012/,会看到如下界面,表示服务启动成功。
采用
我们首先上传了 3 种不同类型的文件来分别演示图片、PDF 和 Word 文档的预览。
图像预览
kkFileView支持jpg、jpeg、png、gif等格式图片的预览,还包括图片的翻转、缩放等操作。
图片预览如下。
Word 文档的预览
kkFileView 支持 doc、docx 文档预览。
另外,根据Word大小和网速,Word预览提供两种模式:
两种模式的适用场景如下
图片预览模式的预览效果如下:
PDF预览模式的预览效果如下:
PDF 文件预览
kkFileView 支持 PDF 文档预览。与 Word 文档预览类似,PDF 预览提供两种模式:
由于预览显示效果和Word文档一样,这里就不放图片了。
文件预览 核心代码分析 API 层
文件预览调用的接口是/onlinePreview。
通过分析 /onlinePreview 接口,我们发现后端收到预览请求后,会从 URL 和请求中过滤掉它需要的信息,例如文件后缀和文件名。
然后调用 FilePreview 类的 filePreviewHandle() 方法。filePreviewHandle() 方法是实现文件预览的核心方法。
@RequestMapping(value = "/onlinePreview")
public String onlinePreview(String url, Model model, HttpServletRequest req) {
FileAttribute fileAttribute = fileUtils.getFileAttribute(url);
req.setAttribute("fileKey", req.getParameter("fileKey"));
model.addAttribute("pdfDownloadDisable", ConfigConstants.getPdfDownloadDisable());
model.addAttribute("officePreviewType", req.getParameter("officePreviewType"));
FilePreview filePreview = previewFactory.get(fileAttribute);
logger.info("预览文件url:{},previewType:{}", url, fileAttribute.getType());
return filePreview.filePreviewHandle(url, model, fileAttribute);
}
FilePreview 是一个文件预览界面。不同文件类型的预览实现了FilePreview接口和filePreviewHandle()方法。
文件预览界面
public interface FilePreview {
String filePreviewHandle(String url, Model model, FileAttribute fileAttribute);
}
不同文件类型的预览实现了FilePreview接口,如下图所示。
不同文件类型的预览会实现 FilePreview 接口,然后重写 filePreviewHandle() 方法。例如:OfficeFilePreviewImpl主要负责处理office文件的预览,PdfFilePreviewImpl主要负责处理pdf文件的预览。
文件预览具体实现分析
下面我们以office文件的预览为入口进行分析。
首先要明确的是,excel类型的预览是通过将excel文件转成HTML实现的,其他类型office文件的预览是通过将文件转成PDF或者图片来实现的。
例如。如果我们上传一个名为“武汉文化市场*敏*感*词*.docx”的Word文件并预览,会在jodconverter-web/src/main/file路径下生成两个相关文件。这两个文件对应我们提到的。PDF预览和图片预览有两种方式。
我们以一个名为《武汉文化市场*敏*感*词*.docx》的文件为例,说明在代码中是如何做到的。
通过分析代码,我们找到了OfficeFilePreviewImpl,它主要负责处理office文件的预览。
/**
* 处理office文件
*/
@Service
public class OfficeFilePreviewImpl implements FilePreview {
}
下面简单分析一下OfficeFilePreviewImpl类中实现预览的核心方法是filePreviewHandle。
注意:这部分代码逻辑不够清晰,可以优化方法使其更易阅读。有兴趣的朋友可以自行重构,然后提交PR给作者。
@Override
public String filePreviewHandle(String url, Model model, FileAttribute fileAttribute) {
// 1.获取预览类型(image/pdf/html),用户请求中传了officePreviewType参数就取参数的,没传取系统默认(image)
String officePreviewType = model.asMap().get("officePreviewType") == null ? ConfigConstants.getOfficePreviewType() : model.asMap().get("officePreviewType").toString();
// 2.获取 URL 地址
String baseUrl = BaseUrlFilter.getBaseUrl();// http://localhost:8012/
// 3.获取图片相关信息
String suffix=fileAttribute.getSuffix();//文件后缀如docx
String fileName=fileAttribute.getName();//文件名如:武汉市文化市场*敏*感*词*.docx
// 4. 判断是否为 html 格式预览也就是判断文件否为 excel
boolean isHtml = suffix.equalsIgnoreCase("xls") || suffix.equalsIgnoreCase("xlsx");
// 5. 将文件的后缀名更换为 .pdf 或者 .html(excel文件的情况)
String pdfName = fileName.substring(0, fileName.lastIndexOf(".") + 1) + (isHtml ? "html" : "pdf");
// 6. 转换后的文件输出的文件夹如 file-online-preview/jodconverter-web/src/main/file/武汉市文化市场*敏*感*词*.pdf)
String outFilePath = FILE_DIR + pdfName;
// 7 .判断之前是否已转换过,如果转换过,直接返回,否则执行转换
// 文件第一次被预览的时候会首先对文件进行缓存处理
if (!fileUtils.listConvertedFiles().containsKey(pdfName) || !ConfigConstants.isCacheEnabled()) {
String filePath;
// 下载文件
ReturnResponse response = downloadUtils.downLoad(fileAttribute, null);
if (0 != response.getCode()) {
model.addAttribute("fileType", suffix);
model.addAttribute("msg", response.getMsg());
return "fileNotSupported";
}
filePath = response.getContent();
if (StringUtils.hasText(outFilePath)) {
officeToPdf.openOfficeToPDF(filePath, outFilePath);
if (isHtml) {
// 对转换后的文件进行操作(改变编码方式)
fileUtils.doActionConvertedFile(outFilePath);
}
if (ConfigConstants.isCacheEnabled()) {
// 加入缓存
fileUtils.addConvertedFile(pdfName, fileUtils.getRelativePath(outFilePath));
}
}
}
// 8.根据预览类型officePreviewType,选择不同的预览方式
// 比如,如果预览类型officePreviewType为pdf则进行pdf方式预览
if (!isHtml && baseUrl != null && (OFFICE_PREVIEW_TYPE_IMAGE.equals(officePreviewType) || OFFICE_PREVIEW_TYPE_ALL_IMAGES.equals(officePreviewType))) {
return getPreviewType(model, fileAttribute, officePreviewType, baseUrl, pdfName, outFilePath, pdfUtils, OFFICE_PREVIEW_TYPE_IMAGE);
}
model.addAttribute("pdfUrl", pdfName);
return isHtml ? "html" : "pdf";
}
项目地址: