最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Java實現(xiàn)Word、Excel、PDF文件在線預覽幾種實現(xiàn)方式

 更新時間:2025年12月10日 08:23:59   作者:Full?Stack?Developme  
在Web開發(fā)中,經常需要實現(xiàn)文件的在線預覽功能,比如預覽PDF、Word、Excel等文檔格式,這篇文章主要介紹了Java實現(xiàn)Word、Excel、PDF文件在線預覽幾種實現(xiàn)方式的相關資料,需要的朋友可以參考下

在線預覽文檔通常有幾種方案:轉換為HTML、轉換為PDF再預覽、使用專門的預覽服務等。下面我將介紹幾種實現(xiàn)方式。

方案一:使用開源庫轉換為HTML預覽

1. 添加Maven依賴

<dependencies>
    <!-- Word處理 -->
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi</artifactId>
        <version>5.2.3</version>
    </dependency>
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi-ooxml</artifactId>
        <version>5.2.3</version>
    </dependency>
    
    <!-- Excel處理 -->
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi-scratchpad</artifactId>
        <version>5.2.3</version>
    </dependency>
    
    <!-- PDF處理 -->
    <dependency>
        <groupId>org.apache.pdfbox</groupId>
        <artifactId>pdfbox</artifactId>
        <version>2.0.27</version>
    </dependency>
    
    <!-- 文件類型檢測 -->
    <dependency>
        <groupId>org.apache.tika</groupId>
        <artifactId>tika-core</artifactId>
        <version>2.4.1</version>
    </dependency>
    
    <!-- Spring Boot Web -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
        <version>2.7.0</version>
    </dependency>
    
    <!-- 模板引擎 -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-thymeleaf</artifactId>
        <version>2.7.0</version>
    </dependency>
</dependencies>

2. 文件預覽服務實現(xiàn)

import org.apache.poi.hwpf.HWPFDocument;
import org.apache.poi.hwpf.converter.WordToHtmlConverter;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.converter.xhtml.XHTMLConverter;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.text.PDFTextStripper;
import org.springframework.stereotype.Service;
import org.w3c.dom.Document;

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import java.io.*;

@Service
public class FilePreviewService {

    /**
     * 預覽Word文檔(轉換為HTML)
     */
    public String previewWord(File file) throws Exception {
        String fileName = file.getName().toLowerCase();
        
        if (fileName.endsWith(".doc")) {
            return convertDocToHtml(file);
        } else if (fileName.endsWith(".docx")) {
            return convertDocxToHtml(file);
        } else {
            throw new IllegalArgumentException("不支持的Word格式");
        }
    }

    /**
     * 預覽Excel文檔(轉換為HTML表格)
     */
    public String previewExcel(File file) throws Exception {
        String fileName = file.getName().toLowerCase();
        Workbook workbook;
        
        try (FileInputStream fis = new FileInputStream(file)) {
            if (fileName.endsWith(".xls")) {
                workbook = new HSSFWorkbook(fis);
            } else if (fileName.endsWith(".xlsx")) {
                workbook = new XSSFWorkbook(fis);
            } else {
                throw new IllegalArgumentException("不支持的Excel格式");
            }
            
            return convertExcelToHtml(workbook);
        }
    }

    /**
     * 預覽PDF文檔(提取文本內容)
     */
    public String previewPdf(File file) throws Exception {
        try (PDDocument document = PDDocument.load(file)) {
            PDFTextStripper stripper = new PDFTextStripper();
            String text = stripper.getText(document);
            
            // 簡單的HTML包裝
            return "<html><body><pre>" + escapeHtml(text) + "</pre></body></html>";
        }
    }

    /**
     * 通用文件預覽方法
     */
    public String previewFile(File file) throws Exception {
        String fileName = file.getName().toLowerCase();
        
        if (fileName.endsWith(".doc") || fileName.endsWith(".docx")) {
            return previewWord(file);
        } else if (fileName.endsWith(".xls") || fileName.endsWith(".xlsx")) {
            return previewExcel(file);
        } else if (fileName.endsWith(".pdf")) {
            return previewPdf(file);
        } else {
            throw new IllegalArgumentException("不支持的文件格式");
        }
    }

