viewers
This commit is contained in:
@@ -11,9 +11,29 @@ from .base import ExtractionResult
|
||||
|
||||
MAX_SHEET_ROWS = 200
|
||||
|
||||
# Generic core-property titles Office writes by default — worse than useless as a
|
||||
# display title (they hide the real one), so we drop them and derive from content.
|
||||
PLACEHOLDER_TITLES = {
|
||||
"word document", "powerpoint presentation", "excel workbook",
|
||||
"microsoft word document", "microsoft powerpoint presentation",
|
||||
"microsoft excel worksheet", "presentation", "workbook", "document",
|
||||
}
|
||||
|
||||
|
||||
def _good_title(t) -> bool:
|
||||
return bool(t) and str(t).strip().lower() not in PLACEHOLDER_TITLES
|
||||
|
||||
|
||||
def _first_line(text: str, limit: int = 120) -> str:
|
||||
for ln in text.splitlines():
|
||||
s = ln.lstrip("#").strip()
|
||||
if s:
|
||||
return s[:limit]
|
||||
return ""
|
||||
|
||||
|
||||
def _core_props(props) -> dict:
|
||||
"""Common OOXML core properties → metadata (only non-empty ones).
|
||||
"""Common OOXML core properties → metadata (only non-empty, non-placeholder).
|
||||
|
||||
python-docx/pptx expose `.author`/`.last_modified_by`; openpyxl uses
|
||||
`.creator`/`.lastModifiedBy`. Each target checks both spellings.
|
||||
@@ -31,6 +51,8 @@ def _core_props(props) -> dict:
|
||||
for src in sources:
|
||||
val = getattr(props, src, None)
|
||||
if val:
|
||||
if dst == "title" and not _good_title(val):
|
||||
continue # skip "Word Document" & friends; derive from content
|
||||
out[dst] = str(val)
|
||||
break
|
||||
return out
|
||||
@@ -43,6 +65,10 @@ def _extract_docx(source: Path) -> ExtractionResult:
|
||||
content = "\n\n".join(p for p in paras if p.strip()) + "\n"
|
||||
metadata = _core_props(doc.core_properties)
|
||||
metadata["paragraphs"] = len([p for p in paras if p.strip()])
|
||||
if "title" not in metadata:
|
||||
t = _first_line(content)
|
||||
if t:
|
||||
metadata["title"] = t
|
||||
return ExtractionResult(content=content, metadata=metadata, extractor="office/python-docx@1")
|
||||
|
||||
|
||||
@@ -62,6 +88,12 @@ def _extract_pptx(source: Path) -> ExtractionResult:
|
||||
content = "\n\n".join(blocks) + "\n"
|
||||
metadata = _core_props(prs.core_properties)
|
||||
metadata["slides"] = len(prs.slides)
|
||||
if "title" not in metadata and prs.slides:
|
||||
# first slide's title placeholder, if any
|
||||
for shape in prs.slides[0].shapes:
|
||||
if shape.has_text_frame and shape.text_frame.text.strip():
|
||||
metadata["title"] = shape.text_frame.text.strip()[:120]
|
||||
break
|
||||
return ExtractionResult(content=content, metadata=metadata, extractor="office/python-pptx@1")
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user