Melhor maneira de extrair texto de um documento do Word sem usar COM/automação?
Pergunta
Existe uma maneira razoável de extrair texto simples de um arquivo do Word que não depende da automação COM?(Este é um recurso para um aplicativo Web implantado em uma plataforma não Windows - isso não é negociável neste caso.)
O Antiword parece ser uma opção razoável, mas parece que pode ser abandonado.
Uma solução Python seria ideal, mas não parece estar disponível.
Solução
Eu uso catdoc ou antiword para isso, o que der o resultado mais fácil de analisar.Eu incorporei isso em funções python, por isso é fácil de usar no sistema de análise (que está escrito em python).
import os
def doc_to_text_catdoc(filename):
(fi, fo, fe) = os.popen3('catdoc -w "%s"' % filename)
fi.close()
retval = fo.read()
erroroutput = fe.read()
fo.close()
fe.close()
if not erroroutput:
return retval
else:
raise OSError("Executing the command caused an error: %s" % erroroutput)
# similar doc_to_text_antiword()
A opção -w para catdoc desativa a quebra de linha, aliás.
Outras dicas
(Mesma resposta que extraindo texto de arquivos MS Word em python)
Use o módulo docx nativo do Python que fiz esta semana.Veja como extrair todo o texto de um documento:
document = opendocx('Hello world.docx')
# This location is where most document content lives
docbody = document.xpath('/w:document/w:body', namespaces=wordnamespaces)[0]
# Extract all text
print getdocumenttext(document)
Ver Site Python DocX
100% Python, sem COM, sem .net, sem Java, sem análise de XML serializado com regexs, sem porcaria.
Se tudo o que você deseja fazer é extrair texto de arquivos Word (.docx), só é possível fazer isso com Python.Como Guy Starbuck escreveu, você só precisa descompactar o arquivo e analisar o XML.Inspirado por python-docx
, eu escrevi um função simples para fazer isso:
try:
from xml.etree.cElementTree import XML
except ImportError:
from xml.etree.ElementTree import XML
import zipfile
"""
Module that extract text from MS XML Word document (.docx).
(Inspired by python-docx <https://github.com/mikemaccana/python-docx>)
"""
WORD_NAMESPACE = '{http://schemas.openxmlformats.org/wordprocessingml/2006/main}'
PARA = WORD_NAMESPACE + 'p'
TEXT = WORD_NAMESPACE + 't'
def get_docx_text(path):
"""
Take the path of a docx file as argument, return the text in unicode.
"""
document = zipfile.ZipFile(path)
xml_content = document.read('word/document.xml')
document.close()
tree = XML(xml_content)
paragraphs = []
for paragraph in tree.getiterator(PARA):
texts = [node.text
for node in paragraph.getiterator(TEXT)
if node.text]
if texts:
paragraphs.append(''.join(texts))
return '\n\n'.join(paragraphs)
Usando a API OpenOffice e Python, e Excelente livro macro online de Andrew Pitonyak Eu consegui fazer isso.A Seção 7.16.4 é o lugar para começar.
Outra dica para fazer funcionar sem precisar da tela é usar a propriedade Hidden:
RO = PropertyValue('ReadOnly', 0, True, 0)
Hidden = PropertyValue('Hidden', 0, True, 0)
xDoc = desktop.loadComponentFromURL( docpath,"_blank", 0, (RO, Hidden,) )
Caso contrário, o documento aparecerá na tela (provavelmente no console do servidor web) quando você o abrir.
O Open Office tem um API
Para arquivos docx, verifique o script Python docx2txt disponível em
http://cobweb.ecn.purdue.edu/~kak/distMisc/docx2txt
para extrair o texto simples de um documento docx.
tika-python
Uma porta Python da biblioteca Apache Tika. De acordo com a documentação, o Apache tika suporta extração de texto de mais de 1.500 formatos de arquivo.
Observação: Também funciona encantadoramente com pyinstaller
Instale com pip:
pip install tika
Amostra:
#!/usr/bin/env python
from tika import parser
parsed = parser.from_file('/path/to/file')
print(parsed["metadata"]) #To get the meta data of the file
print(parsed["content"]) # To get the content of the file
Link para oficial GitHub
Isso funcionou bem para .doc e .odt.
Ele chama o openoffice na linha de comando para converter seu arquivo em texto, que você pode simplesmente carregar em python.
(Parece ter outras opções de formato, embora não estejam aparentemente documentadas.)