Zum Hauptinhalt springen
tsecurity.de LIVE
Echtzeit-Radar & Feeds
Alle RSS Feeds
👥 Community & Social
Windows Tipps & SecurityGarmin Cirqa im Test: Fitness-Tracker ohne Display(22.09.2026 um 10:30 Uhr)
Windows Tipps & SecuritySicher online bezahlen: 7 Methoden im Praxis-Check(22.09.2026 um 09:00 Uhr)
Sichere Programmierunghas_tokens: true is a boolean. 476 of 791 have no market behind them.(22.09.2026 um 10:00 Uhr)
Sichere ProgrammierungClaude Code Hooks – Safety Through Invariants(22.09.2026 um 10:04 Uhr)
Sichere ProgrammierungYour MCP Tool Just Returned a Secret. Did It Need To?(22.09.2026 um 10:05 Uhr)
Windows Tipps & SecurityGarmin Cirqa im Test: Fitness-Tracker ohne Display(22.09.2026 um 10:30 Uhr)
Windows Tipps & SecuritySicher online bezahlen: 7 Methoden im Praxis-Check(22.09.2026 um 09:00 Uhr)
Sichere Programmierunghas_tokens: true is a boolean. 476 of 791 have no market behind them.(22.09.2026 um 10:00 Uhr)
Sichere ProgrammierungClaude Code Hooks – Safety Through Invariants(22.09.2026 um 10:04 Uhr)
Sichere ProgrammierungYour MCP Tool Just Returned a Secret. Did It Need To?(22.09.2026 um 10:05 Uhr)
Intelligence View
⚡ tsecurity.de Intelligence

How I built a browser watermark library that survives DevTools

Identifying the leaker after a screenshot escapes, when the obvious tricks no longer work. The problem Last year, I watched a customer of ours forward a screenshot of an internal dashboard to a vendor. The screenshot showed…

0
↗ Quelle (dev.to)
Reagiere als Erste:r — dein Feedback zählt!

Identifying the leaker after a screenshot escapes, when the obvious tricks no longer work.







The problem



Last year, I watched a customer of ours forward a screenshot of an internal dashboard to a vendor. The screenshot showed financial figures that should have stayed inside the company. Nobody could prove who took it.



If every pixel of that screen had carried that user's email or ID in faint diagonal text, we would have known the answer in five seconds.



That is the whole idea behind a watermark. It does not prevent leaks. It makes leaks attributable.








Why naive watermarks fail



The simplest version is a <div> you put on top of the page:




<div class="watermark">[email protected]</div>






The trouble: anyone who knows F12 opens DevTools and deletes the <div> in two clicks. Or overrides its CSS. Or screenshots the page before your watermark script runs.



The naive watermark catches honest users. It does nothing against the people who actually want to leak.






What I wanted



A library that:




  1. Renders the user's identifier (email, user id, whatever) tiled across the page.

  2. Re-creates itself if someone removes it from the DOM.

  3. Resists CSS overrides that try to hide it.

  4. Optionally redirects users who open DevTools to a "you do not have access to this" page.

  5. Logs every attempt to my server. Even if every browser-side defense gets bypassed, I want a record of who tried what, when.



That last one is the part most teams forget, and it is the most important.






What I built



watermark-shield is a small library on top of watermark-js-plus, which handles the actual canvas rendering very nicely. On top of it I added:




  • A self-healing overlay that comes back if removed.

  • A MutationObserver that catches CSS injection attempts on the watermark.

  • A DevTools-detection layer that fires a callback before it redirects.

  • An audit hook so the server can log attempts.



Framework-agnostic core in plain JavaScript, with bindings for Angular, React, and Vue 3.



The whole thing is roughly 6 KB gzipped, with another 6 KB lazy chunk if you turn on the DevTools guard.






Two-line install






npm install watermark-shield









import { WatermarkShield } from 'watermark-shield';

new WatermarkShield({
content: user.id,
protect: { devtool: true },
}).create();






You get a tiled watermark of the user's id, an active DevTools detector, and the always-on passive protections. Sensible defaults; nothing else to configure.






A realistic production setup






