Every result set, one way to page it
Systems paginate in incompatible ways, some by page number, some by cursor, each with its own quirks. Maesn puts one limit and page parameter in front of all of them, and adds the filters that let you pull only what changed.








Provet










Provet


What is unified pagination and filtering
Normalizing the shape of the data is one problem. Controlling the shape of the result set is a separate one: which records come back, in what order, which ones are filtered out and how many arrive at a time. Two systems can return an identical invoice object and still disagree completely on how you walk through ten thousand of them.
Unified pagination and filtering is the layer that settles that. One paging scheme, one set of filter parameters and one way to order results, applied across every system, so the loop you write for the first integration is the loop that works for all of them. It sits alongside the common data model rather than inside it: the model settles what a record looks like, this settles which records you get.
Two paradigms, and a variant per system
Paging is not one problem with one solution. It is two incompatible models, each with per-system oddities on top, and you meet all of them the first time you try to read a full list.
You count and request numbered pages.
- 1Ask how many pages there are
- 2Request page 1, 2, 3 in a loop
- 3Stop one page early, the last errors
- 4Some return the max count in the URL
You follow a bookmark until it runs out.
- 1Ask for the first batch
- 2Read the cursor out of the response
- 3Send it back to get the next batch
- 4You never learn the total
Two incompatible paradigms, plus a variant per system. Build against them directly and every integration needs its own paging loop.
Two parameters, predictable results
You send limit and page. Maesn translates that into whatever the target system actually needs and hands back a consistent page of normalized records.
Accepts 5, 10, 20, 50 or 100, so a page size is always a valid, predictable number.
Starts at 1 and counts up, with no pre-query and no off-by-one at the end of the set.
One pagination everywhere
Page-based schemes, cursor bookmarks and their per-system variants all sit behind the same two query parameters.
Delta with lastModified
Pass the timestamp of your last fetch and receive only the objects that are new or changed since then.
Filters where they matter
Beyond lastModified there is status on invoices, plus filters built for a specific system's gaps, on the same unified endpoints.
Ordering you control
Order invoices, bills and booking proposals by date, number or created and updated timestamps, ascending or descending.
const res = await axios.get(url, {params: { limit: 50, page: 1 },headers: {'X-API-KEY': apiKey,'X-ACCOUNT-KEY': accountKey}});
Pull what changed, not everything again
The filter most integrations end up living on is lastModified. You store the timestamp of your last successful fetch, pass it on the next request, and receive only the objects that are new or changed since then. A nightly reconciliation over a customer's full ledger becomes a request that returns a handful of records.
It is built on nearly every schema and endpoint, which is what makes it usable as a general strategy rather than a special case. The practical rule that goes with it: poll at the lowest frequency that still keeps your data fresh enough. Polling every minute for something that changes once a day is wasted traffic and cost, and Maesn paces requests to each target system anyway through asynchronous processing. Where you need to react the moment something changes rather than on a schedule, unified webhooks push the event to you instead, and many integrations run both: webhooks for immediacy, a periodic delta poll as the safety net.
Illustrative. Grey objects were already in your database.
You get the two objects that are new or changed since your timestamp, not the whole ledger again.
Filters built for what each system lacks
Some filters exist across the board, others exist because one system has a gap worth closing. Both live on the same unified endpoints, so using them costs you no per-system code.
sevdesk
·ContactsSearch contacts by their contact number, covering both customers and suppliers in the same filter.
sevdesk integrationLexware Office
·ContactsFilter contacts by name or by email address, so you can match a record you already hold.
Lexware Office integrationSage Active
·InvoicesSage Active has no paid or partially paid state in its regular invoice status, so payment status is its own filter.
Sage Active integrationBuchhaltungsButler
·BillsReturn only bills whose bill date falls after the value you pass, filtered in the request itself.
BuchhaltungsButler integrationNot every resource supports all three of filtering, ordering and pagination, and Maesn does not claim otherwise. The capability has to exist somewhere underneath, so support is documented per endpoint in the API reference. You can see what a given endpoint offers before you build against it, which is the honest version of a unified layer: consistent where consistency is possible, transparent about the edges.
One loop, every system
- Write a paging loop per system
- Handle cursors and page counts
- Work around the failing last page
- Re-pull everything to find changes
- One limit and page everywhere
- Cursors and counts handled for you
- No off-by-one to work around
- Pull only what changed since
Reading a full list sounds like the simplest thing an integration does, and it is where a surprising amount of time disappears: a paging loop per system, a workaround for the page that errors, and a full re-read every night because there is no reliable way to ask what changed. Because you page and filter through Maesn rather than against each system, that work happens once. The same two parameters and the same delta filter carry over to every integration you add, including the ones Maesn adds after you have shipped, and the customer connects once for all of it.
Common questions
Build once on the Unified API.
See how unified pagination and filtering works for your integration, or dive into the technical reference.