    // 私有方法:具體轉換實現(xiàn)
    private String convertDocToHtml(File file) throws Exception {
        try (HWPFDocument document = new HWPFDocument(new FileInputStream(file))) {
            WordToHtmlConverter converter = new WordToHtmlConverter(
                DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument()
            );
            converter.processDocument(document);
            
            Document htmlDocument = converter.getDocument();
            return convertDocumentToString(htmlDocument);
        }
    }

    private String convertDocxToHtml(File file) throws Exception {
        try (XWPFDocument document = new XWPFDocument(new FileInputStream(file))) {
            StringWriter writer = new StringWriter();
            XHTMLConverter.getInstance().convert(document, writer, null);
            return writer.toString();
        }
    }

    private String convertExcelToHtml(Workbook workbook) {
        StringBuilder html = new StringBuilder();
        html.append("<html><body><table border='1'>");
        
        for (int i = 0; i < workbook.getNumberOfSheets(); i++) {
            Sheet sheet = workbook.getSheetAt(i);
            html.append("<tr><th colspan='10'>").append(sheet.getSheetName()).append("</th></tr>");
            
            for (Row row : sheet) {
                html.append("<tr>");
                for (Cell cell : row) {
                    html.append("<td>");
                    switch (cell.getCellType()) {
                        case STRING:
                            html.append(escapeHtml(cell.getStringCellValue()));
                            break;
                        case NUMERIC:
                            html.append(cell.getNumericCellValue());
                            break;
                        case BOOLEAN:
                            html.append(cell.getBooleanCellValue());
                            break;
                        default:
                            html.append(" ");
                    }
                    html.append("</td>");
                }
                html.append("</tr>");
            }
        }
        
        html.append("</table></body></html>");
        return html.toString();
    }

    private String convertDocumentToString(org.w3c.dom.Document doc) throws Exception {
        TransformerFactory tf = TransformerFactory.newInstance();
        Transformer transformer = tf.newTransformer();
        transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
        transformer.setOutputProperty(OutputKeys.METHOD, "html");
        transformer.setOutputProperty(OutputKeys.INDENT, "yes");
        transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
        
        StringWriter writer = new StringWriter();
        transformer.transform(new DOMSource(doc), new StreamResult(writer));
        return writer.toString();
    }

    private String escapeHtml(String text) {
        return text.replace("&", "&")
                  .replace("<", "<")
                  .replace(">", ">")
                  .replace("\"", "&quot;")
                  .replace("'", "&#39;");
    }
}

3. Spring Boot控制器

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.Resource;
import org.springframework.core.io.UrlResource;
import org.springframework.http.HttpHeaders;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;

@Controller
public class FilePreviewController {

    @Autowired
    private FilePreviewService filePreviewService;

    private final Path rootLocation = Paths.get("upload-dir");

    @GetMapping("/")
    public String index() {
        return "upload";
    }

    @PostMapping("/upload")
    public String handleFileUpload(@RequestParam("file") MultipartFile file, Model model) {
        try {
            // 創(chuàng)建上傳目錄
            if (!Files.exists(rootLocation)) {
                Files.createDirectories(rootLocation);
            }

            // 保存文件
            Path destinationFile = rootLocation.resolve(
                Paths.get(file.getOriginalFilename()))
                .normalize().toAbsolutePath();
            file.transferTo(destinationFile.toFile());

            // 預覽文件
            String htmlContent = filePreviewService.previewFile(destinationFile.toFile());
            model.addAttribute("previewContent", htmlContent);
            model.addAttribute("fileName", file.getOriginalFilename());

            return "preview";

        } catch (Exception e) {
            model.addAttribute("error", "文件預覽失敗: " + e.getMessage());
            return "upload";
        }
    }

    @GetMapping("/preview/{filename:.+}")
    @ResponseBody
    public ResponseEntity<String> previewFile(@PathVariable String filename) {
        try {
            Path file = rootLocation.resolve(filename);
            String htmlContent = filePreviewService.previewFile(file.toFile());
            return ResponseEntity.ok()
                .header(HttpHeaders.CONTENT_TYPE, "text/html; charset=utf-8")
                .body(htmlContent);
        } catch (Exception e) {
            return ResponseEntity.badRequest().body("預覽失敗: " + e.getMessage());
        }
    }

