Browse Source

OA文件需要访问17服务器

ecss-tx
han\hanst 1 month ago
parent
commit
fc60edbf53
  1. 53
      src/main/java/com/xujie/sys/common/utils/OfficeConverter.java
  2. 1
      src/main/java/com/xujie/sys/config/ShiroConfig.java
  3. 228
      src/main/java/com/xujie/sys/modules/oss/controller/OssController.java
  4. 3
      src/main/resources/application-dev.yml

53
src/main/java/com/xujie/sys/common/utils/OfficeConverter.java

@ -0,0 +1,53 @@
package com.xujie.sys.common.utils;
import com.aspose.cells.PageOrientationType;
import com.aspose.cells.PageSetup;
import com.aspose.cells.PaperSizeType;
import com.aspose.cells.SaveFormat;
import com.aspose.cells.Workbook;
import com.aspose.cells.Worksheet;
import com.aspose.words.Document;
import java.io.File;
/**
* Office文件转PDF工具类使用Aspose
*/
public class OfficeConverter {
public static String getFileExtension(File file) {
String fileName = file.getName();
int lastDot = fileName.lastIndexOf('.');
return (lastDot == -1) ? "" : fileName.substring(lastDot + 1);
}
public static void convertExcelToPdf(File file) throws Exception {
Workbook workbook;
String filePath = file.getAbsolutePath();
if (filePath.endsWith(".xlsx")) {
workbook = new Workbook(file.getAbsolutePath());
} else {
workbook = new Workbook(filePath);
}
Worksheet worksheet = workbook.getWorksheets().get(0);
PageSetup pageSetup = worksheet.getPageSetup();
pageSetup.setOrientation(PageOrientationType.PORTRAIT);
pageSetup.setPaperSize(PaperSizeType.PAPER_A_4);
pageSetup.setZoom(50);
pageSetup.setLeftMargin(0);
pageSetup.setRightMargin(0);
pageSetup.setTopMargin(0.5);
pageSetup.setBottomMargin(0.5);
String pdfPath = filePath.replaceAll("\\.xlsx|\\.xls", ".pdf");
workbook.save(pdfPath, SaveFormat.PDF);
}
public static void convertWordToPdf(File file) throws Exception {
Document document = new Document(file.getAbsolutePath());
String pdfPath = file.getAbsolutePath().replace(".docx", ".pdf").replace(".doc", ".pdf");
document.save(pdfPath);
}
}

1
src/main/java/com/xujie/sys/config/ShiroConfig.java

