Cashback Platform for Dondino
Dondino promises a simple process: shop through the platform, get part of it back. Behind it are transaction reports from a range of affiliate networks, each with its own format and its own status model, that have to become a credit balance a member can understand and an operator can stand behind. Batunet took over development and support of the platform in 2015.
The case in one minute.
- Client
- Dondino — German-language rewards and cashback platform with member accounts and payouts to members in Germany, Austria and Switzerland.
- Role
- Batunet took over development and support of the platform in 2015.
- Business model
- Cashback via affiliate programs, paid promotional emails and a two-tier referral program on a shared credit account.
- External connections
- Historically more than ten affiliate networks, connected via file retrieval, REST and SOAP APIs, each in its own format.
- Core of processing
- A dedicated import path per network that converts reported transactions into a unified internal transaction model.
- Billing
- Splitting the reported commission into a member share and an operator share. Account balances with a traceable booking history.
- Payout
- A separate process with its own status: payouts have prerequisites, are reviewed and either approved or canceled with a stated reason.
- Fraud prevention
- Lockout periods against repeat rewards, detection of automated clicks, identification of duplicate accounts, blocklists and graduated lockouts after suspicious login attempts.
- Processing model
- Import, matching and check runs are set up as recurring batch processing, controlled via a job table with intervals and a time budget per run.
- Technical foundation
- PHP 8 and Laravel 8, combined with a PHP codebase that grew over years, whose imports and check runs were gradually moved to Laravel’s database layer.
A promise that sounds simple.
Cashback is a promise that fits in a few words: shop through the platform and get part of the purchase price back. The sentence needs no explanation. The system behind it consists almost entirely of what the sentence leaves out.
Because the purchase doesn’t happen on the platform. It happens at the merchant, brokered through an affiliate network that reports the transaction later — in its format, on its schedule, with its own status model. Between a member’s click and the credit to their account lie a third-party system, a wait of weeks and states that can still change during that time.
Dondino combines several ways to earn credit: cashback via affiliate programs, paid clicks on promotional emails and shares of the credits earned by referred members. Members can also use their credit themselves for email promotions, which are approved before sending.
Batunet took over development and support of the platform in 2015. The task wasn’t to build an interface for cashback, but to make the billing behind it reliable: to turn the reports of many third-party systems into a credit model that a member can understand and an operator can stand behind.
Ten providers, ten ideas of what data looks like.
Connecting an affiliate network sounds like one API. Connecting what have historically been more than ten networks is something else: it means more than ten ideas of what a transaction should look like.
The differences aren’t in the big picture but in the details — and that is exactly where billing errors arise. One provider offers files for download, the next a REST resource, the third a SOAP service. One knows a few statuses, another more, and labels that sound alike don’t mean the same thing. One returns the identifier a member was sent off with, another passes it through only partially.
The first design decision was therefore to let none of these formats further into the system. Each connection is its own import path with a single task: to produce the internal transaction model from whatever a network delivers. If a network changes the structure of its file, the import detects and logs it instead of silently accepting incorrect values.
- Transport
- File retrieval, REST API, SOAP service
- Data format
- CSV, XML, Provider-specific field names and column orders
- Status model
- Different status labels per provider, Different numbers of states, Normalization to an internal model
- Identifier handover
- A dedicated tracking identifier per transaction, Returned in full or only partially, depending on the provider, A separate path in the import where the identifier isn’t passed through
The path of a transaction.
The central question of this system isn’t whether a transaction arrived, but whom it belongs to. The network doesn’t know the member, and the platform doesn’t know the purchase. The two sides are connected solely by an identifier that the platform assigns on redirect and the network reports back later.
That identifier is therefore not a technical detail but the precondition for every credit. Where a provider doesn’t pass it through in full, that isn’t an edge case to solve later — it’s a separate path in the import that has to be planned from the start.

