Compare commits

...

5 Commits

Author SHA1 Message Date
kl
6e8bf0d359 更新index接入演示界面UI风格 2020-12-28 13:36:08 +08:00
kl
986f562266 引入galimatias,解决不规范文件名导致文件下载异常 2020-12-28 11:43:27 +08:00
kl
11d0441ed4 加回漏掉的pdfjs 2020-12-28 11:22:59 +08:00
kl
ef46e2c51e 增强url base64解码失败时的提示信息 2020-12-28 11:22:59 +08:00
kl
0a3c03f18b 修复发行包运行时找不到日志目录的问题 2020-12-28 11:22:59 +08:00
11 changed files with 83525 additions and 129 deletions

2
.gitignore vendored
View File

@@ -17,7 +17,6 @@ target/
### NetBeans ### ### NetBeans ###
nbproject/private/ nbproject/private/
build/
nbbuild/ nbbuild/
dist/ dist/
nbdist/ nbdist/
@@ -29,4 +28,3 @@ nbdist/
server/src/main/cache/ server/src/main/cache/
server/src/main/file/ server/src/main/file/
server/src/main/log

View File

@@ -201,6 +201,12 @@
<scope>system</scope> <scope>system</scope>
<systemPath>${basedir}/lib/cpdetector-1.04.jar</systemPath> <systemPath>${basedir}/lib/cpdetector-1.04.jar</systemPath>
</dependency> </dependency>
<!-- url 规范化 -->
<dependency>
<groupId>io.mola.galimatias</groupId>
<artifactId>galimatias</artifactId>
<version>0.2.1</version>
</dependency>
</dependencies> </dependencies>
<build> <build>
<resources> <resources>

View File

@@ -15,7 +15,7 @@ public class OtherFilePreviewImpl implements FilePreview {
@Override @Override
public String filePreviewHandle(String url, Model model, FileAttribute fileAttribute) { public String filePreviewHandle(String url, Model model, FileAttribute fileAttribute) {
return this.notSupportedFile(model,fileAttribute,"系统还不支持该格式文件的在线预览"); return this.notSupportedFile(model, fileAttribute, "系统还不支持该格式文件的在线预览");
} }
/** /**
@@ -24,8 +24,28 @@ public class OtherFilePreviewImpl implements FilePreview {
* @return 页面 * @return 页面
*/ */
public String notSupportedFile(Model model, FileAttribute fileAttribute, String errMsg) { public String notSupportedFile(Model model, FileAttribute fileAttribute, String errMsg) {
model.addAttribute("fileType", fileAttribute.getSuffix()); return this.notSupportedFile(model, fileAttribute.getSuffix(), errMsg);
}
/**
* 通用的预览失败,导向到不支持的文件响应页面
*
* @return 页面
*/
public String notSupportedFile(Model model, String errMsg) {
return this.notSupportedFile(model, "未知", errMsg);
}
/**
* 通用的预览失败,导向到不支持的文件响应页面
*
* @return 页面
*/
public String notSupportedFile(Model model, String fileType, String errMsg) {
model.addAttribute("fileType", fileType);
model.addAttribute("msg", errMsg); model.addAttribute("msg", errMsg);
return NOT_SUPPORTED_FILE_PAGE; return NOT_SUPPORTED_FILE_PAGE;
} }
} }

View File

