当前位置:首页 » 《我的小黑屋》 » 正文

java超简单实现文档在线预览功能,支持word\excel\text\pdf\图片等格式转pdf,aspost 转pdf部署linux中文乱码解决方案

20 人参与  2024年04月06日 12:10  分类 : 《我的小黑屋》  评论

点击全文阅读


一、背景

        在工作中需要对上传到服务器的各种类型包括但不限于word、pdf、excel等文件进行在线预览,前端比较菜搞不定,只能本人亲自上。

        网上的经验比较多也比较乱,有的只有预览,没有文件格式转换,有的也不说linux存在字体问题,本文会直白的给出过程和结果,包括文件预览,其他格式文件转pdf进行预览,前端如何接收展示

二、引入jar包

<dependency>
<groupId>org.apache.tika</groupId><artifactId>tika-core</artifactId><version>1.28.4</version>
</dependency>


<dependency>
<groupId>com.luhuiguo</groupId><artifactId>aspose-words</artifactId>
<version>23.1</version>
</dependency>

三、后端实现代码

controller

@GetMapping(”/preview”)

public ResponseEntity<?> previewFile(@RequestParam String fileName){
        String baseDir = RuoYiConfig.getUploadPath();
        String filePath = baseDir + File.separator + fileName;
        String extension = this.getExtension(fileName);
        String pdfPath ="";
        File file;
        if("docx”.equals(extension)||"doc".equals(extension)){

                pdfPath = filePath.substring(0, filePath.lastIndex0f( str:".") + 1) +                                 "pdf";FileCovertUtils.wordToPdf(filePath,pdfPath);
                file = new File(pdfPath);

        } else if ("png”.equals(extension)) {

                // excel\png等格式和上面word一样自己写逻辑

        } else{

                file= new File(filePath);

        }
        try (FileInputStream fileInputStream = new FileInputStream(file)) {

                byte[] buf = new byte[fileInputStream.available()];
                fileInputStream.read(buf);

                 return FileResponseUtils.getResponseEntity

                                (buf,contentDispositionType:"inline",FileUtils.getName(fileName));

        } catch (IOException e) {

                log.error("获取文件流异常{}",e);
                return “预览失败”;
        } finally {

                if ("docx".equals(extension)||“doc".equals(extension)) {

                        FileUtils.deleteFile(pdfPath);

                }

        }

}

getExtension

private String getExtension(String filename) {

        int dotIndex = filename.lastIndex0f( str: ".");

        if (dotIndex >  && dotIndex < filename.length() - 1){

                return filename.substring(dotIndex + 1);

        }
        return "";

}

FileResponseUtils.getResponseEntity

@Component
plic class FileResponseUtils {
        public static ResponseEntity<?> getResponseEntity(byte[] buf, String         contentDispositionlype, String originalFilelame){

                ResponseEntity.BodyBuilder responseEntity = ResponseEntity.ok();HttpHeaders                 HttpHeaders = new HttpHeaders();
                Tika tika = new Tika();
                String mediaType = tika.detect(buf);
                httpHeaders.setContentType(MediaType.parseMediaType(mediaType));
                HttpHeaders headers = new HttpHeaders();
                headers.setContentType(MediaType.parseMediaType(mediaType);

                headers.add(HttpHeaders.CONTENT_DISPOSITION, headerValue:                                                 cntentDispositionType+"; filename=" + originalFilename);
                httpHeaders.setCacheControl(CacheControl.noCache());

                return responseEntity.headers(httpHeaders).body(buf);

        }

}

 FileCovertUtils

public static void wordToPdf(String wordPath, String pdfPath) {

        File file=new File(pdfPath);
        try {

                FileOutputStream os = new FileOutputStream(file);

                Document doc = new Document(wordPath);

                if (System.getProperty("os,name").toLowerCase().contains("linux")){

                        FontSettings fontSettings = new FontSettings();

                        fontSettings.setFontsFolder( fontFolder: "/usr/share/fonts/", recursive: true);

                        doc.setFontSettings(fontSettings);

                }

                doc.save(os,SaveFormat.PDF);
                os.flush();
                os.close();

        }  catch (Exception e){
                log.error("word转pdf异常:{}",e);

        }

}

FileUtils.getName

public static String getName(String fileName){
        if (fileName == null){

                 return null:

        }
        int lastUnixPos = fileName .lastIndex0f('/');

        int lastWindowsPos = fileName .lastIndexOf('\\');

        int index = Math.max(lastUnixPos, lastWindowsPos);

        return fileName.substring(index + 1);

}

四、前端接收方式,简单粗暴

展示:

//1、请求接口 请求设置responseType
axios.get(url,{resonseType:'blob'})
 
//2.根据返回的值创建一个Blob对象, 以pdf文件为例
let blob = new Blob([result],{
       type: "application/pdf;chartset=UTF-8"
})
 
//3.window.URL.createObjectURL创建一个url连接
let blob = new Blob([result],{
       type: "application/pdf;chartset=UTF-8"
})
let url = window.URL.createObjectURL(blob)
 
//4.在线预览
//可以用iframe预览,url的值为 window.URL.createObjectURL(blob),或者直接打开window.open(url)

打印:

//1.创建iframe标签
const iframe = document.createElement('iframe')
 
//2.属性相关
iframe.className = 'tmp-pdf';
iframe.style.display = 'none'
// blobUrl 像在线预览1,2,3这样得来的url
iframe.src = blobUrl
 
//3.创建好的iframe添加到页面body
document.body.appendChild(iframe)
 
//4.执行打印方法,并移除iframe
setTimeout(function() {
   iframe.contentWindow.print()
   document.body.removechild(iframe)
}, 100)

五、linux中文字体乱码解决

        项目使用aspost转pdf,Windows系统本地调试的时候一切正常,部署到Linux服务器,转换后的pdf文件中文无法正确显示。

原因是Linux服务器上没有中文字体库。

解决方法:在linux服务器中安装字体,在Windows系统找到字体文件,路径C:\Windows\Fonts,将字体文件fonts上传到服务器

1、把fonts (只有一层文件夹) 上传至tmp
2、移动 fonts: sudo mv /tmp/fonts/ /usr/share/
3、授权文件: sudo chmod 755 /usr/share/fonts/*
4、进入文件: cd /usr/share/fonts/4
5、执行: sudo mkfontscale 如果没命令执行sudo yum install mkfontscale
6、执行: sudo mkfontdir 如果没命令执行sudo yum install fontconfig
7、sudo fc-cache

六、效果

七、推荐文章

java接口返回图片或pdf如何设置在线预览还是下载

文档在线预览(三)将word、txt、ppt、excel、图片转成pdf来实现在线预览


点击全文阅读


本文链接:http://zhangshiyu.com/post/91097.html

<< 上一篇 下一篇 >>

  • 评论(0)
  • 赞助本站

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

关于我们 | 我要投稿 | 免责申明

Copyright © 2020-2022 ZhangShiYu.com Rights Reserved.豫ICP备2022013469号-1