Подтвердить что ты не робот

.doc в pdf с использованием python

Мне поручено преобразовывать тонны файлов .doc в .pdf. И единственный способ, которым мой руководитель хочет, чтобы я сделал это, - это MSWord 2010. Я знаю, что должен автоматизировать это с помощью автоматизации Python COM. Проблема только в том, что я не знаю, как и с чего начать. Я пробовал искать некоторые уроки, но не смог найти (возможно, может быть, но я не знаю, что я ищу).

Сейчас я читаю это. Не знаю, насколько это полезно.

4b9b3361

Ответ 1

Простой пример с использованием comtypes, преобразования одного файла, ввода и вывода имен файлов, заданных как аргументы командной строки:

import sys
import os
import comtypes.client

wdFormatPDF = 17

in_file = os.path.abspath(sys.argv[1])
out_file = os.path.abspath(sys.argv[2])

word = comtypes.client.CreateObject('Word.Application')
doc = word.Documents.Open(in_file)
doc.SaveAs(out_file, FileFormat=wdFormatPDF)
doc.Close()
word.Quit()

Вы также можете использовать pywin32, который будет таким же, за исключением:

import win32com.client

а затем:

word = win32com.client.Dispatch('Word.Application')

Ответ 2

Я работал над этой проблемой в течение полудня, поэтому я думаю, что должен поделиться некоторыми своими впечатлениями по этому вопросу. Ответ Стивена прав, но он провалится на моем компьютере. Здесь есть два ключевых момента:

(1). В первый раз, когда я создал объект Word.Application, я должен сделать это (текстовое приложение) видимым перед открытием любых документов. (На самом деле, даже я сам не могу объяснить, почему это работает. Если я не сделаю этого на своем компьютере, программа сработает, когда я попытаюсь открыть документ в невидимой модели, тогда объект "Word.Application" будет удален OS.)

(2). После выполнения (1) программа будет работать хорошо, но может часто не срабатывать. Ошибка сбоя "COMError: (-2147418111, 'Call was rejected by callee.', (None, None, None, 0, None))" означает, что сервер COM не может реагировать так быстро. Поэтому я добавляю задержку, прежде чем пытаюсь открыть документ.

После выполнения этих двух шагов программа будет работать без сбоев. Демо-код выглядит следующим образом. Если вы столкнулись с теми же проблемами, попробуйте выполнить эти два шага. Надеюсь, что это поможет.

    import os
    import comtypes.client
    import time


    wdFormatPDF = 17


    # absolute path is needed
    # be careful about the slash '\', use '\\' or '/' or raw string r"..."
    in_file=r'absolute path of input docx file 1'
    out_file=r'absolute path of output pdf file 1'

    in_file2=r'absolute path of input docx file 2'
    out_file2=r'absolute path of outputpdf file 2'

    # print out filenames
    print in_file
    print out_file
    print in_file2
    print out_file2


    # create COM object
    word = comtypes.client.CreateObject('Word.Application')
    # key point 1: make word visible before open a new document
    word.Visible = True
    # key point 2: wait for the COM Server to prepare well.
    time.sleep(3)

    # convert docx file 1 to pdf file 1
    doc=word.Documents.Open(in_file) # open docx file 1
    doc.SaveAs(out_file, FileFormat=wdFormatPDF) # conversion
    doc.Close() # close docx file 1
    word.Visible = False
    # convert docx file 2 to pdf file 2
    doc = word.Documents.Open(in_file2) # open docx file 2
    doc.SaveAs(out_file2, FileFormat=wdFormatPDF) # conversion
    doc.Close() # close docx file 2   
    word.Quit() # close Word Application 

Ответ 3

unoconv (writen in python) и openoffice работает как безгласный демона. http://dag.wiee.rs/home-made/unoconv/

работает очень хорошо для doc, docx, ppt, pptx, xls, xlsx. Очень полезно, если вам нужно конвертировать документы или сохранять/конвертировать в определенные форматы на сервере

Ответ 5

Стоит отметить, что ответ Стивенса работает, но убедитесь, что при использовании цикла for для экспорта нескольких файлов для размещения операторов ClientObject или Dispatch перед циклом - его нужно только создать - см. мою проблему: Python win32com.client.Dispatch зацикливание через документы Word и экспорт в PDF; завершается сбой при следующем цикле

