Skip to main content
DoneThat

AI Adoption GuideConsultingAnalyze

Unstructured Document Extraction Pipeline

LLM extracts structured data tables and metrics from client PDFs, contracts, and legacy reports at scale.

Consulting processSellScopeStaffKickoffAnalyzeRecommendDeliverClose

By Don, DoneThat’s AI coach · updated

Extraction returns candidates, not certified figures

The pipeline's job is a table an analyst can query. Each row is a candidate metric with a period, a value, a unit, a source file, a page trace, and confidence per field. Speed comes from not retyping years of board packs. Credibility comes from never treating those rows as signed numbers.

Client work often starts with monthly packs, a contract PDF, and legacy reports that never lived in a system of record. Someone still has to rebuild revenue by segment, headcount, and working capital as a time series. Dumping the corpus through a model and pasting the first grid into a deck is how a wrong cell becomes a slide.

A high-confidence total does not make the period label trustworthy. Document-level confidence is a weak gate: one sure header can hide a scrambled nested block.

Products in this class, including Azure Document Intelligence, AWS Textract, Google Document AI, Unstructured.io, and ABBYY, read pages and emit text, tables, and key-value pairs. They are capture tools. They do not know which figure belongs on a slide, and they do not know the engagement's data-handling terms. The same capture idea shows up in accounts payable as invoice data extraction. There the downstream control is matching. Here it is an analyst who will put a number on a deliverable.

Store output that analysts can actually check:

  • the label as printed, plus a normalized metric name you control
  • period and grain (month, quarter, full year, year-to-date)
  • value and unit
  • source file and page
  • confidence on the value, and separate confidence on the period and the label
  • a review status: accepted, queued, or corrected

Low-confidence fields go to review. They do not enter the working dataset.

The year-to-date tile that reads as full-year revenue

Picture a commercial due diligence on a mid-market industrial. The data room drops several years of monthly board packs. Early years are native slide exports. Later years are scans of printed packs, because the CEO annotates on paper. Each cover is a scorecard: a large Revenue tile, a margin tile, a working-capital tile. Two slides later sits a nested P&L: segments as rows, months as columns, a sub-block for "of which export", and a footnote that restates the year on a different basis.

An analyst needs a monthly revenue series for the multi-scenario outcome modeler. The extractor reads the cover first. The tile is labeled Revenue, the type is large, and confidence on the value is high. The tile does not say the figure is year-to-date through period nine. The full-year figure is in the nested table. If the pipeline stores the tile as full-year revenue, later months look like a collapse, or the run-rate is nine months treated as twelve.

That is a labeling miss with a confident value, not an exotic character error. The page trace is what makes it recoverable: the cell points at the cover, not at the P&L. An analyst who opens that page sees a tile with no grain. An analyst who never opens the page puts the wrong year into the case. Flattened, the nested "of which" block looks like extra periods or extra segments, and mix shares get added to totals.

Rehearse this before you scale. Pick packs you already know, extract them, and compare the table to the pages. If the cover tile and the P&L disagree in the output, your schema is not capturing period grain. Do not turn that rehearsal into a claimed accuracy rate.

Nested tables and scanned packs fail in different ways

Native files fail on structure. Scans fail on characters, then on structure.

Nested tables, indented subtotals, and multi-column slides still break extraction often enough that you should plan for it. A working-capital bridge with a nested aging block will shift columns. A contract schedule whose header repeats every page will duplicate rows. A two-column board memo will attach a percentage in the left column to a label in the right. When the layout is a slide, not a form, table recovery is a parse, not a readout.

Scanned board packs add a second failure layer. OCR confuses commas and periods in thousands separators. A faint thousand becomes a decimal. Handwritten margin notes next to a printed cell get promoted into the table. Stamps become extra rows. Skew and low contrast usually drop confidence, which is safer than a native PDF with a wrong period label, as long as low confidence still means a human opens the file.

Contracts fail on defined terms versus schedules: the definition of Net Sales in section 1 is not the amount in the fee schedule. Extracting every number without binding it to the defined term produces metric soup. Legacy reports fail when the "table" is a screenshot inside a Word file. There is no grid to recover, only an image of one.

If you extract fee tables and scope exhibits from prior proposals, that structured table is what a comparable past scope retriever can search. Another PDF dump is not.

None of this is a reason to skip extraction. It is a reason to keep per-field confidence, keep the page trace, and refuse to auto-accept nested or scanned regions until a reviewer has seen a sample from that layout family.

Keep the data room inside the allowed processing boundary

Check the data-handling terms before any client document leaves your environment. Engagement letters, data-room rules, and sector rules often prohibit sending files through an external API, even when a vendor says content is not used for training. External includes a public chatbot, an unapproved OCR endpoint, and a personal workspace with a document model turned on.

If the terms require in-tenant or on-premises processing, the pipeline has to run there. The product names above are a class of layout and OCR tools. Some deployments stay inside a boundary you control. Others are public cloud APIs. The logo does not make the path compliant. The path does.

Do not paste a board pack into a browser assistant to get a table out. That is still processing. If a file cannot go out, it cannot go out for a sample either. Run the sample in the same environment you will use for the corpus.

Classify files before they enter the pipeline: allowed for approved extraction, allowed only inside the controlled boundary, or not to be machine-processed. Privileged memos, personnel files, and anything marked do-not-copy should not ride along with the monthly financial packs because they were in the same zip.

Sample the corpus, then verify every figure that will be shown

Do not run the full data room on day one. Take a stratified sample: native versus scanned, each year, each recurring pack type (monthly board, audit pack, contract, operations report). An analyst who knows the files scores value, period, unit, and label, then records disagreements. That disagreement rate is the error rate for this corpus and this schema, not a vendor score.

If the sample is messy, stop. Fix labels, period grain, and nested-table rules. Put those layouts on review. Sample again. Only then run the rest.

Route the full run on field confidence, not on a document score. High confidence on value, period, and label can land in the working table with the page trace intact. If any of those three is low, queue the row with the original page, the extracted values, and the scores visible. Nested-table regions and scanned pages default to review until that layout family has passed the sample.

Verify every figure that will appear in a client deliverable, whatever the confidence. A wrong number in a client deck is a credibility event. The pipeline's speed is for the cells that never get shown. The cells that get shown need a human who opened the source page. Confirm grain, unit, and whether a subtotal was stored as a total. Write corrections back into the table so the next query does not revive the error.

Once the working table is trusted enough for analysis, it can sit in a warehouse or a shared grid. Context around a surprising series belongs in the agentic research and synthesis agent. Cite extracts by page, not by memory. If a model run depends on an extracted driver the client never confirmed, the assumption gap detector should surface that gap before the number hardens into a recommendation.

Is this worth automating for you?

Whether this pays back depends on how much time it takes your team today. Most teams estimate that from memory, and the estimate is usually wrong in one direction or the other.

DoneThat reconstructs where the time actually went, with no timers to forget, so you can measure the baseline before committing to a project and check the gain afterward.

Measure the baseline first