Original research

We Generated 108 Resume PDFs to Find What Breaks Text Extraction

Original research on ATS resume format: 12 formatting patterns tested across 108 resume PDFs, measuring what survives text extraction and what does not.

By ATSPrep Editorial · July 31, 2026 · 12 min read

Resume advice is full of confident claims about what breaks an applicant tracking system, and almost none of it is measured. So we measured it. We built a corpus of resume PDFs where every formatting variable is controlled and the intended text is known exactly, read all of them back with the same PDF engine our X-ray uses, and scored what came out. The headline result surprised us: your words almost always survive. It is your reading order that does not.

The short version

  • Only one condition destroyed a resume outright, and it was the scanned image: 0% of text recovered.
  • Side-by-side layout kept 97.9% of the words while fusing 30.5% of output lines out of unrelated content.
  • Several widely repeated formatting fears — tight line spacing, decorative bullets, rotated sidebars — did no measurable damage at all.
  • Word recovery is the wrong metric. A resume can return every word and still read as nonsense.

Why we ran this instead of repeating the advice

Search for resume formatting guidance and you will find the same list everywhere: avoid columns, avoid tables, avoid headers, avoid fancy bullets, avoid tight spacing. The list is repeated with total confidence and almost never with evidence. Some of it is right. Some of it, as far as we can measure, is not.

The problem is that you cannot learn much from a pile of real resumes. If you collect a thousand files and some extract badly, you know that they failed but not why, because every one of them differs in a dozen ways at once. Layout, font, spacing, bullet style and export tool all vary together, so nothing can be isolated.

So we inverted it. We generate the documents ourselves. That gives us two things a collected corpus cannot: the intended text is known exactly, so recovery can be scored against ground truth rather than eyeballed, and exactly one property changes between conditions, so any difference in the result is attributable to that property.

PDF fileText items+ coordinatesGrouped intolinesFieldsFormatting decides stage three. Everything downstream inherits the result.
A resume passes through four stages before anything reads it as fields. Formatting decides stage three, where positioned fragments are grouped back into lines, and every later stage inherits whatever happens there.

How the corpus was built

We wrote 9 complete resumes covering different fields — backend engineering, nursing, marketing, data analysis, teaching, product, accounting, customer success and quality assurance — each with real sentence structure, contact details, two roles with dated bullet points, a skills list and an education line.

Each resume was then rendered 12 times, once per formatting condition, using the pdf-lib library to place text at exact coordinates. That produces 108 documents that differ only in the property under test. The single-column version is the control.

Every file was then read back with PDF.js and reassembled into lines using the same grouping rules our X-ray ships: fragments within 2.5 points of vertical distance belong to the same line, and a space is inserted between two fragments when the horizontal gap exceeds roughly a fifth of the character height. This matters, because the reassembly step is where most damage actually happens.

  • Layout conditions: single column, two columns, two columns with a narrow gutter, a table grid, contact details in the page margins, tight leading, and a rotated sidebar.
  • Text-construction conditions: letter-spaced headings, whole documents drawn one glyph at a time, text with no space characters at all, symbol-font bullets, and a scanned page with no text layer.
  • Scored on four axes: word recovery, reading-order fidelity, line welding, and whether contact details survived intact.
Keep in mind

The corpus is synthetic. We generated all 108 files rather than collecting real applicant resumes, because a collected corpus can only show that a file failed, never which property caused it. Generating them means one variable moves at a time and the intended text is known exactly. It also means no one's personal data is involved.

Finding one: almost everything returns almost all of its words

Eleven of the 12 conditions returned at least 96.9% of the text we wrote. Two-column layouts returned 97.9%. Table grids returned 97.6%. A document containing no space characters whatsoever returned 99.8%.

Exactly one condition failed completely. The scanned page — a resume saved as an image, with no text layer behind it — returned 0% of its words, 0% of its email addresses and none of its structure. There is nothing to extract, so nothing is extracted.

If you take one thing from this study, take that asymmetry. The gap between a scanned resume and every other mistake in this corpus is not a matter of degree. It is the difference between a damaged document and no document at all.

  • Single column (control)100%
  • Decorative bullets100%
  • Contact in margins100%
  • No space characters99.8%
  • Two columns97.9%
  • Table grid97.6%
  • Letter-spaced headings96.9%
  • Scanned image0%
Word recovery by condition, averaged across 9 resumes each. The scanned page is not a worse version of the others; it is a different category of failure.

Finding two: word recovery is a misleading measure

The two-column resume recovered 97.9% of its words, which sounds like a pass. Then we looked at the lines it actually produced, and the number stopped meaning what it appears to mean.

Here is real output from the two-column condition, unedited. The words are nearly all present. They have simply been reassembled into sentences that were never written.

Order fidelity catches what recovery misses. Measured as the longest run of words still in their intended sequence, the two-column layout scored 83.6% against 100% for the control. That gap is the sound of two columns being read as one.

  1. 01Jordan Rivera EXPERIENCE
  2. 02Senior Backend Engineer Senior Backend Engineer, Northwind Systems
  3. 03jordan.rivera@example.com 2022 - Present
  4. 04555-0142 - Migrated 47 services from virtual machines to Kubernetes across three
  5. 05Austin, TX
  6. 06regions.
  7. 07SKILLS - Cut median checkout latency from 840ms to 210ms by reshaping the
  8. 08Go pricing query.
Verbatim extraction from the two-column condition. Highlighted lines were fused from two unrelated parts of the page: a phone number welded to a job achievement, and a section heading welded to a bullet from a different section.

Finding three: the damage has a shape, and it is measurable

That output suggested a metric none of the standard ones capture. We call it line welding: the share of output lines that were fused from two unrelated parts of the source document.

It is measured without judgement calls. We take only the words that appear exactly once in the entire resume, so each one maps unambiguously to a single source line. If one output line draws such words from two different source lines, the reader has fused content that was never adjacent.

The result isolates the problem cleanly. Line welding is 0% in nine of the twelve conditions. It is non-zero in exactly three, and all three are the same underlying mistake: content sitting side by side across the page.

Keep in mind

Narrowing the gutter made it worse, from 30.5% to 33.1%. The less horizontal space between your columns, the more confidently a reader treats them as one line.

  • Two columns, narrow gutter33.1%
  • Two columns30.5%
  • Table grid24.1%
  • All eight other conditions0%
Share of output lines fused from unrelated source content. Every condition not shown scored zero. Side-by-side layout is the only thing in this study that causes it.
SIDEBARMAIN COLUMNOne sweep, two unrelated fragments, one line of output.
Why it happens. A reader groups text by vertical position, so a horizontal sweep across a two-column page collects one fragment from the sidebar and one from the body and emits them as a single line.

Finding four: tables are the same disease, in a milder form

Table grids welded 24.1% of their lines, meaningfully less than two-column layouts, and the welds were less harmful in kind. A table row places related cells beside each other, so when they fuse you tend to get "2022 - Present Senior Backend Engineer, Northwind Systems" — clumsy, but the date and the job it belongs to are still together and still legible.

That is a different outcome from a sidebar weld, where a phone number lands in the middle of a bullet about Kubernetes. Table grids also scored the highest reading-order fidelity of any multi-region layout at 93.4%.

So the honest version of the advice is narrower than the usual one. The risk is not tables as such. It is placing unrelated content side by side. A table used to align a date with the job on the same row is a much smaller problem than a table used to build a full-height skills rail.

ConditionWordsOrderWelded
Single column100%100%0%
Table grid97.6%93.4%24.1%
Two columns97.9%83.6%30.5%
Two columns, narrow gutter97.9%83%33.1%
Multi-region layouts compared against the single-column control. Recovery barely moves; order and welding are where they separate.

Finding five: letter-spaced headings shred, and the body does not

The two letter-spacing conditions both scored 96.9% recovery, the lowest of any condition with a text layer. When we read the output, the loss was entirely in one place. The body text was perfect. The section headings came back as "E X P E R I E N C E", "S K I L L S" and "E D U C A T I O N".

The mechanism is precise, and the two conditions together prove it. One drew only the headings glyph by glyph with extra tracking; the other drew every line in the document glyph by glyph. Both scored 96.9%. If splitting text into individual glyphs were the problem, the second condition would have been far worse. It was not.

