System · 2025–2026 · Independency, own product
ClientDeck: a campaign control system
The agency had data in a dozen tools, reports that disagreed and account changes nobody could trace. No ready-made tool solved this for the Czech market including Sklik and Heureka. So we built one.


- In short
- One system for Google Ads, Meta, Sklik, LinkedIn and comparison engines, with one metric definition and orders straight from the e-shop.
- Every account intervention goes through an approval queue: name, reason, timestamp and a review date.
- Verified Google and Meta OAuth integrations, tokens encrypted with AES-256 and automatic rotation, eight languages.
The brief
Independency manages dozens of ad accounts across 14 markets. Each platform shows only its piece of the puzzle and its own version of the truth. We needed one place to check performance in the morning, where the system itself flags a deviation, and where every change in an account is traceable to who made it and why.
What we built
ClientDeck is a SaaS with its own admin for the agency and for clients. It pulls data from ad platforms through official APIs, joins it with orders from the e-shop and computes cost of sales from real revenue, not platform attribution. On top run rules and alerts (budget exceeded, ROAS below threshold, CTR falling), budget pacing to month end and an approval queue where every intervention waits for a person.
The AI account audit proposes optimisations straight into the queue. AI proposes, a human always decides. It also includes our own cookie banner with Consent Mode v2, which we deploy on client websites.
The category report: joining two layers of data
The most demanding part of the system is the report that shows which product groups actually earn money. Standard ad-platform reports cannot answer that question, and it is not their fault. They work with a different layer of data than the one in which the money appears.
Cost is known to the ad platform per item of the product feed. Revenue appears in the shop, on individual order lines. These are two different grains in two different identifier spaces, and joining them directly by ID fails for several reasons at once:
- A feed item and an order line need not be the same thing. The feed often carries a variant while the shop bills an SKU, or the other way round.
- Identifiers are not stable over time. When a shop moves to another platform they are renumbered and the history falls apart.
- One product usually sits in several campaigns and several markets, so costs have to be summed before there is anything to attach revenue to.
- Markets use different currencies, so nothing can be added up until it is converted.
We resolve it by joining the two layers through the category. It is the one attribute both layers carry and the one that survives renumbering. The system has three layers for this, which could be built separately and are tested separately:
- Identifier harmonisation. Matching feed items to shop SKUs, including the cases where the relationship is one to many.
- Category mapping. The category tree in the feed and the one in the shop are not the same thing, so a mapping sits between them and is maintained and validated. The validation mainly watches products that fall into several categories: without one primary category their cost would be counted twice.
- Revenue reconciliation. Comparing the sum of order lines against what the shop reports, so that anything lost on the way becomes visible.
Why the category and not the individual product? At product level most accounts have too few conversions for the number to support any conclusion, and the identifiers are unstable. The category is the smallest grain at which the numbers are solid enough to act on.
The output is a weekly overview per market, in one currency and at one exchange rate per period: ad cost and real revenue for the same product group side by side. It is what decides where to add budget and where to cut. What the feed has to contain for any of this to work is covered in our article on feeds for several markets; the same expansion seen from the campaign side is on chci-ppc.cz.
Technology
- Google Verified App and Meta Verified App, OAuth 2.0; third-party passwords are never stored.
- Client tokens encrypted with AES-256 envelope encryption and key rotation every 90 days.
- Eight language versions, generated preview images, payments through Stripe.
- A demo on fictional data at demo.clientdeck.cz.
What it changed
Clients have their own access and see the same numbers as the agency. Problems are handled when they appear, not in the monthly report. In 30 days across August and September 2026 the team logged 302 documented interventions in ClientDeck.


Contact
Have a project? Write to us.
A few sentences about what you are dealing with is enough. We reply within one working day with questions and a proposed approach.