> ## Documentation Index
> Fetch the complete documentation index at: https://docs.anyformat.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Parse-only workflow

> Turn a document into markdown and layout blocks on the Flash, Fast, Standard or Agentic tier, with no extraction

A parse-only workflow is one [Parse](/guides/nodes/parse) node and no edges. It returns the document as markdown plus one block per region, each with a position and a confidence, and it runs no extraction. Use it to preview a document before you write fields, to feed your own model or search index, or to see how a document reads.

<div className="af-payoff">
  <div className="af-payoff-pane">
    <div className="af-payoff-cap">The document</div>
    <div className="af-payoff-line"><b>INVOICE</b></div>

    <div className="af-payoff-line">
      <span className="af-mark">
        {'Invoice #: INV-2026-9001'}
      </span>
    </div>

    <div className="af-payoff-line">
      {'Issue date: 2026-02-20'}
    </div>

    <div className="af-payoff-line">
      {'Description · Qty'}
    </div>

    <div className="af-payoff-line">
      <span className="af-mark">
        {'Matrix Extensible Action-Items · 8'}
      </span>
    </div>
  </div>

  <div className="af-payoff-arrow">→</div>

  <div className="af-payoff-pane">
    <div className="af-payoff-cap">What comes back</div>
    <div className="af-payoff-line"><span className="af-payoff-key">markdown</span><b>{'# INVOICE …'}</b></div>
    <div className="af-payoff-line"><span className="af-payoff-key">parse\_conf</span><b>{'89.1'}</b></div>
    <div className="af-payoff-line"><span className="af-payoff-key">p1\_b0</span><b>{'title · # INVOICE'}</b></div>
    <div className="af-payoff-line"><span className="af-payoff-key">p1\_b5</span><b>{'table · rows as a grid'}</b></div>
    <div className="af-payoff-line"><span className="af-payoff-key">extractions</span><b>{'[]'}</b></div>

    <div className="af-payoff-line">
      <span className="af-cite">
        {'↳ every block carries a page, a bbox and a confidence'}
      </span>
    </div>
  </div>
</div>

<div className="af-cost">
  <span><b>Nodes</b><strong>Parse</strong></span>
  <span><b>Credits</b><strong>25 per page</strong>{' (Parse, standard tier; 7 Flash, 12 Fast, 100 Agentic)'}</span>
  <span><b>You get</b>{' markdown, plain text and one block per region'}</span>
</div>

<Tip>
  To parse one document on the Fast tier without creating a workflow, call [`POST /v3/parse/`](/api-reference-v3/parse/parse) (or [`POST /v3/parse/from-url/`](/api-reference-v3/parse/parse-from-url)) with the file. It runs against a parse workflow that anyformat keeps for your organization and returns a run you poll like any other.
</Tip>

## The graph

<CodeGroup>
  ```json Graph theme={null}
  {
    "name": "Document parser",
    "nodes": [{ "id": "parse_1", "type": "parse", "mode": "standard" }],
    "edges": []
  }
  ```

  ```python Python theme={null}
  import os
  from anyformat.sdk import Client

  client = Client(api_key=os.environ["ANYFORMAT_API_KEY"])

  workflow = client.workflow("Document parser").parse(mode="standard").create()
  ```

  ```typescript TypeScript theme={null}
  import { Anyformat } from "@anyformat/sdk";

  const af = new Anyformat({ apiKey: process.env.ANYFORMAT_API_KEY! });

  const workflow = await af.workflow("Document parser").parse({ mode: "standard" }).create();
  ```
</CodeGroup>

`mode` selects the tier. Nothing else in the graph changes.

## Pick a tier

Each row is what came back for the same one-page invoice.

| Tier | `mode` | What runs | What you get back |
| - | - | - | - |
| **Flash** | `flash` | The PDF's own text layer plus layout grounding. No model call. A page without a text layer is OCR'd (`scanned_pages`). | Plain text per block, tables as markdown pipe tables, `parse_confidence` of 100 on a born-digital PDF. Done in about 12 s. |
| **Fast** | `lite` | One OCR pass, no LLM correction. | One block per text line, tables as bare HTML `<table>`, `parse_confidence` and `layout_confidence` are `null`. Done in about 14 s. |
| **Standard** | `standard` | Page-by-page parsing with reading-order correction. The default. | Merged blocks with headings marked, HTML tables with a `data-cell-id` per cell, `parse_confidence` of 89. Done in about 28 s. |
| **Agentic** | `agentic` | Adaptive, multi-step parsing that works hardest on dense tables. `effort` sets the preset. | The Standard shape, with the most work spent on tables. Done in about 37 s. See [Agentic parse to markdown](/examples/agentic-parse-to-markdown). |

Start on Standard. Move a document type down to Fast or Flash when its output holds up, and up to Agentic only where Standard falls short. The [Parse node](/guides/nodes/parse) page lists the credits per page for each tier.

## Run and read

<CodeGroup>
  ```bash curl theme={null}
  # Upload one file and start a run
  curl -X POST "https://api.anyformat.ai/v3/workflows/$WORKFLOW_ID/upload/run/" \
    -H "Authorization: Bearer $ANYFORMAT_API_KEY" \
    -F 'files=@document.pdf'
  # -> 202 {"run_id": "...", "document_packet_id": "...", "status": "queued"}

  # Read the run. Repeat until "status" is "processed".
  curl "https://api.anyformat.ai/v3/runs/$RUN_ID/" \
    -H "Authorization: Bearer $ANYFORMAT_API_KEY"
  ```

  ```python Python theme={null}
  result = workflow.run("document.pdf").wait()

  print(result.parse.parse_confidence)
  print(result.parse.markdown[:500])
  for block in result.parse.blocks:
      print(block.id, block.type, block.page, block.parse_confidence)
  ```

  ```typescript TypeScript theme={null}
  import { readFile } from "node:fs/promises";

  const file = new File([await readFile("document.pdf")], "document.pdf", { type: "application/pdf" });
  const run = await workflow.run(file);
  const result = await run.wait();

  console.log(result.parse?.parseConfidence);
  console.log(result.parse?.markdown?.slice(0, 500));
  for (const block of result.parse?.blocks ?? []) {
    console.log(block.id, block.type, block.page, block.parse_confidence);
  }
  ```
</CodeGroup>

## What comes back

The Standard tier on a one-page invoice, trimmed to the two blocks worth looking at. `classifications`, `splits`, `extractions` and `edits` are all empty, because only Parse ran.

```json Response highlight={8,9} theme={null}
{
  "results": {
    "parse": {
      "markdown": "…",
      "text": "INVOICE\nInvoice #: INV-2026-9001 …",
      "parse_confidence": 89.1,
      "blocks": [
        { "id": "p1_b0", "type": "title", "page": 1, "parse_confidence": 100.0, "layout_confidence": 0.846, "content": "# INVOICE", "bbox": { "x0": 0.115, "y0": 0.066, "x1": 0.269, "y1": 0.096 } },
        { "id": "p1_b5", "type": "table", "page": 1, "parse_confidence": 85.9, "rows": [[{ "cell_id": "r0c0", "text": "Description" }, { "cell_id": "r0c1", "text": "Qty" }]] }
      ]
    }
  }
}
```

[Runs and results](/concepts/runs-and-results) has the full envelope, section by section.

* Each `<a id="p1_b0">` anchor in `markdown` names the block with the same `id` in `blocks`. That is how you map a passage back to its `bbox` (page fractions, 0 to 1) and its confidences: `parse_confidence` is 0 to 100, `layout_confidence` is 0 to 1.
* A `table` block also carries `rows`, the cells as a grid, so you do not have to parse the HTML.
* Block ids carry the page: `p2_b0` is the first block on page 2. Every page is parsed.

## When it goes wrong

**Your confidence gate never fires.** The Fast tier makes no model call, so `parse_confidence` and `layout_confidence` come back `null`. A gate written as "below 80" never trips on a `null`. Read the tier before you read the number, or stay on Standard, where the number is real.

**A scanned page comes back as text you did not expect.** Flash reads the PDF's own text layer. A page with no words in that layer is OCR'd instead, silently, because `scanned_pages` defaults to `ocr`. Set it to `skip` to serve that page blank and flagged, or to `fail` to raise an error naming the page numbers.

**A table arrives with no addressable cells.** Fast returns bare HTML `<table>` and one block per text line. Standard merges the blocks, marks headings, gives every cell a `data-cell-id`, and fills `rows` with the cells as a grid. Move the node to Standard when you need to point at a cell.

**You fixed the source file and got the old parse back.** Parse caches per file, tier and settings, and a hit skips the parse and its cost. Set `"cache": false` on the node to force a fresh parse of the same file.

**You are about to create a second parse-only workflow.** Nothing in a Parse node depends on the kind of document, so one workflow reads them all. Create another only when a document type needs a different `mode`.

## Next steps

<CardGroup cols={2}>
  <Card title="Parse node" icon="file-lines" href="/guides/nodes/parse">
    Every knob on the node, and the credits per tier
  </Card>

  <Card title="Agentic parse to markdown" icon="wand-magic-sparkles" href="/examples/agentic-parse-to-markdown">
    The Agentic tier and its effort presets
  </Card>

  <Card title="Get run" icon="reply" href="/api-reference-v3/runs/get">
    The full run envelope
  </Card>

  <Card title="Quickstart" icon="route" href="/guides/quickstart">
    Add an Extract node and get fields back
  </Card>
</CardGroup>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.