comments: PDF/DOCX text extraction pipeline #253
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Objective
Extract full text from comment attachments.
Tasks
data/cms/comments/{docket_id}/extracted/Key insight from hti5
70%+ of substantive comments are in attachments, not inline text. Initial analysis using only inline text misses the real content.
FYI: download-side throughput improvement landed in
22cbc74— attachments are now fetched concurrently from the CDN (4 workers, no per-request sleep). They stream into.state/comments/{docket_id}/{comment_id}/and are ready for extraction. Backfill is at ~62% across the 56K-comment corpus; by the time the extraction pipeline kicks off, the attachment store should be substantially complete.Phase 1 complete — landed in 6 commits on main.
What shipped
src/rex/comments/—extract.py(PyMuPDF + python-docx + cheap HTML strip + image→ocr_needed routing),combine.py(atomic writer forcombined.mdwith YAML frontmatter),walker.py(parallelThreadPoolExecutor),view.py(DuckDB view over_index.csv)stack comments {extract, extract-ocr, stats}CLILive smoke run on CMS-2024-0256 (smallest docket)
Full docket processed in 3.3 seconds at 8 workers. Idempotent re-run is a no-op.
Notes
.jpg/.png/.tif/.tiff/.gif/.bmp) auto-route toocr_neededso phase-2 can pick them up.combined.mdwrites are atomic (.tmp+os.replace) — safe under the planned distributed-GPU phase-2 fan-out.extract-ocris a stub that exits 2 with a clear message — phase-2 work tracked in spec.Phase-2 (deferred)
Will use marker (GPU-accelerated PDF→markdown) instead of tesseract. ~1.8K OCR-needed comments across the 56K corpus → ~3-5 hr on a single 4090, vs multi-day on CPU.
Ready for #254/#255
Public API:
body_path(),parse_combined(),comments_indexDuckDB view. Downstream classifiers can consume directly.Commits:
d82bc48skeleton+PDF,b2ad400DOCX+combine,1f60f8cwalker+view,da831c0CLI+integration,7281012review fixes (cross-thread sqlite + atomic writes + image classification + index freshness).Shipped. The extraction pipeline lives in
src/rex/comments/with thestack commentsCLI (extract / extract-ocr / stats — https://git.fhirworx.io/homelab/stack/commit/da831c0 refs this issue):extract.py)stack comments extract-ocr)combined.mdper comment with YAML frontmatter recording each attachment's extraction status; resumable (combine.py)data/cms/comments/{docket}/extracted/to bib/Zotero: per-attachment.mdsiblings (https://git.fhirworx.io/homelab/stack/commit/684a8740, https://git.fhirworx.io/homelab/stack/commit/fafe661) andcombined.mdas a Zotero note (https://git.fhirworx.io/homelab/stack/commit/2f6e2d4), which is where the corpus is actually consumed.Ran at scale: every regulations.gov comment item in Zotero carries the combined extracted text (see #416, which builds on this).