    @GetMapping("/download/{filename:.+}")
    @ResponseBody
    public ResponseEntity<Resource> downloadFile(@PathVariable String filename) {
        try {
            Path file = rootLocation.resolve(filename);
            Resource resource = new UrlResource(file.toUri());
            
            return ResponseEntity.ok()
                .header(HttpHeaders.CONTENT_DISPOSITION, 
                    "attachment; filename=\"" + resource.getFilename() + "\"")
                .body(resource);
        } catch (Exception e) {
            return ResponseEntity.notFound().build();
        }
    }
}

4. HTML模板

src/main/resources/templates/upload.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
    <meta charset="UTF-8">
    <title>文件上傳預覽</title>
</head>
<body>
    <h2>文件上傳預覽</h2>
    
    <form method="POST" enctype="multipart/form-data">
        <input type="file" name="file" accept=".doc,.docx,.xls,.xlsx,.pdf">
        <button type="submit">上傳并預覽</button>
    </form>
    
    <div th:if="${error}" style="color: red;">
        <p th:text="${error}"></p>
    </div>
</body>
</html>

src/main/resources/templates/preview.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
    <meta charset="UTF-8">
    <title>文件預覽</title>
    <style>
        .preview-container {
            border: 1px solid #ccc;
            padding: 20px;
            margin: 20px 0;
            max-height: 600px;
            overflow: auto;
        }
        .actions {
            margin: 10px 0;
        }
    </style>
</head>
<body>
    <h2>文件預覽: <span th:text="${fileName}"></span></h2>
    
    <div class="actions">
        <a th:href="@{'/download/' + ${fileName}}" rel="external nofollow" >下載原文件</a> |
        <a href="/" rel="external nofollow" >返回上傳</a>
    </div>
    
    <div class="preview-container" th:utext="${previewContent}">
        <!-- 預覽內容將在這里顯示 -->
    </div>
</body>
</html>

方案二:使用第三方服務(推薦用于生產環(huán)境)

對于生產環(huán)境,建議使用專門的文檔預覽服務:

  1. 使用Microsoft Office Online Server

  2. 使用Google Docs預覽服務

  3. 使用專業(yè)的文檔預覽SDK(如GroupDocs、Aspose等)

使用Google Docs預覽的示例:

public String previewWithGoogleDocs(String fileUrl) {
    // 將文件上傳到可訪問的URL,然后使用Google Docs預覽
    return "https://docs.google.com/gview?url=" + URLEncoder.encode(fileUrl, "UTF-8") + "&embedded=true";
}

方案三:使用專業(yè)的Java庫(Aspose)

// 需要購買許可證
import com.aspose.words.Document;
import com.aspose.words.HtmlSaveOptions;

public String previewWithAspose(File file) throws Exception {
    Document doc = new Document(file.getAbsolutePath());
    HtmlSaveOptions options = new HtmlSaveOptions();
    options.setExportImagesAsBase64(true);
    
    StringWriter writer = new StringWriter();
    doc.save(writer, options);
    return writer.toString();
}

啟動類

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class FilePreviewApplication {
    public static void main(String[] args) {
        SpringApplication.run(FilePreviewApplication.class, args);
    }
}

配置說明

application.properties中添加:

# 文件上傳大小限制
spring.servlet.multipart.max-file-size=10MB
spring.servlet.multipart.max-request-size=10MB

#  thymeleaf配置
spring.thymeleaf.cache=false
spring.thymeleaf.prefix=classpath:/templates/
spring.thymeleaf.suffix=.html

使用說明

  1. 啟動應用后訪問 http://localhost:8080

  2. 上傳Word、Excel或PDF文件

  3. 系統(tǒng)會自動轉換為HTML格式進行預覽

注意事項

  1. 性能考慮:大文件轉換可能耗時,建議添加進度提示

  2. 內存管理:處理大文件時注意內存使用,建議使用流式處理

  3. 格式兼容性:復雜格式可能無法完美轉換

  4. 安全性:對上傳文件進行病毒掃描和類型驗證

  5. 緩存策略:對已轉換的文件進行緩存以提高性能