@ -48,6 +48,7 @@ public class ShiroConfig {
filterMap.put("/tcp", "anon"); filterMap.put("/tcp", "anon");
filterMap.put("/ckp-file/**", "anon"); filterMap.put("/ckp-file/**", "anon");
filterMap.put("/oss/2/**", "anon"); filterMap.put("/oss/2/**", "anon");
filterMap.put("/oss/previewOssFile", "anon");
// filterMap.put("/**", "authc"); // filterMap.put("/**", "authc");
filterMap.put("/webjars/**", "anon"); filterMap.put("/webjars/**", "anon");
filterMap.put("/druid/**", "anon"); filterMap.put("/druid/**", "anon");

228
src/main/java/com/xujie/sys/modules/oss/controller/OssController.java

@ -1,21 +1,33 @@
package com.xujie.sys.modules.oss.controller; package com.xujie.sys.modules.oss.controller;
import com.xujie.sys.common.utils.OfficeConverter;
import com.xujie.sys.common.utils.R; import com.xujie.sys.common.utils.R;
import com.xujie.sys.modules.oss.entity.SysOssEntity; import com.xujie.sys.modules.oss.entity.SysOssEntity;
import com.xujie.sys.modules.oss.service.SysOssService; import com.xujie.sys.modules.oss.service.SysOssService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile; import org.springframework.web.multipart.MultipartFile;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import java.io.*; import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.util.List; import java.util.List;
@RestController @RestController
@RequestMapping("/oss") @RequestMapping("/oss")
public class OssController { public class OssController {
private static final Logger logger = LoggerFactory.getLogger(OssController.class);
@Value("${sys-file.mes-url}")
private String mesUrl;
@Autowired @Autowired
private SysOssService sysOssService; private SysOssService sysOssService;
@ -62,4 +74,220 @@ public class OssController {
public void previewOssFileById2(@PathVariable("id") Integer id, HttpServletResponse response) throws Exception { public void previewOssFileById2(@PathVariable("id") Integer id, HttpServletResponse response) throws Exception {
sysOssService.previewOssFileById2(id,response); sysOssService.previewOssFileById2(id,response);
} }
/**
* 通过OSS服务代理预览或下载附件
* OSS接口POST http://172.26.68.17:8091//oss/2/{id}
* Word/Excel在预览模式下自动转换为PDF后输出
*
* @param id 附件IDsys_oss.id
* @param download 是否强制下载 true 则下载否则预览
*/
@GetMapping("/previewOssFile")
public void previewOssFile(Long id, String download, HttpServletResponse response) {
File tempFile = null;
File pdfFile = null;
try {
SysOssEntity attachment = sysOssService.getById(id);
if (attachment == null) {
response.sendError(HttpServletResponse.SC_NOT_FOUND, "附件不存在");
return;
}
String fileType = attachment.getFileType();
String fileName = attachment.getFileName();
if (fileType != null && fileType.startsWith(".")) {
fileType = fileType.substring(1);
}
fileType = fileType == null ? "" : fileType.toLowerCase().trim();
boolean forceDownload = "true".equalsIgnoreCase(download);
String ossUrl = mesUrl + id;
logger.info("请求OSS文件: {}", ossUrl);
HttpURLConnection conn = (HttpURLConnection) new URL(ossUrl).openConnection();
conn.setRequestMethod("POST");
conn.setConnectTimeout(10000);
conn.setReadTimeout(60000);
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestProperty("Content-Type", "application/json;charset=UTF-8");
conn.setRequestProperty("Content-Length", "0");
try (OutputStream reqOs = conn.getOutputStream()) {
reqOs.write(new byte[0]);
reqOs.flush();
}
int httpCode = conn.getResponseCode();
String ossContentType = conn.getContentType();
logger.info("OSS响应码: {}, Content-Type: {}", httpCode, ossContentType);
if (httpCode != HttpURLConnection.HTTP_OK) {
response.sendError(HttpServletResponse.SC_BAD_GATEWAY, "OSS服务器响应错误: " + httpCode);
conn.disconnect();
return;
}
byte[] fileBytes;
try (InputStream is = conn.getInputStream()) {
fileBytes = is.readAllBytes();
}
conn.disconnect();
if (fileBytes.length == 0) {
response.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "OSS服务器返回空文件");
return;
}
String actualFileType = detectActualFileType(fileBytes, ossContentType, fileType);
logger.info("OSS文件大小: {} bytes, db_fileType: {}, actual: {}", fileBytes.length, fileType, actualFileType);
if (!forceDownload && actualFileType.equals("pdf")) {
fileType = "pdf";
int dotIdx = fileName.lastIndexOf('.');
fileName = (dotIdx > 0 ? fileName.substring(0, dotIdx) : fileName) + ".pdf";
} else if (!forceDownload && (actualFileType.equals("doc") || actualFileType.equals("docx")
|| actualFileType.equals("xls") || actualFileType.equals("xlsx"))) {
tempFile = File.createTempFile("oss_preview_", "." + actualFileType);
try (FileOutputStream fos = new FileOutputStream(tempFile)) {
fos.write(fileBytes);
fos.flush();
}
logger.info("临时文件已写入: {}, size: {}", tempFile.getAbsolutePath(), tempFile.length());
if (actualFileType.equals("xls") || actualFileType.equals("xlsx")) {
OfficeConverter.convertExcelToPdf(tempFile);
} else {
OfficeConverter.convertWordToPdf(tempFile);
}
String pdfPath = tempFile.getAbsolutePath()
.replaceAll("\\.(doc|docx|xls|xlsx)$", ".pdf");
pdfFile = new File(pdfPath);
logger.info("期望PDF路径: {}, 是否存在: {}", pdfPath, pdfFile.exists());
if (pdfFile.exists()) {
fileBytes = Files.readAllBytes(pdfFile.toPath());
fileType = "pdf";
int dotIdx = fileName.lastIndexOf('.');
fileName = (dotIdx > 0 ? fileName.substring(0, dotIdx) : fileName) + ".pdf";
} else {
forceDownload = true;
fileType = actualFileType;
}
} else {
fileType = actualFileType;
}
response.setContentType(getContentType(fileType));
response.setContentLengthLong(fileBytes.length);
response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate");
response.setHeader("Pragma", "no-cache");
if (!forceDownload && isPreviewableType(fileType)) {
response.setHeader("Content-Disposition", "inline");
} else {
String encoded = URLEncoder.encode(fileName, StandardCharsets.UTF_8.toString())
.replaceAll("\\+", "%20");
response.setHeader("Content-Disposition",
"attachment; filename=\"" + encoded + "\"; filename*=UTF-8''" + encoded);
}
try (OutputStream os = response.getOutputStream()) {
os.write(fileBytes);
os.flush();
}
} catch (Exception e) {
logger.error("previewOssFile error: {}", e.getMessage(), e);
try {
response.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR, "获取文件失败: " + e.getMessage());
} catch (Exception ex) {
logger.error("sendError failed", ex);
}
} finally {
if (tempFile != null && tempFile.exists()) tempFile.delete();
if (pdfFile != null && pdfFile.exists()) pdfFile.delete();
}
}
private String detectActualFileType(byte[] bytes, String ossContentType, String dbFileType) {
if (bytes != null && bytes.length >= 4) {
if (bytes[0] == 0x25 && bytes[1] == 0x50 && bytes[2] == 0x44 && bytes[3] == 0x46) {
return "pdf";
}
if (bytes[0] == 0x50 && bytes[1] == 0x4B) {
if (dbFileType != null && (dbFileType.equals("xlsx") || dbFileType.equals("xls"))) {
return "xlsx";
}
return "docx";
}
if ((bytes[0] & 0xFF) == 0xD0 && (bytes[1] & 0xFF) == 0xCF
&& bytes[2] == 0x11 && (bytes[3] & 0xFF) == 0xE0) {
if (dbFileType != null && (dbFileType.equals("xls") || dbFileType.equals("xlsx"))) {
return "xls";
}
return "doc";
}
if ((bytes[0] & 0xFF) == 0xFF && (bytes[1] & 0xFF) == 0xD8) {
return "jpg";
}
if ((bytes[0] & 0xFF) == 0x89 && bytes[1] == 0x50 && bytes[2] == 0x4E && bytes[3] == 0x47) {
return "png";
}
}
if (ossContentType != null) {
String ct = ossContentType.toLowerCase();
if (ct.contains("pdf")) return "pdf";
if (ct.contains("jpeg") || ct.contains("jpg")) return "jpg";
if (ct.contains("png")) return "png";
if (ct.contains("word") || ct.contains("msword")) {
return dbFileType != null && dbFileType.equals("docx") ? "docx" : "doc";
}
if (ct.contains("excel") || ct.contains("spreadsheet")) {
return dbFileType != null && dbFileType.equals("xlsx") ? "xlsx" : "xls";
}
}
return dbFileType != null ? dbFileType : "bin";
}
private boolean isPreviewableType(String fileType) {
if (fileType == null || fileType.trim().isEmpty()) {
return false;
}
String t = fileType.toLowerCase().trim();
if (t.startsWith(".")) t = t.substring(1);
return t.equals("pdf") || t.equals("jpg") || t.equals("jpeg") || t.equals("png")
|| t.equals("gif") || t.equals("bmp") || t.equals("svg") || t.equals("webp")
|| t.equals("txt") || t.equals("html") || t.equals("htm")
|| t.equals("xml") || t.equals("json");
}
private String getContentType(String fileType) {
if (fileType == null || fileType.trim().isEmpty()) {
return "application/octet-stream";
}
String t = fileType.toLowerCase().trim();
if (t.startsWith(".")) t = t.substring(1);
switch (t) {
case "jpg": case "jpeg": return "image/jpeg";
case "png": return "image/png";
case "gif": return "image/gif";
case "bmp": return "image/bmp";
case "svg": return "image/svg+xml";
case "webp": return "image/webp";
case "ico": return "image/x-icon";
case "pdf": return "application/pdf";
case "doc": return "application/msword";
case "docx": return "application/vnd.openxmlformats-officedocument.wordprocessingml.document";
case "xls": return "application/vnd.ms-excel";
case "xlsx": return "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet";
case "ppt": return "application/vnd.ms-powerpoint";
case "pptx": return "application/vnd.openxmlformats-officedocument.presentationml.presentation";
case "txt": return "text/plain; charset=UTF-8";
case "html": case "htm": return "text/html; charset=UTF-8";
case "xml": return "text/xml; charset=UTF-8";
case "json": return "application/json; charset=UTF-8";
case "zip": return "application/zip";
case "rar": return "application/x-rar-compressed";
case "7z": return "application/x-7z-compressed";
case "mp4": return "video/mp4";
case "avi": return "video/x-msvideo";
case "mp3": return "audio/mpeg";
default: return "application/octet-stream";
}
}
} }