So the cause is not glyph splitting. It is the tracking. A reader decides whether two fragments are one word by measuring the gap between them against a threshold that scales with font size. Normal glyph spacing falls under it and the word holds together. Add letter-spacing and every gap crosses it, so each character becomes its own word.

Keep in mind

This matters more than the small recovery number suggests. Section headings are exactly what software uses to segment a resume into experience, skills and education. Losing the word EXPERIENCE is not losing one word.

NORMAL SPACINGSKILLSgaps under threshold — one wordWITH LETTER-SPACINGSKILLSevery gap crosses it — six wordsThe threshold scales with font size, so bigger headings tolerate less tracking.
The same heading with and without added tracking. The threshold scales with font size, which is why large letter-spaced headings are the most fragile text on a resume.

Finding six: several common warnings did nothing

Null results are worth publishing, especially when the advice they contradict is repeated as confidently as this advice is. Three conditions we expected to cause damage caused none that we could measure.

Tight leading, set at two points, scored 100% recovery and 100% order — identical to the control. The line-grouping tolerance is small enough that cramped spacing never merged two lines.

Symbol-font bullets scored 100% on every axis. We drew them from ZapfDingbats, where the filled circle is stored at the byte for the letter "l", which is exactly the trick Word plays with Wingdings. PDF.js resolved the encoding correctly and the bullets did not contaminate the text.

Documents with no space characters at all scored 99.8%. Every space in that condition was a gap in coordinates rather than a character, and the reader reconstructed word boundaries from geometry almost perfectly.

ConditionWordsOrderWelded
Tight leading (2pt)100%100%0%
Symbol-font bullets100%100%0%
Rotated sidebar100%100%0%
No space characters99.8%99.8%0%
Conditions that changed nothing measurable against the control. Where advice and measurement disagree here, we report the measurement.

Finding seven: some content survives but moves

Two conditions recovered everything while quietly changing where it sat. Contact details placed in the page margins scored 100% recovery but only 93.7% order fidelity, because a reader works down the page and margin content is not where the eye assumes it is. The email and phone number came back at the far end of the text, a long way from the name they belong to.

The rotated sidebar behaved similarly. It scored 100% on every axis, and the body text was untouched. The rotated skills themselves were recovered — but at the end of the document, in reverse order.

Neither is a catastrophe, and both are worth knowing. If software is looking for a phone number near a name, distance is not free.

What we would actually change on a resume

The measurements point at a much shorter list of priorities than the usual advice gives, and they are ordered by how much damage they actually cause.

  • Make sure the file has a text layer. This is the only failure in the study that loses everything. Open the PDF, select all, copy. If nothing is selectable, nothing downstream can read it.
  • Put the body in one column. Side-by-side content is the only structure here that fuses unrelated text, and it did so on roughly a third of lines.
  • If you keep a two-column design, widen the gutter. Narrow gutters measurably increased welding.
  • Do not letter-space your section headings. It is the one text effect that reliably shredded words, and it hits the headings that define your resume's structure.
  • Keep contact details in the body rather than the page margins, so they stay near your name in the extracted text.
  • Stop worrying about decorative bullets and tight line spacing. We could not measure any damage from either.
Keep in mind

One reader was tested: PDF.js, the same library the X-ray runs. Employer systems use other extractors and may differ. Findings describe how these formatting choices behave under extraction, not how any particular company screens.

Check our work

The corpus generator and the measurement script are both in the open-source repository behind this site, under scripts/research. Running them regenerates every number quoted on this page, and the numbers here are read from the generated data file rather than typed in, so the prose cannot drift away from the results.

The complete per-document dataset, with a row for each of the documents and every metric we scored, is published as JSON. Corrections are welcome, and so is disagreement, provided it comes with a measurement.

  • Corpus generator: scripts/research/corpus.mjs
  • Measurement and scoring: scripts/research/run-study.mjs
  • Full dataset: /research/extraction-study.json

Sources and further reading

Test the actual file

See what your resume gives back.

Drop your PDF in and ATSPrep reads it back with a real text extractor, so you see what a parser recovers from it. No account, no upload, and no opaque compatibility score.

Scan my resume

Keep reading

Related guides

All articles →