PDF Text Extraction Error Handling in the Hiring-Agent Repository

The PDFHandler.extract_text_from_pdf method in pdf.py implements a comprehensive try-except block that catches file system errors, PDF library failures, and conversion exceptions, logging each failure and returning None to prevent downstream crashes.

The interviewstreet/hiring-agent repository processes resume PDFs as part of its automated hiring pipeline, making robust PDF text extraction error handling critical to prevent malformed documents from breaking the entire workflow. The system adopts a defensive programming approach where every potential failure point is wrapped in exception handlers that return sentinel values rather than propagating crashes.

Core Error Handling in extract_text_from_pdf

The primary defense mechanism resides in the extract_text_from_pdf method within pdf.py (lines 47-65). This method orchestrates a multi-layered safety net that handles everything from missing files to corrupted binaries.

File Existence Validation

Before attempting to open any document, the code verifies the file path using os.path.exists(pdf_path). If the file is missing, the method deliberately raises a FileNotFoundError with a descriptive message. This exception is immediately caught by the surrounding try … except block, logged as an error via logger.error, and the method returns None to signal failure to calling functions.

PDF Opening and Reading Safeguards

The method opens valid files using pymupdf.open(pdf_path) inside a with context manager. Any exception thrown by the MuPDF library—whether from corrupted files, unsupported PDF formats, or permission issues—bubbles up to the outer except Exception as e clause. This captures library-specific crashes without exposing internal PyMuPDF stack traces to the rest of the application.

Markdown Conversion Protection

After successfully loading the document, the code calls to_markdown(doc, pages=pages) to convert PDF content to plain text. If this conversion step fails due to malformed page structures or memory issues, the exception follows the same path as other errors: it is trapped, logged with the specific exception details, and results in a None return value.

Structured Logging and Return Values

Successful extractions log the character count at the debug level, while failures trigger logger.error calls that record the exact exception object for troubleshooting. The method strictly returns None on any error path, creating a consistent sentinel pattern that higher-level code can detect immediately.

from pdf import PDFHandler

handler = PDFHandler()

# Example: Handling extraction failures gracefully

text = handler.extract_text_from_pdf("corrupted_resume.pdf")
if text:
    print(f"Extracted {len(text)} characters")
else:
    print("Extraction failed – see logs for details")

Downstream Safety Mechanisms

The repository implements additional validation layers beyond the initial extraction to ensure safe PDF text extraction throughout the pipeline.

extract_json_from_pdf Validation

The extract_json_from_pdf method (lines 200-207 in pdf.py) checks the text returned from extract_text_from_pdf. If the value is falsy (including None or empty strings), it logs an explicit error and aborts the JSON conversion step entirely. This prevents processing pipelines from attempting to parse garbage data or passing null values to language models.

Section-Level Extraction Guards

In _extract_all_sections_separately, the code iterates over individual resume sections. If any section extraction fails—for example, due to unparsable LLM responses—the method logs a warning and aborts the entire resume build, returning None. This atomic approach ensures that partial or incomplete resume data never propagates to downstream evaluation systems.


# Example: Missing file handling in the full pipeline

handler = PDFHandler()
result = handler.extract_json_from_pdf("nonexistent.pdf")

# Result is None; caller decides on retry or user notification

if result is None:
    print("Could not process PDF – check the error log.")

Summary

  • Early validation: os.path.exists checks prevent file system errors before they occur.
  • Comprehensive exception coverage: A single try … except block in extract_text_from_pdf catches FileNotFoundError, PyMuPDF crashes, and to_markdown failures.
  • Sentinel return pattern: Returning None on all error paths allows callers to implement their own recovery logic.
  • Pipeline protection: extract_json_from_pdf and _extract_all_sections_separately validate inputs before processing, preventing downstream crashes.
  • Audit trail: All failures are logged via logger.error with full exception details for debugging.

Frequently Asked Questions

What happens when a PDF file is missing in the Hiring-Agent system?

The extract_text_from_pdf method raises a FileNotFoundError which is immediately caught by the internal try-except block, logged as an error, and the method returns None. This prevents the application from crashing and allows the calling code to handle the missing file gracefully.

Does the error handling catch corrupted PDF files?

Yes. When pymupdf.open() encounters a corrupted or malformed PDF, it raises an exception that is caught by the outer except Exception clause in extract_text_from_pdf. The error is logged and the method returns None, preventing the corruption from affecting downstream processing.

How does the system prevent downstream crashes after extraction failures?

The extract_json_from_pdf method validates that extracted text is truthy before attempting JSON conversion. If extract_text_from_pdf returns None or an empty string, the pipeline aborts immediately with a logged error. Similarly, _extract_all_sections_separately aborts the entire resume build if any section fails, ensuring no partial data advances through the system.

What logging information is captured when PDF extraction fails?

All exceptions are logged using logger.error with the full exception object included, providing the exact error type and traceback. Successful extractions log character counts at the debug level. This creates a complete audit trail for troubleshooting Python PDF error handling issues in production environments.

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:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →