PDF Generator API
Intro image

How SaaS Businesses Can Deliver Custom PDF Experiences Without Building Complex Data Transformations

When SaaS companies add document generation to their product, one of the first challenges they face is data structure mismatch.

Customer orders, product details, or nested JSON often don’t look the way you’d want them to appear in a polished PDF.

But here’s the important part: you don’t want to (and often can’t) change your source data just to make PDFs work as expected. Your APIs, databases, and integrations should stay as they are.

Traditionally, developers solve this by writing custom transformation scripts before sending data into a document engine. But that approach comes with hidden costs:

  1. Extra development time
  2. More API complexity
  3. Maintenance overhead whenever your data changes

This is where PDF Generator API’s Data settings come in. Instead of rewriting or restructuring your source JSON, you can sort, filter, and transform it directly in the editor or via the API. Your original dataset remains untouched — but your PDFs get exactly the structure they need.

Why This Matters for SaaS Products

For SaaS businesses, customer expectations are high. Users don’t just want any PDF — they expect documents that feel custom-tailored to their workflows. That could mean:

  1. Business reports that highlight only the most relevant records
  2. Invoices or statements ordered in a clear, logical sequence
  3. Documents enriched with additional calculated fields or metadata
  4. Repeated outputs generated automatically from a single data point (like labels, tickets, or badges)

If your development team has to code every one of these cases, it slows you down and increases maintenance overhead.

With Data settings, your non-technical team members and even end users can prepare data for templates visually, while developers can define the same rules programmatically via the API. And if you’re building templates programmatically, developers can define the same rules directly via the API.

Where Do You Control This?

All of these options — sorting, filtering, and transforming your JSON — are available in two ways, depending on how you build your templates.

In the editor

Open your template, then go to File → Data settings. Here you’ll find three tabs: Sort by, Filter by, and Transformation. This is the easiest way for your team to set up logic without touching the backend.

Via API

If you’re creating templates programmatically, the same settings can be defined in the dataSettings object when you call the API. This gives you full control to configure data preparation as part of your automated template creation process.

"dataSettings": {
  "sortBy": [],
  "filterBy": [],
  "transform": []
}

Sorting and Filtering Data

Imagine you’re building a PDF report from a dataset of orders. By default, all orders would appear in the PDF, but you only want to highlight completed orders, and show them from newest to oldest.

What we want to achieve:

  • Only include orders with status = Completed
  • Sort them by order_date descending

This makes your PDF clear and focused, showing only the most relevant records, without modifying your original dataset.

Input JSON

[
    {
        "order_id": "1001",
        "customer": "Alice Johnson",
        "status": "Completed",
        "order_date": "2025-09-14",
        "total": 129.99
    },
    {
        "order_id": "1003",
        "customer": "Bob Smith",
        "status": "Pending",
        "order_date": "2025-09-20",
        "total": 59.5
    },
    {
        "order_id": "1002",
        "customer": "Charlie Davis",
        "status": "Completed",
        "order_date": "2025-09-18",
        "total": 249
    },
    {
        "order_id": "1005",
        "customer": "Diana Evans",
        "status": "Completed",
        "order_date": "2025-09-22",
        "total": 179.75
    },
    {
        "order_id": "1004",
        "customer": "Ethan Ford",
        "status": "Canceled",
        "order_date": "2025-09-21",
        "total": 89.99
    }
]

Resulting JSON used in PDF:

[
    {
        "order_id": "1005",
        "customer": "Diana Evans",
        "status": "Completed",
        "order_date": "2025-09-22",
        "total": 179.75
    },
    {
        "order_id": "1002",
        "customer": "Charlie Davis",
        "status": "Completed",
        "order_date": "2025-09-18",
        "total": 249
    },
    {
        "order_id": "1001",
        "customer": "Alice Johnson",
        "status": "Completed",
        "order_date": "2025-09-14",
        "total": 129.99
    }
]

Data Transformation