3
src/main/resources/application-dev.yml

@ -4,7 +4,7 @@ spring:
druid: druid:
driver-class-name: com.microsoft.sqlserver.jdbc.SQLServerDriver driver-class-name: com.microsoft.sqlserver.jdbc.SQLServerDriver
# url: jdbc:sqlserver://192.168.1.90:1433;databaseName=CKP_MES_Real_250207 # url: jdbc:sqlserver://192.168.1.90:1433;databaseName=CKP_MES_Real_250207
url: jdbc:sqlserver://xujiesoft.vicp.net:11515;databaseName=CKP_MES_Real_250207
url: jdbc:sqlserver://xujiesoft.vicp.net:11515;databaseName=CKT_MES_II_REAL_0309
# url: jdbc:sqlserver://xujiesoft.vicp.net:11515;databaseName=ckp-srm # url: jdbc:sqlserver://xujiesoft.vicp.net:11515;databaseName=ckp-srm
username: sa username: sa
password: XJsoft123 password: XJsoft123
@ -43,6 +43,7 @@ spring:
sys-file: sys-file:
file-path: 'D:\ckp-file'#不可以放入中文字符 file-path: 'D:\ckp-file'#不可以放入中文字符
oss-url: 'http://192.168.1.160:9000/' oss-url: 'http://192.168.1.160:9000/'
mes-url: 'http://192.168.1.162:8089/oss/2/'
#--------------------------------------------定时器任务参数------------------------------------------------- #--------------------------------------------定时器任务参数-------------------------------------------------
task: task:

Loading…
Cancel
Save