Ответ 6

Я попробовал принятый ответ, но не особенно интересовался раздутыми PDF файлами, которые создавалось Word, которое обычно на порядок больше ожидаемого. Посмотрев, как отключить диалоги при использовании виртуального принтера PDF, я наткнулся на Bullzip PDF Printer, и меня впечатлили его особенности. Теперь он заменил другие виртуальные принтеры, которые я использовал ранее. На странице загрузки вы найдете "бесплатную версию сообщества".

COM API можно найти здесь и список доступных параметров можно найти здесь. Настройки записываются в файл "runonce", который используется только для одного задания печати, а затем автоматически удаляется. При печати нескольких PDF файлов нам нужно убедиться, что одно задание на печать завершено перед началом другого, чтобы убедиться, что настройки используются правильно для каждого файла.

import os, re, time, datetime, win32com.client

def print_to_Bullzip(file):
    util = win32com.client.Dispatch("Bullzip.PDFUtil")
    settings = win32com.client.Dispatch("Bullzip.PDFSettings")
    settings.PrinterName = util.DefaultPrinterName      # make sure we're controlling the right PDF printer

    outputFile = re.sub("\.[^.]+$", ".pdf", file)
    statusFile = re.sub("\.[^.]+$", ".status", file)

    settings.SetValue("Output", outputFile)
    settings.SetValue("ConfirmOverwrite", "no")
    settings.SetValue("ShowSaveAS", "never")
    settings.SetValue("ShowSettings", "never")
    settings.SetValue("ShowPDF", "no")
    settings.SetValue("ShowProgress", "no")
    settings.SetValue("ShowProgressFinished", "no")     # disable balloon tip
    settings.SetValue("StatusFile", statusFile)         # created after print job
    settings.WriteSettings(True)                        # write settings to the runonce.ini
    util.PrintFile(file, util.DefaultPrinterName)       # send to Bullzip virtual printer

    # wait until print job completes before continuing
    # otherwise settings for the next job may not be used
    timestamp = datetime.datetime.now()
    while( (datetime.datetime.now() - timestamp).seconds < 10):
        if os.path.exists(statusFile) and os.path.isfile(statusFile):
            error = util.ReadIniString(statusFile, "Status", "Errors", '')
            if error != "0":
                raise IOError("PDF was created with errors")
            os.remove(statusFile)
            return
        time.sleep(0.1)
    raise IOError("PDF creation timed out")

Ответ 7

Вы должны начать с изучения так называемых виртуальных драйверов печати PDF. Как только вы его найдете, вы сможете написать пакетный файл, который печатает ваши файлы DOC в файлы PDF. Вероятно, вы тоже можете это сделать на Python (установить драйвер принтера и вывести команду document/print в MSWord, позже можно выполнить с помощью командной строки AFAIR).

Ответ 8

В качестве альтернативы функции SaveAs вы также можете использовать ExportAsFixedFormat, который дает вам доступ к диалоговому окну параметров PDF, который вы обычно видите в Word. При этом вы можете указать закладки и другие свойства документа.

doc.ExportAsFixedFormat(OutputFileName=pdf_file,
    ExportFormat=17, #17 = PDF output, 18=XPS output
    OpenAfterExport=False,
    OptimizeFor=0,  #0=Print (higher res), 1=Screen (lower res)
    CreateBookmarks=1, #0=No bookmarks, 1=Heading bookmarks only, 2=bookmarks match word bookmarks
    DocStructureTags=True
    );

Полный список аргументов функции: "OutputFileName", "ExportFormat", "OpenAfterExport", "OptimizeFor", "Range", "From", "To", "Item", "IncludeDocProps", "KeepIRM", 'CreateBookmarks', 'DocStructureTags', 'BitmapMissingFonts', 'UseISO19005_1', 'FixedFormatExtClassPtr'

Ответ 9

Может ли кто-нибудь помочь преобразовать поток файлов .doc в поток файлов .pdf?

Ответ 10

Я бы предложил игнорировать своего супервизора и использовать OpenOffice, у которого есть api Python. OpenOffice построил поддержку Python, и кто-то создал библиотеку, предназначенную для этой цели (PyODConverter).

Если он не доволен выходом, скажите ему, что это может занять недели, чтобы сделать это со словом.