@@ -4,6 +4,7 @@ import cn.keking.config.ConfigConstants;
import cn.keking.model.FileAttribute; import cn.keking.model.FileAttribute;
import cn.keking.model.FileType; import cn.keking.model.FileType;
import cn.keking.model.ReturnResponse; import cn.keking.model.ReturnResponse;
import io.mola.galimatias.GalimatiasParseException;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
@@ -81,7 +82,6 @@ public class DownloadUtils {
public static byte[] getBytesFromUrl(String urlStr) throws IOException { public static byte[] getBytesFromUrl(String urlStr) throws IOException {
InputStream is = getInputStreamFromUrl(urlStr); InputStream is = getInputStreamFromUrl(urlStr);
if (is == null) { if (is == null) {
// urlStr = URLUtil.normalize(urlStr, true, true);
is = getInputStreamFromUrl(urlStr); is = getInputStreamFromUrl(urlStr);
if (is == null) { if (is == null) {
logger.error("文件下载异常url{}", urlStr); logger.error("文件下载异常url{}", urlStr);
@@ -98,13 +98,14 @@ public class DownloadUtils {
private static InputStream getInputStreamFromUrl(String urlStr) { private static InputStream getInputStreamFromUrl(String urlStr) {
try { try {
URL url = new URL(urlStr);
URL url = io.mola.galimatias.URL.parse(urlStr).toJavaURL();
URLConnection connection = url.openConnection(); URLConnection connection = url.openConnection();
if (connection instanceof HttpURLConnection) { if (connection instanceof HttpURLConnection) {
connection.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)"); connection.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");
} }
return connection.getInputStream(); return connection.getInputStream();
} catch (IOException e) { } catch (IOException | GalimatiasParseException e) {
logger.warn("连接url异常url{}", urlStr); logger.warn("连接url异常url{}", urlStr);
return null; return null;
} }

View File

@@ -5,6 +5,7 @@ import cn.keking.service.FilePreview;
import cn.keking.service.FilePreviewFactory; import cn.keking.service.FilePreviewFactory;
import cn.keking.service.cache.CacheService; import cn.keking.service.cache.CacheService;
import cn.keking.service.impl.OtherFilePreviewImpl;
import cn.keking.utils.DownloadUtils; import cn.keking.utils.DownloadUtils;
import cn.keking.service.FileHandlerService; import cn.keking.service.FileHandlerService;
import org.slf4j.Logger; import org.slf4j.Logger;
@@ -31,21 +32,30 @@ import static cn.keking.service.FilePreview.PICTURE_FILE_PREVIEW_PAGE;
@Controller @Controller
public class OnlinePreviewController { public class OnlinePreviewController {
public static final String BASE64_DECODE_ERROR_MSG = "Base64解码失败请检查你的 %s 是否采用 Base64 + urlEncode 双重编码了!";
private final Logger logger = LoggerFactory.getLogger(OnlinePreviewController.class); private final Logger logger = LoggerFactory.getLogger(OnlinePreviewController.class);
private final FilePreviewFactory previewFactory; private final FilePreviewFactory previewFactory;
private final CacheService cacheService; private final CacheService cacheService;
private final FileHandlerService fileHandlerService; private final FileHandlerService fileHandlerService;
private final OtherFilePreviewImpl otherFilePreview;
public OnlinePreviewController(FilePreviewFactory filePreviewFactory, FileHandlerService fileHandlerService, CacheService cacheService) { public OnlinePreviewController(FilePreviewFactory filePreviewFactory, FileHandlerService fileHandlerService, CacheService cacheService, OtherFilePreviewImpl otherFilePreview) {
this.previewFactory = filePreviewFactory; this.previewFactory = filePreviewFactory;
this.fileHandlerService = fileHandlerService; this.fileHandlerService = fileHandlerService;
this.cacheService = cacheService; this.cacheService = cacheService;
this.otherFilePreview = otherFilePreview;
} }
@RequestMapping(value = "/onlinePreview") @RequestMapping(value = "/onlinePreview")
public String onlinePreview(String url, Model model, HttpServletRequest req) { public String onlinePreview(String url, Model model, HttpServletRequest req) {
String fileUrl = new String(Base64Utils.decodeFromString(url)); String fileUrl;
try {
fileUrl = new String(Base64Utils.decodeFromString(url));
} catch (Exception ex) {
String errorMsg = String.format(BASE64_DECODE_ERROR_MSG, "url");
return otherFilePreview.notSupportedFile(model, errorMsg);
}
FileAttribute fileAttribute = fileHandlerService.getFileAttribute(fileUrl, req); FileAttribute fileAttribute = fileHandlerService.getFileAttribute(fileUrl, req);
FilePreview filePreview = previewFactory.get(fileAttribute); FilePreview filePreview = previewFactory.get(fileAttribute);
logger.info("预览文件url{}previewType{}", fileUrl, fileAttribute.getType()); logger.info("预览文件url{}previewType{}", fileUrl, fileAttribute.getType());
@@ -54,18 +64,24 @@ public class OnlinePreviewController {
@RequestMapping(value = "/picturesPreview") @RequestMapping(value = "/picturesPreview")
public String picturesPreview(String urls, Model model, HttpServletRequest req) throws UnsupportedEncodingException { public String picturesPreview(String urls, Model model, HttpServletRequest req) throws UnsupportedEncodingException {
String fileUrls = new String(Base64Utils.decodeFromString(urls)); String fileUrls;
try {
fileUrls = new String(Base64Utils.decodeFromString(urls));
} catch (Exception ex) {
String errorMsg = String.format(BASE64_DECODE_ERROR_MSG, "urls");
return otherFilePreview.notSupportedFile(model, errorMsg);
}
logger.info("预览文件url{}urls{}", fileUrls, urls); logger.info("预览文件url{}urls{}", fileUrls, urls);
// 抽取文件并返回文件列表 // 抽取文件并返回文件列表
String[] imgs = fileUrls.split("\\|"); String[] images = fileUrls.split("\\|");
List<String> imgUrls = Arrays.asList(imgs); List<String> imgUrls = Arrays.asList(images);
model.addAttribute("imgUrls", imgUrls); model.addAttribute("imgUrls", imgUrls);
String currentUrl = req.getParameter("currentUrl"); String currentUrl = req.getParameter("currentUrl");
if(StringUtils.hasText(currentUrl)){ if (StringUtils.hasText(currentUrl)) {
String decodedCurrentUrl = new String(Base64Utils.decodeFromString(currentUrl)); String decodedCurrentUrl = new String(Base64Utils.decodeFromString(currentUrl));
model.addAttribute("currentUrl", decodedCurrentUrl); model.addAttribute("currentUrl", decodedCurrentUrl);
}else { } else {
model.addAttribute("currentUrl", imgUrls.get(0)); model.addAttribute("currentUrl", imgUrls.get(0));
} }
return PICTURE_FILE_PREVIEW_PAGE; return PICTURE_FILE_PREVIEW_PAGE;

View File

@@ -0,0 +1,7 @@
README.txt
log目录是用来存放kkFileView.log的预览服务的运行情况最终都会反映到这个日志文件里
可以提供给开发运维排查系统问题如果通过kkFileView.log还无法定位问题所在请你在寻求
kk官方支持时QQ群一 613025121QQ群二 484680571将此日志文件一并携带并按照这个
格式重命名日志文件 kkFileView-QQ昵称-时间日期.logkkFileView-kl博主-2020-12-27.log
所有收集的日志文件我们都会存档供所有的kk用户作为排查案例使用所以在你提供日志前
先自行处理日志文件里的业务敏感内容

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -2,54 +2,52 @@
<html lang="en"> <html lang="en">
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, user-scalable=yes, initial-scale=1.0" /> <meta name="viewport" content="width=device-width, user-scalable=yes, initial-scale=1.0"/>
<title>kkFileView演示首页</title> <title>kkFileView演示首页</title>
<link rel="stylesheet" href="css/viewer.min.css" /> <link rel="stylesheet" href="css/viewer.min.css"/>
<link rel="stylesheet" href="css/loading.css" /> <link rel="stylesheet" href="css/loading.css"/>
<link rel="stylesheet" href="bootstrap/css/bootstrap.min.css" /> <link rel="stylesheet" href="bootstrap/css/bootstrap.min.css"/>
<link rel="stylesheet" href="bootstrap-table/bootstrap-table.min.css" /> <link rel="stylesheet" href="bootstrap-table/bootstrap-table.min.css"/>
<link rel="stylesheet" href="gitalk/gitalk.css" /> <link rel="stylesheet" href="gitalk/gitalk.css"/>
<script type="text/javascript" src="js/jquery-3.0.0.min.js"></script> <script type="text/javascript" src="js/jquery-3.0.0.min.js"></script>
<script type="text/javascript" src="js/jquery.form.min.js"></script> <script type="text/javascript" src="js/jquery.form.min.js"></script>
<script type="text/javascript" src="bootstrap/js/bootstrap.min.js"></script> <script type="text/javascript" src="bootstrap/js/bootstrap.min.js"></script>
<script type="text/javascript" src="bootstrap-table/bootstrap-table.min.js"></script> <script type="text/javascript" src="bootstrap-table/bootstrap-table.min.js"></script>
<script type="text/javascript" src="gitalk/gitalk.min.js"></script> <script type="text/javascript" src="gitalk/gitalk.min.js"></script>
<script type="text/javascript" src="js/base64.min.js" ></script> <script type="text/javascript" src="js/base64.min.js"></script>
</head> </head>
<body> <body>
<h1>文件预览项目接入和测试界面</h1> <div class="panel-group container" id="accordion">
<div class="panel-group" id="accordion"> <h1>文件预览项目接入和测试界面</h1>
<div class="panel panel-default"> <div class="panel panel-default">
<div class="panel-heading"> <div class="panel-heading">
<h4 class="panel-title"> <h4 class="panel-title">
<a data-toggle="collapse" data-parent="#accordion" <a data-toggle="collapse" data-parent="#accordion" href="#collapseOne">
href="#collapseOne">
接入说明 接入说明
</a> </a>
</h4> </h4>
</div> </div>
<div id="collapseOne" class="panel-collapse collapse">
<div class="panel-body"> <div class="panel-body">
<div> <div>
如果你的项目需要接入文件预览项目达到对docx、excel、ppt、jpg等文件的预览效果那么通过在你的项目中加入下面的代码就可以 如果你的项目需要接入文件预览项目达到对docx、excel、ppt、jpg等文件的预览效果那么通过在你的项目中加入下面的代码就可以
成功实现: 成功实现:
<pre style="background-color: #2f332a;color: #cccccc"> <pre style="background-color: #2f332a;color: #cccccc">
var url = 'http://127.0.0.1:8080/file/test.txt'; //要预览文件的访问地址 var url = 'http://127.0.0.1:8080/file/test.txt'; //要预览文件的访问地址
window.open('http://127.0.0.1:8012/onlinePreview?url='+encodeURIComponent(base64Encode(url))); window.open('http://127.0.0.1:8012/onlinePreview?url='+encodeURIComponent(base64Encode(url)));
</pre> </pre>
</div> </div>
<div> <div>
新增多图片同时预览功能,接口如下: 新增多图片同时预览功能,接口如下:
<pre style="background-color: #2f332a;color: #cccccc"> <pre style="background-color: #2f332a;color: #cccccc">
var fileUrl =url1+"|"+"url2";//多文件使用“|”字符隔开 var fileUrl =url1+"|"+"url2";//多文件使用“|”字符隔开
window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(base64Encode(fileUrl))); window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(base64Encode(fileUrl)));
</pre> </pre>
</div> </div>
</div> </div>
</div> </div>
</div>
<div class="panel panel-default"> <div class="panel panel-default">
<div class="panel-heading"> <div class="panel-heading">
<h4 class="panel-title"> <h4 class="panel-title">
@@ -59,12 +57,11 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
</a> </a>
</h4> </h4>
</div> </div>
<div id="collapseTwo" class="panel-collapse collapse">
<div class="panel-body"> <div class="panel-body">
<div style="padding: 10px"> <div style="padding: 10px">
<form enctype="multipart/form-data" id="fileUpload"> <form enctype="multipart/form-data" id="fileUpload">
<input type="file" name="file" /> <input type="file" name="file"/>
<input type="button" id="btnsubmit" value=" " /> <input type="button" id="btnubmit" value=" "/>
</form> </form>
</div> </div>
<div> <div>
@@ -72,21 +69,18 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
</div> </div>
</div> </div>
</div> </div>
</div>
<div class="panel panel-default"> <div class="panel panel-default">
<div class="panel-heading"> <div class="panel-heading">
<h4 class="panel-title"> <h4 class="panel-title">
<a data-toggle="collapse" data-parent="#accordion" <a data-toggle="collapse" data-parent="#accordion" href="#collapseThree">
href="#collapseThree"> 发版记录
更新记录
</a> </a>
</h4> </h4>
</div> </div>
<div id="collapseThree" class="panel-collapse collapse in">
<div class="panel-body"> <div class="panel-body">
<div> <div>
2020年12月27日 <br> 2020年12月27日 <br>
2020年年终大版本更新架构全面设计代码全面重构代码质量全面提升二次开发更便捷欢迎拉源码品鉴提issue、pr共同建设 2020年年终大版本更新架构全面设计代码全面重构代码质量全面提升二次开发更便捷欢迎拉源码品鉴提issue、pr共同建设<br>
1. 架构模块调整,大量的代码重构代码质量提升N个等级欢迎品鉴<br> 1. 架构模块调整,大量的代码重构代码质量提升N个等级欢迎品鉴<br>
2. 增强XML文件预览效果新增XML文档数结构预览<br> 2. 增强XML文件预览效果新增XML文档数结构预览<br>
3. 新增markdown文件预览支持预览支持md渲染和源文本切换支持<br> 3. 新增markdown文件预览支持预览支持md渲染和源文本切换支持<br>
@@ -154,9 +148,9 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
2.项目github开源:<a href="https://github.com/kekingcn/kkFileView" target="_blank">https://github.com/kekingcn/kkFileView</a> 2.项目github开源:<a href="https://github.com/kekingcn/kkFileView" target="_blank">https://github.com/kekingcn/kkFileView</a>
</div> </div>
</div> </div>
</div>
<div class="panel-body"> <div class="panel-body">
<div id = "comments"></div> <div id="comments"></div>
</div> </div>
</div> </div>
@@ -190,9 +184,9 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
url: '${baseUrl}deleteFile?fileName=' + encodeURIComponent(fileName), url: '${baseUrl}deleteFile?fileName=' + encodeURIComponent(fileName),
success: function (data) { success: function (data) {
// 删除完成刷新table // 删除完成刷新table
if (1 == data.code) { if (1 === data.code) {
alert(data.msg); alert(data.msg);
} else{ } else {
$('#table').bootstrapTable('refresh', {}); $('#table').bootstrapTable('refresh', {});
} }
}, },
@@ -201,6 +195,7 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
} }
}) })
} }
$(function () { $(function () {
$('#table').bootstrapTable({ $('#table').bootstrapTable({
url: 'listFiles', url: 'listFiles',
@@ -211,14 +206,14 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
field: 'action', field: 'action',
title: '操作' title: '操作'
},] },]
}).on('pre-body.bs.table', function (e,data) { }).on('pre-body.bs.table', function (e, data) {
// 每个data添加一列用来操作 // 每个data添加一列用来操作
$(data).each(function (index, item) { $(data).each(function (index, item) {
item.action = "<a class='btn btn-default' target='_blank' href='${baseUrl}onlinePreview?url="+ encodeURIComponent(Base64.encode('${baseUrl}' + item.fileName)) +"'>预览</a>" + item.action = "<a class='btn btn-default' target='_blank' href='${baseUrl}onlinePreview?url=" + encodeURIComponent(Base64.encode('${baseUrl}' + item.fileName)) + "'>预览</a>" +
"<a class='btn btn-default' href='javascript:void(0);' onclick='deleteFile(\""+item.fileName+"\")'>删除</a>"; "<a class='btn btn-default' href='javascript:void(0);' onclick='deleteFile(\"" + item.fileName + "\")'>删除</a>";
}); });
return data; return data;
}).on('post-body.bs.table', function (e,data) { }).on('post-body.bs.table', function (e, data) {
return data; return data;
}); });
@@ -228,12 +223,12 @@ window.open('http://127.0.0.1:8012/picturesPreview?urls='+encodeURIComponent(bas
$(".loading_container").css("height", height).show(); $(".loading_container").css("height", height).show();
} }
$("#btnsubmit").click(function () { $("#btnSubmit").click(function () {
showLoadingDiv(); showLoadingDiv();
$("#fileUpload").ajaxSubmit({ $("#fileUpload").ajaxSubmit({
success: function (data) { success: function (data) {
// 上传完成刷新table // 上传完成刷新table
if (1 == data.code) { if (1 === data.code) {
alert(data.msg); alert(data.msg);
} else { } else {
$('#table').bootstrapTable('refresh', {}); $('#table').bootstrapTable('refresh', {});