這種方案適合中小型項目的文檔預覽需求,對于企業(yè)級應用,建議使用專業(yè)的文檔預覽服務。

總結

到此這篇關于Java實現(xiàn)Word、Excel、PDF文件在線預覽幾種實現(xiàn)方式的文章就介紹到這了,更多相關Java在線預覽Word、Excel、PDF內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • Java客戶端服務端上傳接收文件實現(xiàn)詳解

    Java客戶端服務端上傳接收文件實現(xiàn)詳解

    這篇文章主要介紹了Java客戶端服務端上傳接收文件實現(xiàn)詳解,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2020-07-07
  • SpringBoot實現(xiàn)異步任務的項目實踐

    SpringBoot實現(xiàn)異步任務的項目實踐

    本文將使用SpringBoot 去實現(xiàn)異步之間的調用,提高系統(tǒng)的并發(fā)性能、用戶體驗,具有一定的參考價值,感興趣的可以了解一下
    2023-10-10
  • Kotlin語法學習-變量定義、函數(shù)擴展、Parcelable序列化等簡單總結

    Kotlin語法學習-變量定義、函數(shù)擴展、Parcelable序列化等簡單總結

    這篇文章主要介紹了Kotlin語法學習-變量定義、函數(shù)擴展、Parcelable序列化等簡單總結的相關資料,需要的朋友可以參考下
    2017-05-05
  • java實現(xiàn)多圖片上傳功能

    java實現(xiàn)多圖片上傳功能

    這篇文章主要為大家詳細介紹了java多圖片同步上傳功能的實現(xiàn)方法,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-08-08
  • Java數(shù)據(jù)脫敏實現(xiàn)的方法總結

    Java數(shù)據(jù)脫敏實現(xiàn)的方法總結

    數(shù)據(jù)脫敏,指的是對某些敏感信息通過脫敏規(guī)則進行數(shù)據(jù)的變形,實現(xiàn)敏感隱私數(shù)據(jù)的可靠保護,本文主要是對后端數(shù)據(jù)脫敏實現(xiàn)的簡單總結,希望對大家有所幫助
    2023-07-07
  • 分享Java多線程實現(xiàn)的四種方式

    分享Java多線程實現(xiàn)的四種方式

    這篇文章主要介紹了分享Java多線程實現(xiàn)的四種方式,文章基于?Java的相關資料展開多線程的詳細介紹,具有一的的參考價值,需要的小伙伴可以參考一下
    2022-05-05
  • SpringBoot實戰(zhàn)記錄之數(shù)據(jù)訪問

    SpringBoot實戰(zhàn)記錄之數(shù)據(jù)訪問

    對于數(shù)據(jù)訪問層,無論是SQL還是NOSQL,Spring Boot默認采用整合Spring Data的方式進行統(tǒng)一處理,添加大量自動配置,屏蔽了很多設置,下面這篇文章主要介紹了SpringBoot實戰(zhàn)記錄之數(shù)據(jù)訪問,需要的朋友可以參考下
    2022-04-04
  • 解讀Spring配置與服務組件的關系和注入機制

    解讀Spring配置與服務組件的關系和注入機制

    這篇文章主要介紹了解讀Spring配置與服務組件的關系和注入機制,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-09-09
  • 詳解java中static關鍵詞的作用

    詳解java中static關鍵詞的作用

    這篇文章主要介紹了java中static關鍵詞的作用,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-01-01
  • java中應用Stack進行算術運算的操作

    java中應用Stack進行算術運算的操作

    這篇文章主要介紹了java中應用Stack進行算術運算的操作,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2021-03-03

最新評論

龙胜| 客服| 武邑县| 曲沃县| 黄石市| 同江市| 赣州市| 桐乡市| 宁陕县| 敦煌市| 长治县| 扎鲁特旗| 赞皇县| 宁远县| 井冈山市| 南充市| 宜川县| 大冶市| 蓝山县| 衡阳市| 山东| 南通市| 邵阳县| 留坝县| 徐闻县| 洪泽县| 绍兴县| 华阴市| 肇州县| 大荔县| 天峻县| 敦化市| 清河县| 长白| 台北县| 乐清市| 秀山| 涡阳县| 松江区| 平阳县| 叶城县|