new WatermarkShield({
content: user.id,
fontSize: '1.5vw', // scales with screen
fontColor: { light: '#000', dark: '#fff' }, // light/dark aware
globalAlpha: 0.18, // survives JPEG compression
protect: {
devtool: true,
devtoolUrl: 'https://yourapp.com/security/blocked',

onDevtoolOpen: (detectorType) => {
// The user is about to be redirected. Fire and forget.
// No userId in the body. The server resolves the user from
// the session cookie or JWT, never from what the client sends.
navigator.sendBeacon('/api/audit/devtool', new Blob(
[JSON.stringify({
detectorType,
url: location.href,
ts: Date.now(),
})],
{ type: 'application/json' },
));
},
},
}).create();






Three things worth pointing out.



Identity belongs to the server. The audit body has no userId. The server resolves who the user is from the session cookie or the Authorization header. If you trust the client to tell you who is logged in, an attacker can forge the audit log too.



The audit log is the real backstop. A determined attacker can defeat any browser-side defense (custom Chromium build, an extension that strips watermarks, JS overrides). But the beacon already left their browser before they got that far. The server log is what gives you attribution that survives sophisticated bypasses.



Always devtool: false in development. Otherwise your engineers cannot debug their own app. Gate it with import.meta.env.PROD or environment.production.






Framework bindings






// Angular
import { WatermarkShieldService } from 'watermark-shield/angular';
this.shield.create({ content: user.id, protect: { devtool: true } });

// React
import { useWatermarkShield } from 'watermark-shield/react';
useWatermarkShield({ content: user.id, protect: { devtool: true } });

// Vue 3
import { useWatermarkShield } from 'watermark-shield/vue';
useWatermarkShield({ content: user.value.id, protect: { devtool: true } });






Same lifecycle in every binding: create, update, destroy.



The goal is not to prevent capture. It is to make every captured image carry the leaker's name. That changes the calculation from "no one will know" to "of course I will be caught."






Try it






npm install watermark-shield






Source and docs: https://github.com/mhwazrah/watermark-shield

Ähnliche Beiträge
🔍 Verwandte News

Auch interessante Nachrichten How I built a browser watermark library that survives DevTools

Thematisch verwandte Begriffe: built, browser, watermark, library · 6 Treffer

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Laden...

Beiträge werden geladen ...

Laden...

Videos werden geladen ...

Zum Aktualisieren ziehen
ZERO-DAY CVE-2026-94426 | A vulnerability was determined in xuxueli xxl-job up to 3.5.0. The impac…
Advisory →
TTS Reader • tsecurity.de Voice
tsecurity.de Icon
tsecurity.de App
Offline-Lesen, Eilmeldungen & 0ms Ladezeit

Installiere tsecurity.de direkt auf deinen Home-Bildschirm für das ultimative Vollbild-Magazinerlebnis ohne Browser-Leisten.

Nächster Beitrag
Themen-Radar & Intelligence Matrix
Echtzeit-Taxonomie nach Angriffsvektoren & Plattformen

tsecurity.de Live Threat Radar

🔴 LIVE RADAR
MONITORING
AKTIV
CVE-DATENBANK
LIVE
🔍
Community Radar & Live Chat
Sentinel Bot online • Live-Stream
Dein Cluster: Security Explorer
Match:
lädt…
Verbindung zum Community-Stream wird aufgebaut...
Bearbeitungsmodus — Senden überschreibt deine Nachricht
Community-Puls — was gerade passiert
lädt…
Aktivitäten deiner Analysten
lädt…
Neues Thema oder Eilmeldung einreichen

Reiche interessante Links, Zero-Days oder Debatten ein. Die Community entscheidet per Upvote über die Veröffentlichung.

Heiß diskutierte Einreichungen
🔖 Gespeicherte Artikel
📂 Keine gespeicherten Artikel vorhanden.
Zurück Ziehen Vor
Links: vorheriger Artikel Rechts: nächster Artikel unten: schließen
News NIS-2 Frühwarnung Tier-1 Intel ⏱️ 3 Min vor 10 Min
Artikeldaten werden geladen...

Zurück: vorheriger Vor: nächster
↗ Original-Quelle
Social Reaktionen Deine Reaktion zählt
Einstufung & Relevanz-Poll 0 Stimmen
In sozialen Netzwerken teilen 1-Klick