content: package com.ruoyi.web.controller.work;
  
  import cn.hutool.core.io.resource.ResourceUtil;
  import com.alibaba.fastjson2.JSON;
  import com.itextpdf.text.pdf.PdfReader;
  import com.ruoyi.common.annotation.Anonymous;
  import com.ruoyi.common.config.RuoYiConfig;
  import com.ruoyi.common.constant.Constants;
  import com.ruoyi.common.core.controller.BaseController;
  import com.ruoyi.common.core.domain.AjaxResult;
  import com.ruoyi.common.core.redis.RedisLock;
  import com.ruoyi.common.exception.file.FileUploadException;
  import com.ruoyi.common.utils.StringUtils;
  import com.ruoyi.common.utils.file.FileUploadUtils;
  import com.ruoyi.work.config.PdfSignatureConfig;
  import com.ruoyi.work.domain.KeywordInfo;
  import com.ruoyi.work.domain.Stamp;
  import com.ruoyi.work.service.IPdfService;
  import com.ruoyi.work.utils.PdfUtils;
  import com.ruoyi.work.utils.TransparentImageUtils;
  import org.apache.pdfbox.pdmodel.PDDocument;
  import org.apache.pdfbox.rendering.PDFRenderer;
  import org.springframework.beans.factory.annotation.Autowired;
  import org.springframework.validation.annotation.Validated;
  import org.springframework.web.bind.annotation.*;
  
  import javax.imageio.ImageIO;
  import javax.servlet.http.HttpServletResponse;
  import javax.validation.constraints.NotBlank;
  import java.awt.image.BufferedImage;
  import java.io.File;
  import java.io.IOException;
  import java.io.InputStream;
  import java.io.PrintWriter;
  import java.nio.file.Files;
  import java.nio.file.Paths;
  import java.util.ArrayList;
  import java.util.HashMap;
  import java.util.List;
  
  /**
   * 操作pdf盖章
   *
   * @author fengcheng
   */
  @RestController
  @RequestMapping("/file/pdf")
  @Validated
  public class PdfController extends BaseController {
  
      @Autowired
      private IPdfService pdfService;
  
      @Autowired
      private RedisLock redisLock;
  
      @Autowired
      private PdfSignatureConfig pdfSignatureConfig;
  
      private static final String PDF_COUNTERSIGN = "pdf_countersign";
  
      /**
       * 完成盖章和签名
       *
       * @param stampList
       * @return
       */
      @PostMapping("/complete")
      public AjaxResult complete(@RequestBody List<Stamp> stampList) {
          redisLock.lock(PDF_COUNTERSIGN);
          try {
              pdfService.completeStamp(stampList);
          } finally {
              redisLock.unlock(PDF_COUNTERSIGN);
          }
          return AjaxResult.success();
      }
  
      /**
       * 完成加盖骑缝章
       *
       * @return
       */
      @PostMapping("/completeRidingSeal")
      public AjaxResult completeRidingSeal(@RequestBody Stamp stamp) throws IOException {
          boolean b;
  
          // 获取pdf文件路径
          String localPath = RuoYiConfig.getProfile();
          String pathPdf = StringUtils.substringAfter(stamp.getFilePath(), Constants.RESOURCE_PREFIX);
  
          String inputPdfPathPdf = localPath + pathPdf;
          String outPdfPathPdf = localPath + "/temp" + pathPdf;
  
          // 获取章图片路径
          String inputPdfPathSura = localPath + StringUtils.substringAfter(stamp.getImagesUrl(), Constants.RESOURCE_PREFIX);
  
          PdfSignatureConfig pdfSignatureConfig1 =
                  new PdfSignatureConfig(
                          ResourceUtil.getStream(pdfSignatureConfig.getPath()),
                          pdfSignatureConfig.getPassword(),
                          pdfSignatureConfig.getName(),
                          pdfSignatureConfig.getPhone(),
                          pdfSignatureConfig.getPlace(),
                          pdfSignatureConfig.getCause());
          redisLock.lock(PDF_COUNTERSIGN);
          try {
              b = PdfUtils.generatePagingSeal(pdfSignatureConfig1, inputPdfPathPdf, outPdfPathPdf, inputPdfPathSura, stamp.getX(), stamp.getY(), stamp.getWidth(), stamp.getHeight(), localPath);
          } finally {
              redisLock.unlock(PDF_COUNTERSIGN);
          }
          return toAjax(b);
      }
  
      /**
       * 通过关键字获取xy
       *
       * @param filePath 文档id
       * @param keyword  关键字
       * @return Result
       */
      @GetMapping("/keyword")
      public AjaxResult getSealLocation(String filePath, String keyword) {
          // 本地资源路径
          String localPath = RuoYiConfig.getProfile();
          // 数据库资源地址
          String loadPath = localPath + StringUtils.substringAfter(filePath, Constants.RESOURCE_PREFIX);
  
          try (InputStream io = Files.newInputStream(Paths.get(loadPath))) {
              List<KeywordInfo> list = pdfService.getSealLocation(new PdfReader(io), keyword);
              return AjaxResult.success(list);
          } catch (Exception e) {
              return AjaxResult.error(e.getMessage());
          }
      }
  
      /**
       * 生成骑缝章图片
       *
       * @param suraImg 印章路径
       * @param page    pdf总页数
       * @return
       */
      @GetMapping("/generatePagingSeal")
      public AjaxResult generatePagingSeal(String suraImg, int page) {
          // 本地资源路径
          String localPath = RuoYiConfig.getProfile();
          // 数据库资源地址
          String loadPath = localPath + StringUtils.substringAfter(suraImg, Constants.RESOURCE_PREFIX);
  
          List<HashMap<String, Object>> map = new ArrayList<>();
  
          // 获取文件后缀
          String fileExtension = FileUploadUtils.getFileExtension(loadPath);
  
          String name = new File(loadPath).getName();
          String nameWithoutExtension = name.substring(0, name.lastIndexOf("."));
  
          try {
              BufferedImage[] images = PdfUtils.getImage(loadPath, page, null, null);
              for (int i = 0; i < page; i++) {
                  HashMap<String, Object> hashMap = new HashMap<String, Object>(16);
  
                  BufferedImage image = images[i];
                  String filePath = localPath + "/sura/" + nameWithoutExtension + (i + 1) + "." + fileExtension;
                  File outputFile = new File(filePath);
  
                  if (!outputFile.exists()) {
                      outputFile.mkdirs();
                  }
                  ImageIO.write(image, fileExtension, outputFile);
  
  
                  if (TransparentImageUtils.changeImgColor(filePath, filePath.replace(FileUploadUtils.getFileExtension(filePath), "png"))) {
                      String fileName = "/sura" + "/" + outputFile.getName();
                      hashMap.put("url", Constants.RESOURCE_PREFIX + fileName);
                      hashMap.put("page", i + 1);
                      map.add(hashMap);
                  } else {
                      throw new FileUploadException("处理失败");
                  }
              }
          } catch (Exception e) {
              e.printStackTrace();
              return AjaxResult.error();
          }
          return AjaxResult.success(map);
      }
  
      /**
       * 获取pdf大纲
       *
       * @param filePath
       * @return
       */
      @GetMapping("/getPdfOutline")
      public AjaxResult getPdfOutline(@NotBlank(message = "filePath为空") String filePath) {
          // 本地资源路径
          String localPath = RuoYiConfig.getProfile();
          // 数据库资源地址
          String downloadPath = localPath + StringUtils.substringAfter(filePath, Constants.RESOURCE_PREFIX);
          List<HashMap<String, Object>> outlines = pdfService.getPdfOutline(downloadPath);
          return AjaxResult.success(outlines);
      }
  
  
      /**
       * 获取pdf指定页图片,返回给前端图片
       *
       * @param filePath 文档路径
       * @param page     页码
       * @param response
       * @throws IOException
       */
      @Anonymous
      @GetMapping("/img")
      public void img(String filePath, Integer page, HttpServletResponse response)
              throws IOException {
          // 本地资源路径
          String localPath = RuoYiConfig.getProfile();
          // 数据库资源地址
          String downloadPath = localPath + StringUtils.substringAfter(filePath, Constants.RESOURCE_PREFIX);
  
          PDDocument doc = PDDocument.load(new File(downloadPath));
          PDFRenderer renderer = new PDFRenderer(doc);
          int pageCount = doc.getNumberOfPages();
          if (page - 1 > pageCount) {
              //返回结果
              response.setContentType("application/json");
              response.setCharacterEncoding("UTF-8");
              // 获取PrintWriter对象
              PrintWriter out = response.getWriter();
              out.print(JSON.toJSONString(AjaxResult.error()));
              // 释放PrintWriter对象
              out.flush();
              out.close();
              return;
          }
          response.setContentType("image/jpeg");
          // 不缓存此内容
          response.setHeader("Pragma", "No-cache");
          response.setHeader("Cache-Control", "no-cache");
          response.setDateHeader("Expire", 0);
  
          BufferedImage image = renderer.renderImage(page - 1, 2f);
          ImageIO.write(image, "JPEG", response.getOutputStream());
          doc.close();
      }
  }
  