Sometimes sorting and filtering isn’t enough. You may want to add new fields or expand arrays to better fit your PDF layout. Here are two practical examples.

Creating a combined field

Suppose your data contains separate first_name and last_name, but you want a full_name field to use across your template.

Transformation applied:

  • New field: full_name
  • Expression: {first_name}~” “~{last_name}

Now, full_name can be reused wherever needed in your template, avoiding repetitive expressions.

Input JSON

{
  "first_name": "Alice",
  "last_name": "Johnson"
}

Output JSON

{
  "first_name": "Alice",
  "last_name": "Johnson",
  "full_name": "Alice Johnson"
}

Expanding array items for repeated outputs

If an order includes multiple units of the same item, you may want to generate one label per unit.

Transformation applied:

  • New array: custom_array
  • Expression: flatten(map({production_order::materials},’iterate(1..reference[_key][“quantity”], “reference”, reference[_key])’,{production_order::materials}))

This allows your PDF to generate one row, label, or barcode per unit, without modifying the original dataset.

Input JSON

{
    "production_order": {
        "order_id": "PO-202",
        "warehouse": "Berlin Factory",
        "materials": [
            {
                "item": {
                    "name": "Wood Panel",
                    "sku": "WD-11"
                },
                "quantity": 2
            },
            {
                "item": {
                    "name": "Metal Leg",
                    "sku": "ML-45"
                },
                "quantity": 4
            },
            {
                "item": {
                    "name": "Varnish",
                    "sku": "VR-07"
                },
                "quantity": 1
            }
        ]
    }
}

Output JSON

{
    "production_order": {
        "order_id": "PO-202",
        "warehouse": "Berlin Factory",
        "materials": [
            {
                "item": {
                    "name": "Wood Panel",
                    "sku": "WD-11"
                },
                "quantity": 2
            },
            {
                "item": {
                    "name": "Metal Leg",
                    "sku": "ML-45"
                },
                "quantity": 4
            },
            {
                "item": {
                    "name": "Varnish",
                    "sku": "VR-07"
                },
                "quantity": 1
            }
        ]
    },
    "custom_array": [
        {
            "item": {
                "name": "Wood Panel",
                "sku": "WD-11"
            },
            "quantity": 2
        },
        {
            "item": {
                "name": "Wood Panel",
                "sku": "WD-11"
            },
            "quantity": 2
        },
        {
            "item": {
                "name": "Metal Leg",
                "sku": "ML-45"
            },
            "quantity": 4
        },
        {
            "item": {
                "name": "Metal Leg",
                "sku": "ML-45"
            },
            "quantity": 4
        },
        {
            "item": {
                "name": "Metal Leg",
                "sku": "ML-45"
            },
            "quantity": 4
        },
        {
            "item": {
                "name": "Metal Leg",
                "sku": "ML-45"
            },
            "quantity": 4
        },
        {
            "item": {
                "name": "Varnish",
                "sku": "VR-07"
            },
            "quantity": 1
        }
    ]
}

The Business Value

For SaaS businesses, the benefits are clear and can give an competitive advantage over competitors.

  • Faster iteration — product and design teams can adjust documents without engineering bottlenecks
  • Lower maintenance — no fragile data-prep scripts living in your codebase
  • Consistent results — data is transformed once at the data level and reused across documents
  • Happier users — customers get exactly the PDFs they expect, formatted the way they want

Conclusion

Delivering custom PDF experiences doesn’t have to mean building a mini ETL pipeline inside your SaaS. With PDF Generator API’s Sort, Filter, and Transformation features, you can handle complex JSON datasets directly in the editor or define them programmatically via the API. That means less engineering effort, faster go-to-market, and documents that adapt perfectly to your users’ needs.

👉 Ready to try it? Start a free trial and see how easy it is to transform your data into professional PDFs.

Interested in Document Automation?

Meet Michal Liska. He is our pre-sales engineer and operations manager. He is the best person to help you achieve your goals and answer any questions you might have.

Book a meeting with Michal ›

Michal Liska