Skip to content

Core Concepts

Learn about the conceptual foundations of Press. Read once, refer back when stuck.

Press is a document language built around a few central concepts. Once you've understood them, you should be able to pick up the rest from the guides and reference as you go.

Documents and Pages

In a given template, <document> wraps a sequence of pages. Pages can be defined directly within <document> or else defined in the separate <pages> section and referred to within <document>. Pages have absolute dimensions — they're physical like pieces of paper and not like the infinite scroll of web pages.

xml
<press>
  <document format="a4" page-margin="2cm">
    <page>
      <p>First page.</p>
    </page>
    <page>
      <p>Second page.</p>
    </page>
  </document>
</press>

Frames

Frames are the Press layout primitive. They hold content and arrange it, vertically by default and horizontally with direction="row". Pages are special frames. They follow a box model similar to CSS, but they're far simpler: there is usually just one way of doing anything in Press.

xml
<frame direction="row">
  <frame width="50%">
    <p>Left column</p>
  </frame>
  <frame width="50%">
    <p>Right column</p>
  </frame>
</frame>

Flows

Flows separate content and layout. A flow is a named stream of content separate from the template that "paints" it. This is one of the key differences between Press and HTML, and enables templates to be powerful reusable assets.

xml
<press>
  <document>
    <page format="a4" page-margin="2cm">
      <flow name="body" />
    </page>
  </document>
  <flows>
    <body>
      <h1>The template references the flow.</h1>
      <p>The flow holds the content.</p>
    </body>
  </flows>
</press>

The same flow can be rendered through a different template — a one-column page, a two-column layout, or a multi-page document — without changing the content.

Templates and Payloads

A template is a Press document with named flows and/or data use. A payload is written in the same language — you just provide the "missing" parts of the document and they're merged into the template.

shell
curl -X POST "https://api.papermill.io/v2/pdf?template_id=tpl_invoice" \
  -H "X-API-Key: $PAPERMILL_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "data": {
      "customer": "Acme Ltd",
      "amount": 1250.00,
      "items": [
        { "description": "Consulting", "qty": 10, "rate": 125 }
      ]
    }
  }' \
  -o invoice.pdf

The template tpl_invoice is stored in your account and reused across requests. Each request supplies a different payload.

Data

Templates can reference data using {{ data.name }} expressions. You can inject data into the document, but also use it in conditionals, repeats, and lookups. Templates are functions over data, so one template can adapt to many different payloads. Data can be provided in JSON, XML, and CSV format.

Here's an example where data is referenced in a template. This will be swapped with new data when calling our API:

xml
<press>
  <document>
    <page format="a4" page-margin="2cm">
      <flow name="body" />
    </page>
  </document>
  <flows>
    <body>
      <h1>Invoice for {{ customer }}</h1>
      <p>Amount due: £{{ amount }}</p>
    </body>
  </flows>
  <data type="json">
    {
      "customer": "Acme Ltd",
      "amount": 1250.00
    }
  </data>
</press>

What's Next?