Springboot + Vue 下载Word、PDF文档并保留内部格式

相对于上传,下载时复杂的地方就是文件中文名称乱码

前端

            <el-button @click="clickCall('handleExport', scope,index)">导出</el-button>
 // 文件下载操作
    handleExport(row) {
      axios
        .get(**********master/proj/exportContract?id=" + row.id, {
          responseType: "blob",
          headers: { Authorization: Cookie.get("**********") },
        })
        .then((response) => {

       // 获取后端返回的文件名
        const contentDisposition = response.headers["content-disposition"];
        const fileNameMatch = contentDisposition.match(/filename="(.+)"/);
        console.log(fileNameMatch[1])
        const fileName = this.binaryStringToString(fileNameMatch[1])
        // 创建URL并模拟点击下载链接
        const url = window.URL.createObjectURL(new Blob([response.data]));
        const link = document.createElement("a");
        link.href = url;
        link.setAttribute("download", fileName);
        document.body.appendChild(link);
        link.click();
        })
        .catch((err) => {
          this.$message.error(`数据导出失败,${err.message}`);
        });
    },
    binaryStringToString(binaryStr){
    	  const binaryBytes = binaryStr.split(" ");
 		 const bytes = binaryBytes.map(binaryByte => parseInt(binaryByte, 2));
 		 const utf8String = new TextDecoder().decode(new Uint8Array(bytes));
 		 return utf8String;
    },

后端

    @ApiOperation("导出合同文件")
    @GetMapping("exportContract")
    public ResponseEntity<Resource> exportData(@RequestParam(value="id")Integer id) throws Exception {
        return projectService.exportData(id);
    }
      @Override
    public ResponseEntity<Resource> exportData(Integer id) throws IOException {
        Project project = projectRepo.getById(Long.valueOf(id));
        if (project.getContactFile().isBlank()) {
            throw (new BizExceptEntityNotFound("文件不存在!"));
        }
        File file = new File(project.getContactFile());
        // 设置响应头
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_OCTET_STREAM);

        String binaryString  = stringToBinary(project.getContactFile().split("/")[2]);
        System.out.println(project.getContactFile().split("/")[2]);
        System.out.println(binaryString );
        System.out.println(binaryToString(binaryString ));
        headers.setContentDisposition(ContentDisposition.parse("attachment; filename=" +binaryString  ));
        return new ResponseEntity<>(new FileSystemResource(file), headers, HttpStatus.OK);
    }

    /**
     * 字符串转8位一组的二进制字符串
     * @param inputString
     * @return
     */
    public static String stringToBinary(String inputString) {
        byte[] utf8Bytes = inputString.getBytes(StandardCharsets.UTF_8);
        StringBuilder binaryStr = new StringBuilder();
        for (byte b : utf8Bytes) {
            String binaryByte = String.format("%8s", Integer.toBinaryString(b & 0xFF)).replace(' ', '0');
            binaryStr.append(binaryByte).append(" ");
        }
        return binaryStr.toString().trim();
    }

        public static String binaryToString(String binaryStr) {
            StringBuilder result = new StringBuilder();
            String[] binaryBytes = binaryStr.split(" ");
            byte[] bytes = new byte[binaryBytes.length];
            for (int i = 0; i < binaryBytes.length; i++) {
                bytes[i] = (byte) Integer.parseInt(binaryBytes[i], 2);
            }
            result.append(new String(bytes, StandardCharsets.UTF_8));
            return result.toString();
        }

我采用的是把文件名转成二进制传输,再转化回去。最后没乱

在这里插入图片描述

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
要实现Spring BootVue导出Word文档,可以使用poi和docx4j这两个工具。 首先是后端Spring Boot的实现: 1. 添加poi和docx4j依赖到pom.xml文件中: ```xml <dependency> <groupId>org.apache.poi</groupId> <artifactId>poi</artifactId> <version>4.1.2</version> </dependency> <dependency> <groupId>org.docx4j</groupId> <artifactId>docx4j</artifactId> <version>11.3.3</version> </dependency> ``` 2. 创建Word导出接口: ```java @RestController @RequestMapping("/export") public class ExportController { @GetMapping("/word") public void exportWord(HttpServletResponse response) throws Exception { // 创建一个空白的Word文档 WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.createPackage(); // 添加段落 wordMLPackage.getMainDocumentPart().addParagraphOfText("Hello, World!"); // 设置响应头 response.setContentType("application/vnd.openxmlformats-officedocument.wordprocessingml.document"); response.setHeader("Content-Disposition", "attachment; filename=test.docx"); // 输出Word文档 wordMLPackage.save(response.getOutputStream()); } } ``` 3. 启动Spring Boot应用,访问http://localhost:8080/export/word即可下载导出的Word文档。 然后是前端Vue的实现: 1. 安装axios和file-saver依赖: ```bash npm install axios file-saver --save ``` 2. 创建导出Word的方法: ```js exportWord() { axios({ method: 'get', url: '/export/word', responseType: 'blob' }).then(response => { const blob = new Blob([response.data]); const fileName = 'test.docx'; saveAs(blob, fileName); }); } ``` 3. 在Vue组件中添加一个按钮,并绑定导出Word的方法: ```html <template> <div> <button @click="exportWord">导出Word</button> </div> </template> <script> import axios from 'axios'; import { saveAs } from 'file-saver'; export default { name: 'Export', methods: { exportWord() { axios({ method: 'get', url: '/export/word', responseType: 'blob' }).then(response => { const blob = new Blob([response.data]); const fileName = 'test.docx'; saveAs(blob, fileName); }); } } }; </script> ``` 4. 运行Vue应用,点击按钮即可下载导出的Word文档。 以上就是Spring BootVue导出Word文档的实现步骤,希望能对你有帮助!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值