平行文档转换ODT> PDF的LibreOffice(Parallel Document Co

2019-08-17 04:39发布

我将数以百计的ODT文件为PDF文件,它需要很长的时间做一前一后。 我有多个内核的CPU。 是否有可能使用bash或Python编写一个脚本在平行于做这些? 有没有一种方法来并行(如果我用不知道正确的字),使用LibreOffice的命令行批处理文件的转换? 我一直在做它在Python / bash中调用下面的命令:

libreoffice --headless --convert-to pdf *appsmergeme.odt

要么

subprocess.call(str('cd $HOME; libreoffice --headless --convert-to pdf *appsmergeme.odt'), shell=True);

谢谢!

蒂姆

Answer 1:

你可以作为一个守护进程/服务运行的LibreOffice。 请检查下面的链接,也许它可以帮助你太: 守护进程的LibreOffice的服务

其他posibility是使用unoconv 。 “unoconv是一个命令行实用工具,可以将任何文件格式的OpenOffice可以导入到任何文件格式,OpenOffice是可以导出的。”



Answer 2:

这个线程或答案是旧的。 我测试的LibreOffice 4.4,我可以确认我可以同时运行的LibreOffice。 看到我的脚本。

 for odt in test*odt ; do echo $odt soffice --headless --convert-to pdf $odt & ps -ef|grep ffice done 



Answer 3:

我在golang批量编写的程序转换成千上万的DOC / XLS文件。

  • 定义“根”变量值的文件的路径转换
  • 已经转换为PDF文件被跳过(如果没有,在访问()函数评论检验条件)
  • 在这里我使用4个线程(我有一个英特尔酷睿i3 4个核心)。 您可以在main()函数修改值

有时,它可能发生的LibreOffice不转换某些文件,所以你应该打开它,并将其手动转换为PDF。 幸运的是,他们只是10我的16.000文件转换的。

package main

import (
    "os/exec"
    "sync"
    "path/filepath"
    "os"
    "fmt"
    "strings"
)

// root dir of your documents to convert
root := "/.../conversion-from-office/"

var tasks = make(chan *exec.Cmd, 64)

func visit(path string, f os.FileInfo, err error) error {
    if (f.IsDir()) {
        // fmt.Printf("Entering %s\n", path)
    } else {
        ext := filepath.Ext(path)
        if (strings.ToLower (ext) == "pdf") {
        } else {


            outfile := path[0:len(path)-len(ext)] + ".pdf"

            if _, err := os.Stat(outfile); os.IsNotExist(err) {

                fmt.Printf("Converting %s\n", path)

                outdir := filepath.Dir(path)
                tasks <- exec.Command("soffice", "--headless", "--convert-to", "pdf", path, "--outdir", outdir)
            }
        }
    }
    return nil
} 


func main() {
    // spawn four worker goroutines
    var wg sync.WaitGroup

    // the  ...; i < 4;... indicates that I'm using 4 threads
    for i := 0; i < 4; i++ {
        wg.Add(1)
        go func() {
            for cmd := range tasks {
                cmd.Run()
            }
            wg.Done()
        }()
    }


    err := filepath.Walk(root, visit)
    fmt.Printf("filepath.Walk() returned %v\n", err)

    close(tasks)

    // wait for the workers to finish
    wg.Wait()
}


Answer 4:

我们与unoconv类似的问题。 unoconv内部利用的LibreOffice的。 我们通过发送多个文件中的一个调用到unoconv解决了这个问题。 因此,而不是遍历所有的文件,我们只是分区的文件组到水桶,占O / P格式每个桶。 然后我们作出有桶尽可能多地调用。

我敢肯定的LibreOffice也有类似的模式。



Answer 5:

由于笔者已经介绍Python作为一个有效的答案:

import subprocess
import os, glob
from multiprocessing.dummy import Pool    # wrapper around the threading module

def worker(fname, dstdir=os.path.expanduser("~")):
    subprocess.call(["libreoffice", "--headless", "--convert-to", "pdf", fname],
                    cwd=dstdir)

pool = Pool()
pool.map(worker, glob.iglob(
        os.path.join(os.path.expanduser("~"), "*appsmergeme.odt")
    ))

使用线程池,而不是通过一个进程池multiprocessing.dummy因为真正的并行新工艺被催生足够subprocess.call()反正。

我们可以在命令以及当前工作目录cwd直接。 无需加载shell为每个文件只是这样做。 此外, os.path支持跨平台的互操作性。



Answer 6:

未经测试的潜在有效:

你/可/能够:

  • 瓜分文件分成若干部分公平的方式,如平行批次将他们所有的文件夹;
  • 创建一个独特的本地用户帐户来处理每个文件夹;
  • 运行连续的LibreOffice每个用户

 for paralleluser in timlev1 timlev2 timlev3 timlev4 ; do
      su - $paralleluser -c \
         "for file in /var/spool/pdfbatches/$paralleluser ; do \
            libreoffice --headless --convert-to pdf $file ; done" 
 done

通过使用su -你会不小心从您的实际会话继承任何环境变量,所以并行进程不应该彼此(从争夺资源除外)干扰。

请记住,这些都是有可能的I / O密集型任务,所以运行1每个CPU核心可能不会加速到你的意思非常多。



文章来源: Parallel Document Conversion ODT > PDF Libreoffice