Digital Design
Data Privacy Agent
A browser extension that says “no” for you — and never pretends. Research-led, end-to-end product design, shipped publicly on Chrome, Firefox, and Safari.

Data Privacy Agent is a browser extension that handles cookie consent for you — and never pretends. I built it solo (with an AI engineering copilot), owning everything from the founding research through product strategy, UX, and a shipped public launch on Chrome, Firefox, and Safari stores.

The problem
Cookie consent banners are the most-clicked UI on the web, and they are engineered to be lost to. Dark patterns bury the “reject” behind mazes of toggles, and a growing class of European publishers have escalated to the practice of “pay or consent” walls: accept tracking, or pay a subscription to decline.
Existing auto-consent products claim to solve this, but I found their success rates lower than I wanted and their UI’s leaving a lot to be desired. I also knew that dealing with cookie pop-ups on your phone would save users a ton of time, and annoyance while browsing.
Research: test the incumbents before designing anything
I built a Playwright crawl harness and ran a control/treatment study of 194 EU/UK sites from a German IP — each site loaded with and without the leading open-source auto-reject extension, every verdict validated by screenshot.

Two findings shaped the entire product:
- The biggest failure mode isn’t missing banners — it’s lying about success. In 26% of encounters the tool clicked something, reported success, and left the consent wall standing. Nearly all of these were pay-or-consent walls: the tool clicks into the paywall funnel, declares victory, and leaves the user worse off.
- Most pay-or-consent walls are genuinely binary. A follow-up click-through audit of all 27 walls in the sample — actually following every path, not reading button labels — found ~22 of 27 offer no free “reject” at all. My original hypothesis, that a free reject was merely buried, was wrong for most of these walls.
When “no” doesn’t exist, the honest product doesn’t fake one. It tells the user the truth and gives them a different lever.
Strategy: an honest agent, not a magic blocker
That insight split the product into a free hook and a paid promise.
Free: automatically reject every banner when a real “no” exists — including rejects buried behind dark-pattern mazes — and when a site offers no free decline call it out instead of pretending.
Paid: when saying “no” isn’t enough, act — an agent that files data-deletion and opt-out requests on the user’s behalf.
Three product constraints were non-negotiable from day one:
- Privacy is an invariant, not a feature. Local-first; the only identifier is an anonymous install ID; crowdsourced reporting is opt-in and sends a bare hostname — never history, never identity.
- Never consent on the user’s behalf. The engine clicks “reject,” never “accept” — even when accepting would make a banner disappear and the metrics look better.
- Heal without shipping code. Sites change daily; store reviews take days. All site coverage ships as data — a server-hosted ruleset every installed client picks up within hours, no store update needed, and fully compliant with extension-store rules against remote code.
The design system of honesty
The signature UX surfaces all follow one rule: the interface never claims more than the engine actually did.
The rights flag. When the extension detects a standing pay-or-consent wall it cannot clear, it doesn’t fail silently — a small card explains what the site is doing and what rights the user has (GDPR framing in the EU; opt-out and deletion framing in the US). The moment of user frustration becomes the moment of education — and the natural surface for the paid agent.

The “no decline option” notice. Some sites show an agree-only wall — one button, no refusal, and clicking “Agree” often accepts full Terms of Service, not just cookies. The extension will never click it. Instead it hides the wall and shows a plain-language disclosure: “This site only lets you accept. There’s no way to refuse here, so we hid the notice. It may still track you.” Honesty over theater — and these hidden notices are deliberately excluded from the “handled” statistics, so the numbers stay truthful too.

The missed-banner ask. Coverage is a moving target, so the product asks for help — carefully. If nothing in the pipeline acted and something banner-shaped is still on screen after 15 seconds, a one-tap prompt asks “did we miss one?” Every gate around it — evidence checks, double-sighting, per-site caps, global cooldowns — exists to keep quiet sites silent: the ask must be rarer than the failure.

The status card. The popup shows exactly what happened on the current site — rejected, by which mechanism, and what the site tried (pre-ticked consent boxes, for instance). That log lives only on the device.


First-run. Chrome hides new extensions behind a puzzle-piece menu, and testers’ first feedback was “did it even install?” The welcome page now proves the extension is live — it detects it running and flips to “You’re protected” — and teaches the one real setup step: pin the icon.

