pdf-inspector: bộ phân tích PDF viết bằng Rust
pdf-inspector là thư viện Rust phân loại PDF thành dạng văn bản, bản scan, dạng ảnh hoặc hỗn hợp, rồi trích xuất và chuyển các PDF dạng văn bản sang Markdown mà không cần OCR. Nên dùng nếu bạn đang xây pipeline xử lý tài liệu cần bỏ qua chi phí OCR cho những PDF đã có sẵn văn bản thật. Nên bỏ qua nếu phần lớn PDF của bạn là bản scan — pdf-inspector nhận diện đúng trường hợp này nhưng không trích xuất được từ đó.
Giới thiệu pdf-inspector
pdf-inspector là thư viện Rust do Firecrawl xây dựng, giúp phân biệt PDF dạng văn bản với PDF dạng scan hoặc dạng ảnh, rồi chuyển các trang dạng văn bản thành Markdown có cấu trúc — gồm tiêu đề, danh sách, bảng và liên kết. Công cụ đi kèm binding chính thức cho Python, Node.js và WebAssembly trên trình duyệt, cùng hai công cụ dòng lệnh là pdf2md và detect-pdf để xử lý nhanh từ terminal.
Các tính năng chính để phân tích PDF
- ✓Phân loại trong khoảng 10-50ms: lấy mẫu content stream để gắn nhãn PDF là TextBased, Scanned, ImageBased hay Mixed, kèm điểm tin cậy từ 0.0 đến 1.0 và định tuyến OCR theo từng trang.
- ✓Trích xuất văn bản có nhận biết vị trí, ghi lại thông tin font chữ và toạ độ X/Y cho từng đoạn văn bản.
- ✓Chuyển sang Markdown: dựng lại tiêu đề (H1-H4 dựa trên tỉ lệ cỡ chữ), danh sách gạch đầu dòng/đánh số/chữ cái, khối code (nhận diện font đều), bảng, định dạng đậm/nghiêng và liên kết URL.
- ✓Nhận diện bảng theo hai cơ chế: dựa trên hình chữ nhật từ các lệnh vẽ trong PDF, cộng với nhận diện theo kiểu căn chỉnh văn bản — xử lý được cả bảng tài chính lẫn bảng nối tiếp qua nhiều trang.
- ✓Hỗ trợ font CID: giải mã ToUnicode CMap cho font Type0/Identity-H, trên các bảng mã UTF-16BE, UTF-8 và Latin-1.
- ✓Nhận diện bố cục nhiều cột kiểu báo in, dựng lại thứ tự đọc và hỗ trợ văn bản RTL (viết từ phải sang trái).
- ✓Phát hiện lỗi encoding: tự động gắn cờ các font bị lỗi encoding để bên gọi biết mà chuyển sang OCR thay vì nhận về văn bản lỗi.
- ✓Chỉ tải tài liệu một lần rồi dùng chung cho cả bước phân loại lẫn trích xuất, nên xử lý cùng một file không bị đọc lại từ đầu.
Ứng dụng thực tế và định tuyến thông minh
- •Lọc trước trong pipeline nạp tài liệu: phân loại mọi PDF đầu vào, trích xuất cục bộ những file dạng văn bản, chỉ đẩy PDF dạng scan hoặc dạng ảnh sang dịch vụ OCR.
- •Chuyển báo cáo, bài nghiên cứu, hoá đơn và văn bản pháp lý thành Markdown sạch để lập chỉ mục tìm kiếm hoặc đưa vào context của LLM.
- •Dùng pages_needing_ocr để chỉ gửi đúng những trang thiếu văn bản của một PDF dạng Mixed sang OCR, thay vì gửi cả file.
- •Chạy cùng logic phân loại và chuyển đổi ngay trên trình duyệt qua bản WASM, cho các công cụ không thể gửi mọi PDF về backend.
Cài đặt trên nhiều nền tảng
Python: chạy pip install maturin rồi maturin develop --release để build binding PyO3 tại máy (phần Quick Start không nhắc tới wheel dựng sẵn). Node.js: chạy npm install @firecrawl/pdf-inspector để lấy binding napi-rs. Trình duyệt: chạy npm install @firecrawl/pdf-inspector-wasm để lấy bản WebAssembly. Rust: chạy cargo add pdf-inspector, hoặc thêm thủ công dòng pdf-inspector = "0.1" vào Cargo.toml, lấy từ crates.io. CLI: cargo install pdf-inspector cài hai binary pdf2md và detect-pdf; nếu chạy từ source checkout thì dùng cargo run --bin pdf2md -- document.pdf thay thế.
Ví dụ code để tích hợp
Trong Python, pdf_inspector.process_pdf("document.pdf") trả về một object có pdf_type (một trong "text_based", "scanned", "image_based", "mixed") và chuỗi markdown, giá trị None nếu không có gì để trích xuất. Trong Node.js, processPdf(readFileSync('document.pdf')) từ @firecrawl/pdf-inspector trả về pdfType tương đương (viết PascalCase: "TextBased", "Scanned", "ImageBased", "Mixed") cùng markdown. Bản WASM có API giống Node nhưng nhận vào Uint8Array do bạn tự fetch: gọi processPdf(pdf) sau khi await init(). Trong Rust, pdf_inspector::process_pdf("document.pdf")? trả về enum result.pdf_type và Option<String> ở result.markdown. CLI pdf2md bọc lại đúng logic đó cho dòng lệnh — pdf2md document.pdf --json xuất dữ liệu có cấu trúc để pipe đi, --select-pages 1,3,5-10 giới hạn theo trang, còn --compact rút gọn các dấu chấm nối dài (dot leader) để đầu ra tiết kiệm token hơn.
Điểm mạnh
- ✓Số liệu benchmark cho thấy pdf-inspector đạt 0.875 điểm tổng trên bộ 200 PDF opendataloader-bench với thời gian chạy trung vị 0.470s, trong khi pymupdf4llm chỉ đạt 0.735/17.117s và markitdown đạt 0.589/16.165s — chênh lệch thật sự, không phải sai số nhỏ, khi cả năm engine được chấm cùng cách và tắt OCR.
- ✓Các con số định tuyến trong README — khoảng 20ms để phân loại một PDF, khoảng 150ms để trích xuất cục bộ một PDF dạng TextBased, so với 2-10 giây cho dịch vụ OCR — giúp ước tính khá dễ pipeline tiết kiệm được bao nhiêu khi thêm bước này.
- ✓Thuần Rust, chỉ phụ thuộc vào lopdf, không dùng model machine learning nào — không phải lo license mô hình hay hạ tầng GPU, và bản WASM chạy đúng cùng bộ phân tích đó ngay trên trình duyệt.
- ✓Giấy phép MIT, nên không phải lo ràng buộc copyleft khi nhúng vào pipeline mã nguồn đóng.
Giới hạn phạm vi của pdf-inspector
- △Không tự làm OCR — pdf-inspector phát hiện trang dạng scan hoặc dạng ảnh và liệt kê trang nào cần OCR, nhưng việc trích xuất văn bản từ đó phải giao cho một dịch vụ khác.
- △Binding Python, theo phần Quick Start, được build tại máy bằng maturin develop --release chứ không cài từ wheel dựng sẵn.
- △Benchmark trong README so sánh pdf-inspector với bốn engine khác trên một bộ 200 PDF, tắt OCR — không nói gì về độ tin cậy phân loại với các PDF được tạo bởi công cụ bất thường hoặc lỗi ngoài bộ dữ liệu đó.
- △Việc chuyển sang Markdown dựa vào tỉ lệ cỡ chữ và tên font (Bold, Italic, Courier...) để suy ra cấu trúc, nên PDF không mã hoá rõ các tín hiệu đó sẽ cho ra Markdown phẳng hơn.
So sánh với các trình phân tích PDF khác
Câu hỏi thường gặp
pdf-inspector chia PDF thành bốn nhóm — TextBased, Scanned, ImageBased hoặc Mixed — bằng cách lấy mẫu các toán tử văn bản và hình ảnh trong content stream, đồng thời trả về điểm tin cậy từ 0.0 đến 1.0 kèm kết quả.
pdf-inspector không tự chạy OCR. Nó chỉ gắn cờ các trang dạng scan hoặc dạng ảnh, kể cả danh sách pages_needing_ocr cho PDF dạng Mixed, để bên gọi tự định tuyến đúng những trang đó sang một dịch vụ OCR riêng.
pdf-inspector viết bằng Rust và có binding chính thức cho Python (qua PyO3/maturin), Node.js (qua napi-rs) và WebAssembly trên trình duyệt, cộng thêm crate Rust trên crates.io và hai công cụ dòng lệnh pdf2md, detect-pdf.
pdf-inspector dựng lại tiêu đề từ tỉ lệ cỡ chữ, nhận diện danh sách gạch đầu dòng/đánh số/chữ cái và khối code theo font đều, định dạng bảng từ cả hình chữ nhật được vẽ lẫn văn bản căn chỉnh, rồi chuyển các mẫu font đậm/nghiêng và URL sang cú pháp Markdown.
pdf-inspector phát hành theo giấy phép MIT, nên bạn có thể nhúng vào pipeline thương mại hoặc mã nguồn đóng mà không vướng ràng buộc copyleft.
Benchmark trong README chạy pdf-inspector trên bộ 200 PDF với thời gian chạy trung vị 0.470s, còn ví dụ use case của chính dự án ước tính khoảng 20ms để phân loại và khoảng 150ms để trích xuất cục bộ một PDF dạng văn bản — số liệu ủng hộ việc dùng ở khối lượng lớn, dù đây là benchmark tự công bố chứ không phải đánh giá độc lập.
Vấn đề pdf-inspector giải quyết
Phần lớn pipeline xử lý tài liệu đối xử với mọi PDF đầu vào như nhau: đẩy hết qua OCR, kể cả khi PDF đã có sẵn văn bản chọn được từ trình soạn thảo hay bản xuất LaTeX. README ước tính khoảng 54% PDF — tức phần lớn — không cần OCR chút nào, nhưng vẫn bị đẩy qua vì thiếu một bước nhanh, chạy cục bộ, ít phụ thuộc, để phân biệt PDF dạng văn bản với bản scan trước khi tới dịch vụ OCR.
Nên dùng khi nào — và nên bỏ qua khi nào
Nên dùng pdf-inspector nếu bạn đang xây pipeline nạp tài liệu bằng Rust, Python hoặc Node.js, nhận vào cả PDF thật lẫn bản scan, và muốn bỏ chi phí OCR cho những file đã có sẵn văn bản — riêng bước phân loại, chỉ mất khoảng 10-50ms mỗi file, đã đủ bù lại chi phí khi khối lượng đủ lớn. Nên bỏ qua nếu toàn bộ PDF bạn xử lý đều là bản scan hoặc dạng ảnh ngay từ đầu: pdf-inspector vẫn nhận diện đúng trường hợp này, nhưng việc OCR thật sự lại giao cho công cụ khác, nên bạn chỉ thêm một bước không trích xuất được gì.
Repo liên quan
Chưa chắc pdf-inspector có hợp với bạn?
Để ChatGPT, Claude hoặc Perplexity tìm hiểu giúp — bấm bên dưới và xem AI nói gì về pdf-inspector.
