Quickstart
The fastest way to see the Pagr API in action is to get a key, POST some JSON to an existing template, and get a PDF back.
Don’t have a Pagr account yet? See Create an account first. You will need a workspace and at least one template before the steps below will produce anything.
1. Get an API key
Section titled “1. Get an API key”Generate a test key in the workspace under Settings → API Keys — test keys produce watermarked output and don’t consume page credits, so they’re safe to experiment with. See API Keys for the full walkthrough.
2. Render a document
Section titled “2. Render a document”You need a template’s id (open the template in the workspace and copy it from the URL or the template list). Then call the render endpoint with your key and some data — raw HTTP, or with one of the official SDKs:
curl -X POST "https://pagr-prd-api-public.azurewebsites.net/v1/render/8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90" \ -H "Authorization: Bearer pagr_test_xxxxxxxxxxxxxxxx" \ -H "Content-Type: application/json" \ -d '{ "documents": [ { "Title": "Acme Q3 Invoice", "Amount": 42 } ], "includeDocument": true }'import asynciofrom pagr import PagrApiClient
async def main(): async with PagrApiClient("pagr_test_xxxxxxxxxxxxxxxx") as client: result = await client.render( "8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90", json_data={"Title": "Acme Q3 Invoice", "Amount": 42}, include_document=True, ) if result.ok: result.document.save("out/") else: if result.insufficient_credit: print("Out of credit:", result.message) for issue in result.issues: print(issue)
asyncio.run(main())import { PagrApiClient } from 'pagr';
const client = new PagrApiClient('pagr_test_xxxxxxxxxxxxxxxx');
const result = await client.render( '8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90', { Title: 'Acme Q3 Invoice', Amount: 42 }, { includeDocument: true },);
if (result.ok) { await result.document!.save('./out');} else { console.log(result.status, result.issues);}import org.example.PagrApiClient;import org.example.RenderOptions;import org.example.models.RenderResult;import java.nio.file.Path;import java.util.UUID;
try (PagrApiClient client = new PagrApiClient("pagr_test_xxxxxxxxxxxxxxxx")) {
RenderResult result = client.render( UUID.fromString("8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90"), "{\"Title\": \"Acme Q3 Invoice\", \"Amount\": 42}", RenderOptions.builder().includeDocument(true).build());
if (result.isOk()) { result.getDocument().save(Path.of("out")); } else { for (var issue : result.getIssues()) System.out.println(issue); }}using Pagr.Sdk;
using var client = new PagrApiClient("pagr_test_xxxxxxxxxxxxxxxx");
var result = await client.RenderAsync( Guid.Parse("8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90"), new { Title = "Acme Q3 Invoice", Amount = 42 }, includeDocument: true);
if (result.Ok) await result.Document!.SaveAsync(@"C:\out");else foreach (var issue in result.Issues) Console.WriteLine(issue);require "pagr"
client = Pagr::Client.new("pagr_test_xxxxxxxxxxxxxxxx")
result = client.render( "8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90", { "Title" => "Acme Q3 Invoice", "Amount" => 42 }, include_document: true,)
if result.ok? result.document.save("out/#{result.document.document_name}.pdf")else result.issues.each { |issue| warn issue }end#include "pagr/PagrApiClient.hpp"
pagr::PagrApiClient client("pagr_test_xxxxxxxxxxxxxxxx");
auto result = client.render( std::string("8bec66ff-6f3d-4c1e-9a2b-1f0e5d7c4a90"), R"({"Title": "Acme Q3 Invoice", "Amount": 42})", {.include_document = true});
if (result.ok() && result.document->has_content()) result.document->save("out/" + result.document->document_name + ".pdf");else for (auto& issue : result.issues) { /* handle */ }3. What you get back
Section titled “3. What you get back”A JSON envelope reporting the outcome, with the rendered document’s metadata — and,
because includeDocument was true, the PDF itself as Base64:
{ "status": "ok", "requestedCount": 1, "renderedCount": 1, "missingCount": 0, "issues": [], "documents": [ { "documentName": "Acme Q3 Invoice", "pageCount": 1, "viewUrl": "https://…", "documentBase64": "JVBERi0xLjcK…" } ]}Inspect status rather than the HTTP status code — a document that fails validation is
a normal outcome, not a request error. See
Render a document → Response for
every field.
Next steps
Section titled “Next steps”- Render and save a PDF — the same call step by step, with the
persistandversionvariations. - Choose a rendering shape — single vs. batch vs. async vs. stateless.
- Validate before rendering — catch data problems without spending a credit.
- Handle errors and retries — what raises, what doesn’t, and what the SDKs retry.
- API Overview — base URL, rendering shapes, limits, and errors in full.
- Authentication — test vs. production keys, and the two auth-related error codes.
- SDKs — official client libraries for six languages.