The visual system
Small on purpose. The whole product has to feel like one thing across a 320-pixel popup, an options page, cards injected into other people’s websites, a welcome page, and an iOS app — so the system is a handful of rules rather than a library.
- One dark surface stack, no webfont. Three greys (
#0b0f14/#11181f/#1e2a36), the system font at five sizes. A popup should feel native to the browser it lives in, and an extension has no byte budget for type. - Colour is a verdict, not decoration. One sky-blue accent is reserved for actions. Everything else colour says is a state: green Denied, red Accepted, and a solid red Pay or Consent — the one state worth shouting about. Every state the status card can be in has a badge; there is no ambiguous “done.”
- One warm surface. The tracker reveal is the only card that isn’t cool grey. It is the single place the product asks for something, and the colour marks it as such.
- Same card, everywhere. The in-page rights, no-decline and missed-banner cards use the popup’s card language inside a shadow root, styled with a constructed stylesheet so a host page’s CSS — or its Content Security Policy — can’t reach in and break it.
- Restack, don’t squeeze. Touch devices get a taller tier; iPad’s narrow system popover gets a compact tier that stacks rows vertically rather than truncating a verdict.

One wall, four faces
One early user report — “your extension breaks HBO Max” — turned into the project in miniature.
The investigation first uncovered a genuine engineering bug worth its own postmortem: the site wrote its own CSS into the extension’s stylesheet, and our cleanup was silently erasing the site’s design system. But fixing it revealed the deeper design problem — the same consent dialog element served four different faces depending on who and where you were. US visitors got an agree-only Terms wall. French visitors got a GDPR dialog with a one-click free reject. English-locale EU visitors got the reject buried behind “Manage Cookies.” Logged-in users got a different component entirely.
A single rule would have been wrong somewhere, for someone. The shipped design treats each face honestly: the agree-only wall is hidden and disclosed, and each of the three rejectable variants gets its reject clicked — verified from both US and EU vantage points before shipping, a two-region verification doctrine every site rule now goes through.


Outcomes
- Shipped public on all three browser stores — Chrome, Firefox, and Safari including iOS — with a weekly release train and a same-day server-side rule channel: site fixes reach every installed client in hours, without a store review.
- Zero-breakage methodology. Every rule ships through a regression harness against real sites, smoke gates on every release, and the dual-vantage US + EU verification doctrine — because a privacy tool that breaks pages gets uninstalled, and the study showed 0.0% breakage is achievable.
- Coverage that compounds. 200+ CMP rule families in the engine plus a growing server-side ruleset; user reports flow through a triage pipeline that turns a single report into coverage for everyone.
- A validated honesty stance. The research finding that most pay-or-consent walls are truly binary became the product’s differentiator: the only tool in the space that tells users the truth when “no” doesn’t exist.
What I learned
- Verify by doing, not by reading. The buried-reject hypothesis survived reading button labels and died the day I clicked through all 27 walls. That correction — cheap, early, slightly embarrassing — redirected the entire paid product.
- Honesty is a feature you have to design. “Never fake success” sounds like a value; making it real took concrete mechanisms — a disclosure card, excluded statistics, a reporting flow — each of which had to earn its screen space.
- Constraints make the product. Privacy-first, never-click-accept, and data-not-code weren’t limitations to work around; they’re why the product is trustable, and half the design decisions fell out of them automatically.
- Design for being wrong. Geo-variant walls, sites that change overnight, rules that misfire — the healing ruleset, the verification doctrine, and the missed-banner ask are all UX for the failure cases, and they matter more than the happy path.
Since launch
The free extension went public on 8 September 2026. Two weeks in, the numbers below are the real ones: production telemetry, real installs only — harness and automation traffic is tagged and excluded — and there is nothing to count but an anonymous install ID, because that is all the product knows.
- 293
- installs
- Chrome, Firefox and Safari (Mac + iOS); 252 of them in the two weeks since launch
- 65%
- of all installs active in the past 7 days
- 191 of 293 — still running, not just installed
- 1,080
- sites where a banner was rejected
- distinct sites per install, summed; the site names never leave the device, only the count
- 620
- pay-or-consent walls flagged
- the rights card, shown to 42 EU installs
- 1 in 5
- installs raised a hand for Pro
- 58 “count me in” taps on the deletion agent, before billing exists
- 108
- reported sites now handled
- from 205 user reports on 174 hosts — 62% closed as coverage, shipped as data
Coverage behind those numbers: 207 CMP rule families in the engine, plus 39 served site rules, 52 shadow-DOM entries and 68 pre-hide selectors — every one of them shipped as data, reaching each install within hours of a fix.