How to Get Detailed PDF Analysis with JSON Output from detect-pdf
Use the --json flag to emit structured detection results, and add --analyze to include layout metadata such as tables and columns in the JSON output.
The detect-pdf CLI tool in the firecrawl/pdf-inspector repository provides a fast, programmatic way to classify PDF documents and extract structural metadata. By combining specific command-line flags, you can generate deterministic JSON reports that detail page types, OCR requirements, and complex layout features without writing custom parsing code.
Understanding the detect-pdf CLI Architecture
The detect-pdf binary, defined in src/bin/detect_pdf.rs, serves as a lightweight wrapper around the core inspection library. It exposes two primary operational modes that determine the depth of analysis performed before serialization.
When you invoke the tool without flags, it runs run_detect_only (lines 29-43 in src/bin/detect_pdf.rs), which calls detect_pdf_type() to return a DetectionResult containing basic classification data. Adding the --analyze flag triggers run_analyze (lines 45-64), which executes process_pdf_with_options() with ProcessMode::Analyze to perform full layout extraction including table and column detection.
Generating Basic JSON Output
To receive a compact JSON summary instead of the default human-readable report, append the --json flag to your command. This flag instructs the binary to manually construct the response using internal helper functions like json_escape and format_ocr_reasons_by_page rather than relying on external serialization libraries.
detect-pdf my-document.pdf --json
Typical output structure:
{
"pdf_type":"scanned",
"page_count":12,
"pages_sampled":5,
"pages_with_text":0,
"confidence":0.95,
"title":"My PDF Title",
"ocr_recommended":true,
"pages_needing_ocr":[1,2,3,4,5,6,7,8,9,10,11,12],
"ocr_reasons_by_page":[
{"page":1,"reasons":["no extractable text"]},
{"page":2,"reasons":["low text density"]}
],
"detection_time_ms":84
}
The ocr_reasons_by_page array is formatted by the format_ocr_reasons_by_page helper (lines 29-43), which safely escapes strings to ensure valid JSON output.
Enabling Detailed Layout Analysis
For applications requiring structural metadata—such as identifying tabular data or multi-column layouts—combine the --json and --analyze flags. This configuration runs the full extraction pipeline via process_pdf_with_options() before reporting, populating additional fields in the JSON output.
detect-pdf my-document.pdf --json --analyze
Extended output includes layout-specific fields:
{
"pdf_type":"mixed",
"page_count":30,
"pages_needing_ocr":[7,14,21],
"ocr_reasons_by_page":[
{"page":7,"reasons":["image‑only region"]},
{"page":14,"reasons":["low text density"]},
{"page":21,"reasons":["mixed content"]}
],
"is_complex":true,
"pages_with_tables":[5,12,19],
"pages_with_columns":[3,8,15],
"detection_time_ms":212
}
According to the source code in src/bin/detect_pdf.rs (lines 45-64), the --analyze flag invokes run_analyze(), which calls process_pdf_with_options(pdf_path, PdfOptions::new().mode(ProcessMode::Analyze)) to extract the pages_with_tables and pages_with_columns vectors from the ProcessResult structure.
Understanding the JSON Schema
Basic Detection Fields
The core DetectionResult struct—returned by detect_pdf_type() in src/detector.rs—serializes the following fields to JSON:
- pdf_type: Classification as "scanned", "text", or "mixed"
- confidence: Float value between 0.0 and 1.0 indicating detection certainty
- pages_needing_ocr: Array of page numbers requiring optical character recognition
- ocr_reasons_by_page: Per-page explanations for OCR recommendations
- title: Extracted document metadata (when available)
Extended Analysis Fields
When --analyze is specified, the tool augments the base detection with data from the ProcessResult structure:
- is_complex: Boolean indicating multi-column or intricate layouts
- pages_with_tables: Array of page indices containing tabular structures (detected via logic in
src/tables/) - pages_with_columns: Array of page indices with columnar text layouts
- detection_time_ms: Total processing time including layout analysis
Using the Rust API for Custom Workflows
While the CLI provides convenient JSON serialization, you can access the same detection and analysis capabilities programmatically through the library interface defined in src/lib.rs.
use pdf_inspector::{detect_pdf_type, process_pdf_with_options, PdfOptions, ProcessMode};
fn main() -> Result<(), pdf_inspector::PdfError> {
// Simple detection
let det = detect_pdf_type("my-document.pdf")?;
println!("Detected type: {}", det.pdf_type);
// Full analysis
let res = process_pdf_with_options(
"my-document.pdf",
PdfOptions::new().mode(ProcessMode::Analyze),
)?;
println!("Layout is complex? {}", res.layout.is_complex);
Ok(())
}
The PdfOptions and ProcessMode enums, defined in src/process_mode.rs, control which extraction stages execute. Setting mode(ProcessMode::Analyze) activates the same pipeline used by the CLI's --analyze flag.
Summary
- Use
--jsonto output machine-readable detection results instead of formatted text reports - Add
--analyzeto include layout metadata like tables and columns in the JSON output - The CLI manually constructs JSON strings to avoid external serializer dependencies, ensuring deterministic output
- Underlying functionality relies on
detect_pdf_type()for basic classification andprocess_pdf_with_options()for full layout analysis - Key source files include
src/bin/detect_pdf.rs(CLI logic),src/detector.rs(core detection), andsrc/process_mode.rs(analysis configuration)
Frequently Asked Questions
What is the difference between basic detection and full analysis in detect-pdf?
Basic detection, triggered without flags or with only --json, executes detect_pdf_type() to classify the PDF and determine OCR requirements. Full analysis, enabled by --analyze, runs process_pdf_with_options() with ProcessMode::Analyze to extract structural elements like tables and columns, adding these fields to the JSON output.
How does detect-pdf handle JSON serialization without external dependencies?
The tool constructs JSON output manually through helper functions json_escape, format_ocr_reasons_by_page, and format_detector_ocr_reasons within src/bin/detect_pdf.rs. This approach keeps the binary lightweight and ensures consistent, deterministic formatting without pulling in full-fledged serialization libraries.
Can I use detect-pdf programmatically outside of the CLI?
Yes. The firecrawl/pdf-inspector library exposes public APIs in src/lib.rs including detect_pdf_type() and process_pdf_with_options(). You can import the crate into your Rust application and configure analysis options using PdfOptions::new().mode(ProcessMode::Analyze) to replicate CLI behavior programmatically.
What determines if a page needs OCR according to the detector?
The detection logic in src/detector.rs evaluates text density, extractability, and content type. Pages are flagged for OCR if they contain no extractable text, exhibit low text density, or contain image-only regions. The ocr_reasons_by_page field in the JSON output provides specific justification for each flagged page.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →