Templates

List templates and instantiate a locked one with field_values — the placeholder-filling API.

Templates are reusable contracts you author once and send many times. Instead of uploading a PDF + positions per request, you instantiate a locked template and supply the merge values.

List templates

GET /api/v1/templates
Authorization: Bearer lsk_live_…
{
  "templates": [
    {
      "id": "…", "name": "Mietvertrag", "status": "locked",
      "version": 3, "pages": 2, "content_kind": "richtext",
      "instantiable": true, "updated_at": "2026-06-20T…"
    }
  ]
}

Only status: "locked" templates (instantiable: true) can be instantiated — locking freezes the field_key set so your integration stays stable.

Instantiate

POST /api/v1/templates/{id}/instantiate
Authorization: Bearer lsk_live_…
Content-Type: application/json
{
  "recipients": [
    { "slot": 1, "email": "buyer@acme.ch", "name": "Sara Buyer" }
  ],
  "field_values": {
    "client_name": "Acme AG",
    "plan_tier": "Gold",                       // enum — validated
    "line_items": [                            // collection — array of rows
      { "description": "Design sprint", "qty": "1", "unit_price": "900.00", "amount": "900.00" }
    ]
  },
  "locale": "de",
  "signing_mode": "sequential"
}

field_values keys are the template's {{placeholders}} and positioned field_keys — the same namespace. See Fields & placeholders for the lead-vs-API split and collections. Discover the exact keys, types, enum options and limits with GET /api/v1/fields.

Validation

Values are checked against the workspace registry:

  • enum → must be one of the allowed options, else 400 { code: "invalid-enum", field, allowed }.
  • email / number / date → format-checked, else 400 { code: "invalid-email" | … }.
  • max length → values longer than a field's cap are abbreviated () to fit the space the template allocates.

The legacy path /api/templates/{id}/instantiate still works as a deprecated alias. New integrations should use the /api/v1/ path above.

Generate (no signature)

Need the filled PDF without a signing step — an invoice, an order confirmation, a letter? generate fills the template and returns the PDF bytes directly. No recipients, no signing request.

POST /api/v1/templates/{id}/generate
Authorization: Bearer lsk_live_…
Content-Type: application/json
{
  "field_values": {
    "client_name": "Acme AG",
    "line_items": [
      { "description": "Design sprint", "qty": "1", "unit_price": "900.00", "amount": "900.00" }
    ]
  },
  "filename": "invoice-1042.pdf"     // optional
}

Responds 200 with Content-Type: application/pdf (the document as an attachment). The template must be locked. field_values are validated and length-capped exactly like instantiate. This is the API behind the editor's “Generate via API” option; “Generate & sign via API” uses instantiate.