- 01
Identifier
When redirecting to an affiliate program, the platform assigns its own tracking identifier for this transaction.
- 02
Handover
The identifier is passed to the affiliate network and carried along with the transaction there.
- 03
Report
Later, the network reports the transaction — in its own format, with its own status.
- 04
Normalization
The provider-specific import path converts fields and statuses into the internal transaction model.
- 05
Matching
The returned identifier is used to assign the transaction to a member account.
- 06
Credit
Only once the network confirms the transaction does the reported commission become a credit with an entry in the booking history.
From commission to credit.
A reported commission isn’t a credit yet. Between the two lies a calculation that has to stay traceable: the amount reported by the network yields the member’s share and the operator’s share. This split belongs to the business logic, not to downstream reporting. The referral program builds on the same credit: whoever referred a member receives a share, across two tiers.
That’s why there is a booking history alongside the account balance. A credit balance that exists only as a total can’t be explained when in doubt; one with a history can be broken down item by item — which transaction, which point in time, which status.
External status models are normalized in the process. Confirmed and canceled are part of the internal transaction model, not the vocabulary of individual providers. Credit balances and booking history remain separately traceable.
The step that deliberately isn’t automatic.
At the end comes a payout — the only point at which money leaves the system. That is precisely where, by design, not everything runs on its own.
A payout request is therefore a separate process with its own status. It has prerequisites — a minimum amount, a verified bank account or an approved PayPal account — it is reviewed, and it is either approved or canceled with a stated reason. Between sufficient credit and an actual payout lies a decision that stays visible in the system; payout receipts are available as PDF.
This isn’t technical convenience but a design decision. Automation is right wherever an error can be corrected. A paid-out amount can’t.
Where money is generated, people will try.
As soon as a system pays out money, it becomes a target. That isn’t suspicion of members but a property of the business model: a process that ends in a credit makes it worth trying to trigger it without actually going through it.
The countermeasures therefore aren’t in one place but spread across the workflow. After a recorded transaction, a lockout period applies per member and affiliate program before the same path is rewarded again. Automated clicks on promotional emails are detected and filtered out. Duplicate accounts are made identifiable via shared attributes, down to matching bank accounts. Blocklists apply where a pattern is already known. Accounts with a suspicious number of failed logins are locked in stages rather than immediately and permanently.
None of these measures is complex on its own. Together, they are the difference between a cashback program that pays off and one that gets exploited.
What an integration means over years.
An affiliate integration isn’t a project with an end date. The networks it is connected to belong to other companies: they change fields, formats, status labels and access methods without asking — and they don’t do it all at once.
For the platform, this means the work at the edges never stops while the core has to stay stable. That is exactly what the separation between provider-specific import and internal transaction model is for: a changed format affects one import path, not the billing.
In any case, the value of a system like this isn’t in its technology, but in the rules that have grown into it over years — matching, splits, deadlines, quirks of individual providers. If you want to keep those rules, you maintain the edges instead of rebuilding the core.
A mature codebase on a new foundation.
Dondino is older than its newer technical foundation. The member area and administration run in a Laravel 8 application on PHP 8; alongside it is a PHP codebase that grew over years, with its own import and check scripts.
We didn’t replace this codebase in one go. Older database access continues to run through a compatibility layer, and imports and check runs were moved step by step to Laravel’s database layer. They are controlled via a job table with priority, interval and a fixed time budget per run, so that no single import blocks the next.
The member accounts have also evolved without anyone having to notice: older password hashes are upgraded to a current algorithm at the next login — without forcing a password change for all members.
Where this case connects.
Questions about this case
How do you connect multiple affiliate networks to a shared billing model?
By not allowing any provider format further into the system. Each connection is its own import path with a single task: converting the network’s fields, formats and status labels into an internal transaction model. Everything after that — matching, billing, credit — knows only this one model.
How is an affiliate transaction assigned to the right member?
Via a tracking identifier that the platform assigns when redirecting to the affiliate program and that the network returns with the reported transaction. Weeks can pass between the two events. Where a provider doesn’t pass the identifier through in full, a separate path in the import handles it.
Why isn’t a payout triggered automatically?
Because it’s the step that can’t be undone. A payout is therefore a separate process with its own status: it has prerequisites, it is reviewed, and it is either approved or canceled with a stated reason. Automation is right where an error remains correctable.
How does a cashback platform deal with fraud?
Through several controls along the workflow rather than a single check: lockout periods against repeat rewards, detection of automated clicks, identification of duplicate accounts, blocklists for known patterns and graduated lockouts after a suspicious number of failed logins.
Why don’t you name the connected affiliate networks?
Because they aren’t needed to show the engineering work. Integration, matching, billing, payout and fraud prevention can be described completely without naming the providers; the relationships with the networks are part of Dondino’s business.
Related topics.
Guides, decisions, services and case studies connected to this page.
Let’s talk about your project.
Tell us briefly about your project. Your first conversation is directly with our management.
