Skip to content

Migration von python-docx

Office Oxide ist ein Drop-in-Ersatz für die häufigsten python-docx-Use-Cases — Textextraktion, Absatziteration, Tabellen-Lesen, Find-and-Replace — bei 14× Geschwindigkeit und 3,8 Prozentpunkten höherer Pass-Rate auf einem 2.538-DOCX-Korpus. Bonus: du musst nicht mehr verschiedene Libraries für .xlsx (openpyxl), .pptx (python-pptx) und Legacy .doc (catdoc / antiword) vendor-en — ein pip install deckt alle sechs Formate ab.

Wann migrieren

Wechsle, wenn du eines davon machst:

  • Text oder Markdown aus .docx für Ingestion / RAG / Suche extrahieren
  • Find-and-Replace-Templates über tausende Dokumente jagen
  • Tabellen aus Verträgen oder Reports lesen
  • Auch .xlsx, .pptx oder Legacy-Formate verarbeiten wollen, ohne weitere Abhängigkeiten

Bleib bei python-docx, wenn du das tust und nicht in die formatspezifische Rust-API absteigen willst:

  • Komplexe DOCX von Grund auf mit Custom-Styles und Themes bauen
  • python-docx-Erweiterungs-Libraries brauchst (z. B. docxcompose, python-docx-ng)

Installation

pip uninstall python-docx
pip install office-oxide

Der Distributionsname auf PyPI ist office-oxide (mit Bindestrich); der Import ist office_oxide (mit Underscore).

Side-by-side-Cheatsheet

Reiner Text

python-docx

from docx import Document

doc = Document("report.docx")
text = "\n".join(p.text for p in doc.paragraphs)

office_oxide

from office_oxide import Document

with Document.open("report.docx") as doc:
    text = doc.plain_text()

Ein einziger Methodenaufruf, inklusive Kopf- und Fußzeilen, ~14× schneller.

Markdown / HTML

python-docx — kein eingebautes Markdown / HTML; du müsstest auf pandoc, mammoth zurückgreifen oder einen eigenen Converter schreiben.

office_oxide

from office_oxide import Document

with Document.open("report.docx") as doc:
    md   = doc.to_markdown()
    html = doc.to_html()

Absätze iterieren

python-docx

from docx import Document

doc = Document("report.docx")
for p in doc.paragraphs:
    print(p.style.name, p.text)

office_oxide (über IR)

from office_oxide import Document

with Document.open("report.docx") as doc:
    ir = doc.to_ir()

for section in ir["sections"]:
    for el in section["elements"]:
        if el["kind"] == "Heading":
            print(f"H{el['level']}", el["text"])
        elif el["kind"] == "Paragraph":
            print("P", " ".join(r["text"] for r in el["runs"]))

Tabellen iterieren

python-docx

from docx import Document

doc = Document("report.docx")
for table in doc.tables:
    for row in table.rows:
        cells = [cell.text for cell in row.cells]
        print(cells)

office_oxide

from office_oxide import Document

with Document.open("report.docx") as doc:
    ir = doc.to_ir()

for section in ir["sections"]:
    for el in section["elements"]:
        if el["kind"] == "Table":
            for row in el["rows"]:
                print(row)

Find and replace (Templating)

python-docx — keine First-Class-API; das übliche Muster ist, jedes Run zu durchlaufen und Text umzuschreiben, was bei Cross-Run-Matches bricht. Die meisten greifen zu docx-mailmerge oder schreiben fragile Regex.

office_oxide

from office_oxide import EditableDocument

with EditableDocument.open("template.docx") as ed:
    n = ed.replace_text("{{client_name}}", "Acme Corp")
    print(f"{n} Ersetzungen")
    ed.save("filled.docx")

replace_text behandelt Cross-Run-Matches transparent und bewahrt alle unveränderten OPC-Teile (Bilder, Diagramme, Stile).

Core-Properties lesen

python-docx

from docx import Document

doc = Document("report.docx")
print(doc.core_properties.author)
print(doc.core_properties.modified)

office_oxide

from office_oxide import Document

with Document.open("report.docx") as doc:
    props = doc.as_docx().core_properties()
    print(props.author)
    print(props.modified)

Was office_oxide aktuell nicht exponiert

Das einheitliche EditableDocument deckt den Templating-Use-Case ab. Für reichere DOCX-Konstruktion — Absätze hinzufügen, Tabellen programmatisch bauen, benannte Stile anwenden — geh in das formatspezifische Modul:

from office_oxide.docx import DocxBuilder

builder = DocxBuilder()
builder.add_heading("Q4-Bericht", level=1)
builder.add_paragraph("Umsatz wuchs um 18 %.")
builder.save("report.docx")

Oder generiere aus der IR mit create_from_ir(ir, "docx", "report.docx"). Siehe Aus IR bauen.

Performance

Gleicher 2.538-Datei-Korpus, single-thread:

Library Mittelwert p99 Pass-Rate
office_oxide 0,8 ms 3,9 ms 98,9 %
python-docx 11,8 ms 98 ms 95,1 %

Eine Million-Dokument-Ingestion, die mit python-docx 3 h 16 min dauert, läuft mit office_oxide auf derselben Hardware in 14 Minuten durch.

Siehe auch