package jnpf.bizcommon.onlyoffice.service.impl;
|
|
import jnpf.dmsEntity.preview.model.DmsFilePreviewTicket;
|
import jnpf.exception.DataException;
|
import jnpf.util.TicketUtil;
|
import org.apache.pdfbox.Loader;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.stereotype.Service;
|
|
import java.io.IOException;
|
import java.util.Locale;
|
import java.util.UUID;
|
import java.util.function.Function;
|
|
/** Counts the physical pages rendered from the same protected source used by the preview. */
|
@Service
|
public class DmsOnlyOfficePageCountService {
|
private final OnlyOfficeDmsPrintRenderer renderer;
|
private final Function<String, Object> ticketReader;
|
|
@Autowired
|
public DmsOnlyOfficePageCountService(OnlyOfficeDmsPrintRenderer renderer) {
|
this(renderer, TicketUtil::parseTicket);
|
}
|
|
DmsOnlyOfficePageCountService(OnlyOfficeDmsPrintRenderer renderer,
|
Function<String, Object> ticketReader) {
|
this.renderer = renderer;
|
this.ticketReader = ticketReader;
|
}
|
|
public int getPageCount(UUID fileVersionId, String accessTicket) {
|
if (fileVersionId == null || accessTicket == null || accessTicket.isBlank()) {
|
throw new DataException("缺少页数查询文件版本或预览票据");
|
}
|
DmsFilePreviewTicket ticket;
|
try {
|
ticket = DmsFilePreviewTicket.fromRaw(ticketReader.apply(accessTicket));
|
} catch (RuntimeException exception) {
|
throw new DataException("DMS 预览票据无效或已过期");
|
}
|
if (!DmsFilePreviewTicket.SCOPE.equals(ticket.getScope())
|
|| !fileVersionId.equals(ticket.getFileVersionId())) {
|
throw new DataException("页数查询票据与文件版本或预览用途不匹配");
|
}
|
String name = ticket.getFileName().toLowerCase(Locale.ROOT);
|
if (!name.endsWith(".doc") && !name.endsWith(".docx")) {
|
throw new DataException("OnlyOffice 页数查询仅支持 doc、docx 文件");
|
}
|
// Keep preview preparation, approval pages and watermarks identical to the editor.
|
// Do not issue a PRINT ticket or use printBase, which changes the preview source.
|
byte[] pdf = renderer.render(ticket, accessTicket);
|
try (PDDocument document = Loader.loadPDF(pdf)) {
|
int pages = document.getNumberOfPages();
|
if (pages < 1) {
|
throw new DataException("OnlyOffice 排版结果没有有效页面");
|
}
|
return pages;
|
} catch (IOException exception) {
|
throw new DataException("无法读取 OnlyOffice 排版结果页数");
|
}
|
}
|
}
|