Java中的Docx转Pdf转换器

6
以下代码与Apache poi 3.16不兼容。 请有人提供正确的解决方案,我的项目中只能使用一些依赖项。
public void ConvertToPDF(String docPath, String pdfPath) {
    try {
        InputStream doc = new FileInputStream(new File(docPath));
        XWPFDocument document = new XWPFDocument(doc);
        PdfOptions options = PdfOptions.create();
        OutputStream out = new FileOutputStream(new File(pdfPath));
        PdfConverter.getInstance().convert(document, out, options);
        System.out.println("Done");
    } catch (FileNotFoundException ex) {
        System.out.println(ex.getMessage());
    } catch (IOException ex) {
        System.out.println(ex.getMessage());
    }
}

异常:

Exception in thread "AWT-EventQueue-0" java.lang.NoSuchMethodError: org.apache.poi.POIXMLDocumentPart.getPackageRelationship()Lorg/apache/poi/openxml4j/opc/PackageRelationship;
at org.apache.poi.xwpf.converter.core.styles.XWPFStylesDocument.getFontsDocument(XWPFStylesDocument.java:1479)
at org.apache.poi.xwpf.converter.core.styles.XWPFStylesDocument.<init>(XWPFStylesDocument.java:190)
at org.apache.poi.xwpf.converter.core.styles.XWPFStylesDocument.<init>(XWPFStylesDocument.java:184)
at org.apache.poi.xwpf.converter.core.XWPFDocumentVisitor.createStylesDocument(XWPFDocumentVisitor.java:166)
at org.apache.poi.xwpf.converter.core.XWPFDocumentVisitor.<init>(XWPFDocumentVisitor.java:159)
at org.apache.poi.xwpf.converter.pdf.internal.PdfMapper.<init>(PdfMapper.java:149)
at org.apache.poi.xwpf.converter.pdf.PdfConverter.doConvert(PdfConverter.java:55)
at org.apache.poi.xwpf.converter.pdf.PdfConverter.doConvert(PdfConverter.java:38)
at org.apache.poi.xwpf.converter.core.AbstractXWPFConverter.convert(AbstractXWPFConverter.java:45)
at recall.wordEditor.converter(recall_word.java:395)
at recall.wordEditor.process(recall_word.java:379)
at recall.wordEditor$5.actionPerformed(recall_word.java:194)
at javax.swing.AbstractButton.fireActionPerformed(Unknown Source)
at javax.swing.AbstractButton$Handler.actionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.fireActionPerformed(Unknown Source)
at javax.swing.DefaultButtonModel.setPressed(Unknown Source)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(Unknown Source)
at java.awt.Component.processMouseEvent(Unknown Source)
at javax.swing.JComponent.processMouseEvent(Unknown Source)
at java.awt.Component.processEvent(Unknown Source)
at java.awt.Container.processEvent(Unknown Source)
at java.awt.Component.dispatchEventImpl(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.LightweightDispatcher.retargetMouseEvent(Unknown Source)
at java.awt.LightweightDispatcher.processMouseEvent(Unknown Source)
at java.awt.LightweightDispatcher.dispatchEvent(Unknown Source)
at java.awt.Container.dispatchEventImpl(Unknown Source)
at java.awt.Window.dispatchEventImpl(Unknown Source)
at java.awt.Component.dispatchEvent(Unknown Source)
at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
at java.awt.EventQueue.access$500(Unknown Source)
at java.awt.EventQueue$3.run(Unknown Source)
at java.awt.EventQueue$3.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue$4.run(Unknown Source)
at java.awt.EventQueue$4.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
at java.awt.EventQueue.dispatchEvent(Unknown Source)
at java.awt.EventDispatchThread.pumpOneEventForFilters(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
at java.awt.EventDispatchThread.run(Unknown Source)

1
“is not working”:你是指它抛出异常了吗?能否请你将这个问题补充到你的提问中呢? - Leviand
请参见 https://dev59.com/6FUK5IYBdhLWcg3wwSLg#51337157 获取已测试并可用的完整示例。 - Axel Richter
4个回答

30
这主要问题在于那些`PdfOptions`和`PdfConverter`不是`apache poi`项目的一部分。它们是由`opensagres`开发的,最初版本的命名很糟糕,为`org.apache.poi.xwpf.converter.pdf.PdfOptions`和`org.apache.poi.xwpf.converter.pdf.PdfConverter`。这些旧类自2014年以来没有更新,并且需要使用`apache poi`的`3.9`版本。
请使用更加当前的fr.opensagres.poi.xwpf.converter.pdf,它可以与最新稳定版本的`apache poi 3.17`一起使用。
然后进行操作。
import java.io.InputStream;
import java.io.OutputStream;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.File;

//needed jars: fr.opensagres.poi.xwpf.converter.core-2.0.1.jar, 
//             fr.opensagres.poi.xwpf.converter.pdf-2.0.1.jar,
//             fr.opensagres.xdocreport.itext.extension-2.0.1.jar,
//             itext-2.1.7.jar                                  
import fr.opensagres.poi.xwpf.converter.pdf.PdfOptions;
import fr.opensagres.poi.xwpf.converter.pdf.PdfConverter;

//needed jars: apache poi and it's dependencies
import org.apache.poi.xwpf.usermodel.XWPFDocument;

public class DOCXToPDFConverterSampleMin {

 public static void main(String[] args) throws Exception {

  String docPath = "./WordDocument.docx";
  String pdfPath = "./WordDocument.pdf";

  InputStream in = new FileInputStream(new File(docPath));
  XWPFDocument document = new XWPFDocument(in);
  PdfOptions options = PdfOptions.create();
  OutputStream out = new FileOutputStream(new File(pdfPath));
  PdfConverter.getInstance().convert(document, out, options);

  document.close();
  out.close();

 }
}

2018年10月: 这段代码使用的是apache poi 3.17版本,无法在apache poi 4.0.0版本下运行,因为apache poi发生了一些变化,而这些变化在fr.opensagres.poi.xwpf.converter中尚未考虑到。
2019年2月: 现在对我来说运行良好,使用最新的apache poi版本4.0.1和最新版本的2.0.2fr.opensagres.poi.xwpf.converter.pdf及其相关组件。
2021年6月: 使用apache poi版本4.1.2和最新版本的2.0.2fr.opensagres.poi.xwpf.converter.pdf及其相关组件进行工作。 无法使用apache poi版本5.0.0,因为XDocReport需要ooxml-schemas,而apache poi 5不再支持。
2022年4月: 使用apache poi版本5.2.2和最新版本的2.0.3fr.opensagres.poi.xwpf.converter.pdf及其相关组件。
2023年7月: 使用apache poi版本5.2.3和最新版本的2.0.4fr.opensagres.poi.xwpf.converter.pdf及其相关工具进行工作。

@Alex Richter您好,能否提供一个可行的示例或者库链接?我已经在Android Studio上尝试了几周,但是无论我怎么做都无法使其正常工作。有时会出现重复错误、异常或找不到类等问题,有时候可以编译通过,但在运行时找不到类。我使用的是Android Studio:Arctic Fox。 - Ahsan raza
@Ahsan raza:以上是使用默认的Java运行环境的工作示例。但是,androidJava不同,只是java的一部分。在android上使用apache poi存在多个已知问题,例如缺少AWT类。因此,我没有android的解决方案。 - Axel Richter
@Anmol Jain:“因为我们需要org.apache.poi.xwpf.converter.pdf”:这个旧版本将无法在使用大于“apache poi 3.9”的“apache poi”版本时工作。而且这永远不会改变。怎么办?我在我的答案中清楚地指出了opensagres版本与哪些apache poi版本配合使用。 - Axel Richter
2022年4月:使用apache poi版本5.2.2和最新版本的fr.opensagres.poi.xwpf.converter.core和consorts,但仍无法正常工作。需要帮助吗? - Kumaresan Perumal
出现错误 org.apache.xmlbeans.XmlException: error: The 'namespace-prefix' feature is not supported while the 'namespaces' feature is enabled. @AxelRichter - Mujahid Khan
显示剩余3条评论

2
2021年6月:使用apache poi 4.1.2版本和最新版本的fr.opensagres.poi.xwpf.converter.core和相关版本的作品可以正常工作。无法使用apache poi 5.0.0版本,因为XDocReport需要ooxml-schemas,而apache poi 5不再支持它。 ooxml-schemas已被poi-ooxml-full取代。

https://mvnrepository.com/artifact/org.apache.poi/poi-ooxml-full/5.0.0

但是它与fr.opensagres.poi.xwpf.converter.core 2.0.2 不兼容,因为它不支持包含在apache-poi 5.0.0中的新版本CTStyle。

是的,它没用。我也遇到了同样的问题。当我下载PDF时,文字被覆盖了。我使用的版本是apache poi 5.2.0和xdocreport 2.0.2。 - Kumaresan Perumal
你有任何解决方案吗? - Kumaresan Perumal
org.apache.xmlbeans.XmlException: 错误:启用了“namespaces”功能,不支持“namespace-prefix”功能。 - Mujahid Khan

2

最新版本的 fr.opensagres.poi.xwpf.converter.core 2.0.2 可以与 apache poi 4.0.1 和 itext 2.17 兼容。

您只需要在 Maven 中添加以下依赖项,Maven 就会自动下载所有相关依赖项。(更新您的 Maven 项目,以便它下载所有这些库及其所有依赖项)

<dependency>
    <groupId>fr.opensagres.xdocreport</groupId>
    <artifactId>fr.opensagres.poi.xwpf.converter.pdf</artifactId>
    <version>2.0.2</version>
</dependency>

当我下载PDF时,文字被覆盖。我使用的版本是apache poi 5.2.0和xdocreport 2.0.2。 - Kumaresan Perumal

0

刚刚在POX.xml中添加了

<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>4.0.0</version>
</dependency>
<dependency>
    <groupId>fr.opensagres.xdocreport</groupId>
    <artifactId>fr.opensagres.poi.xwpf.converter.pdf</artifactId>
    <version>2.0.2</version>
</dependency>

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接