Most organisations approve browser extensions on three signals: the extension came from the official store, its manifest asks for very little, and what it does looks harmless. This talk shows that all three signals can be true at the same time as the extension is stealing credentials, session tokens and sensitive data.
It does that in four parts: a live demonstration of an extension that passes every one of those checks, the public incident record from late 2024 into 2026, an explanation of why store review cannot catch this class of attack, and the controls that move the risk, including a gap in Australia's Essential Eight that most organisations do not know they have.
The three signals we trust
Ask a room how many extensions they installed this month, then how many read the permissions. The second number is always smaller. But even the people who do read them are relying on the same three signals:
It came from the store
It has an official Chrome Web Store listing, so it must have been vetted.
The manifest is minimal
It only asks for a few modest permissions.
The purpose looks benign
It does something useful and unremarkable.
All three are true. All three are about to be shown insufficient.
The permission gap
The extension used in the demonstration, FocusGuard, is a simple "stay on task" tool. Its permissions list is a single entry:
"permissions": ["storage"]
That is what an approver sees, and it looks minimal. What it also declares, in a separate field that is easy to skim past, is this:
"host_permissions": ["<all_urls>"]
Together with two content scripts that run on every page the user visits, that is enough to read and act on anything the user can see in the browser. Manifest V3 narrowed what extensions can do, but it did not remove this capability. Minimal permissions do not mean minimal capability.
Meet the extension
In the recording, FocusGuard is installed and behaves exactly as described. Nothing happens until an operator, working from a separate console, sends it a target. From that point, every time the user opens the targeted web mail application, the extension quietly reads the page and returns what it finds.
What just happened
Go back to the three signals. Every one of them is still true.
| Signal | After the demonstration |
|---|---|
| It came from the store | Still true. The store surface never distinguished it from any other listing. |
| The manifest was minimal | Still true. The capability was packaged and clean. |
| The purpose looked benign | Still true. The intent arrived from a server, after installation. |
The capability was reviewed. The intent was not.
What the attacker now has
From a single page visit, through an extension the user trusts:
A password reset email with a live temporary code. Multi-factor authentication is irrelevant once the code itself is intercepted.
A session token captured on every page load, giving authenticated access without the password.
An API response showing the user's role, for example finance administrator. The attacker knows the access level before moving.
Salary figures, bonuses and a board pack. High-value data with no further action required.
This is not hypothetical
Cyberhaven, December 2024
The attacker sent a phishing email made to look like a Chrome Web Store policy notice. A developer consented to a malicious OAuth application, which was granted the right to see, edit, update and publish the company's extensions. A malicious version was then published under the legitimate developer's identity. Because no password was used, multi-factor authentication never came into play.
Estimates of the scale vary with who was counting:
Crucially, the Cyberhaven campaign was configuration driven, the same pattern as the demonstration:
- Generic code ships. The malicious build carried no service-specific logic, so it was clean enough to pass.
- Configuration is fetched from a command and control server. The extension pulled a configuration file and stored it locally.
- The targeting lives in the configuration. Servers returned configurations targeting ChatGPT and Facebook Business accounts.
GitLab: sixteen extensions
GitLab Threat Intelligence's February 2025 analysis is worth reading closely because the mechanism was not phishing. The actor acquired at least some of the extensions directly from their original developers. Ownership changed hands with no visible signal to users, many of the extensions had not been updated for months, and the malicious behaviour was gated on the server side by check-in count. There was nothing for store review to catch.
The sleepers, 2025 into 2026
These extensions held Featured and Verified status and showed years of clean behaviour, then flipped when triggered remotely.
Beyond Chrome
Chrome was the primary platform in all three anchor incidents, but it is not the only one. After Google removed the ShadyPanda extensions from Chrome, they persisted in the Edge store, and DarkSpectre's three-day logic bomb was an Edge add-on. On Firefox, the GhostPoster campaign accounted for 17 extensions in the DarkSpectre cluster, using the same gap and the same evasion. Any organisation that permits personal browsers, or browsers other than Chrome, carries exposure that Chrome Enterprise controls do not cover.
One mechanism, three times
| Cyberhaven | GitLab 16 | The sleepers | |
|---|---|---|---|
| Distribution | Official store | Official store | Official store |
| Declared purpose | Benign, worked | Benign, worked | Benign, worked |
| Trigger | Remote configuration | Remote configuration | Update or configuration |
| Scrutiny avoided by | OAuth publishing | Ownership change | Aged reputation |
Not three tricks. The same mechanism, three times.
Why store review does not catch it
Four ways onto the marketplace
Submit clean, flip later
Ship an extension that genuinely does nothing malicious. The payload is generic, and the targeting arrives later as remote configuration.
Why it passes: nothing malicious exists at review time.
Hijack the publish path
Use OAuth consent phishing against a legitimate developer, then publish as the trusted owner. No password is involved, so multi-factor authentication never fires.
Why it passes: the publisher is genuine. Cyberhaven.
Buy the trust
Acquire an existing listing from its developer. Ownership transfers invisibly, and the clean history transfers with it.
Why it passes: no new developer and no new listing. GitLab 16.
Grow the trust
Publish something genuinely useful, accumulate installs, reviews and Featured status over years, then flip it.
Why it passes: the reputation was earned honestly. ShadyPanda.
Only the first route is an attack on review. The other three are attacks on the trust that review confers.
How review actually works
A common belief is that extension updates are not reviewed. That is a myth. Google applies the same review process to new submissions and to updates, combining automated analysis (malware signatures, obfuscation, dangerous APIs and policy checks) with human review for compliance. The gap is not that updates escape review.
The gap is that scrutiny is signal driven. Closer review is triggered by things like a new developer, a new extension, a request for dangerous permissions, or significant code changes. None of those fire when an established developer ships a configuration change to an existing extension.
| Review signal | Present in these attacks? |
|---|---|
| New developer? | No. The account is established, sometimes for years. |
| New extension? | No. It is an existing, reputable listing. |
| Dangerous new permission? | No. Broad permissions were granted at installation. |
| Significant code change? | No. The malice arrives as remote configuration. |
In the strongest cases, nothing is submitted for review at all.
Two details that seal it
Broad permissions draw scrutiny. The malicious extensions carried exactly the permissions that attract review, but at review time the code did nothing with them.
Obfuscation is banned. So the campaigns keep the packaged code clean enough to pass review, then serve the obfuscated payload from the configuration server at runtime, outside anything review can see. This is the gap between static and runtime behaviour, in Google's own terms.
Store review evaluated a package at a point in time. The hostile behaviour arrives afterwards, as data.
Review sees a moment, not a lifetime.
What actually reduces the risk
"Review permissions carefully" is not enough. In every case above, the permissions were either minimal or already granted, and the malice arrived after approval. User vigilance is the weakest layer, so the risk has to be managed through enterprise controls.
The Essential Eight blind spot
For Australian organisations, this is the part that surprises people. The Essential Eight does cover browser extensions, but only for patching and support:
- Patch web browsers and their extensions within two weeks, tightening to 48 hours for critical vulnerabilities at Maturity Level Three.
- Remove browsers and extensions that are no longer supported by the vendor (ISM-1704, all maturity levels).
What it does not require, at any maturity level, is an extension allowlist. That control does exist in the Information Security Manual, as ISM-1235: extensions for user applications are restricted to an organisation-approved set. But it is not part of the Essential Eight.
The control that would stop this is in the ISM but not in the Essential Eight, at any maturity level. And the one Essential Eight requirement that does cover extensions, keeping them patched to the vendor's current version, is the very channel this attack arrives on.
Controls that move the needle
Block all, allow some
Block the store by default and have an administrator manage an allowlist. The single most effective control.
Blocked and allowed permissions
Also catches an allowlisted extension that updates to request more.
Force install
Deploy the tools users actually need, so that pressure does not drive shadow installs.
Runtime blocked hosts
Keeps every extension off HR, finance and administration domains, regardless of its permissions.
Inventory and risk scoring
See every installed extension, its permissions and a risk score.
In Chrome Enterprise these are delivered through the ExtensionSettings policy, including its runtime_blocked_hosts setting.
The residual gap, stated honestly
An extension that is already allowlisted, holds broad permissions and runs on general domains can still be flipped by remote configuration. So layer the defence:
- Pin trusted versions of highly permissioned extensions.
- Monitor for permission or ownership changes on update.
- Restrict runtime hosts on sensitive domains.
- Watch outbound traffic for anomalous command and control and exfiltration domains.
Before Monday morning
- Run an inventory. Use the Chrome Enterprise Apps and Extensions Usage Report. Most organisations have no complete list of what is installed.
- Block all, allow some. One
ExtensionSettingschange: block by default and build a known-good allowlist. It is the highest-value single action. - Protect your crown jewels. Set
runtime_blocked_hostsfor HR, finance, administration and source control, so a flipped extension cannot touch sensitive applications. - Monitor what you have approved. Alert on permission or ownership changes for highly permissioned extensions. Both are compromise indicators.
- Remove what is unused. Extensions no longer in use are exposure with no benefit. Audit installations older than 90 days.
For teams doing their own analysis
Comparing versions of an extension over time surfaces useful signals:
- Permission and host differences across versions.
- New domains in the code, which are candidate command and control or exfiltration endpoints.
- Entropy jumps in changed scripts, which often indicate obfuscation.
- Per-file hash comparison, which catches stealthy edits to worker scripts where the manifest is unchanged.
Third-party auditing covers only a fraction of the store and lags by months. Treat it as a supplement, not a control.
What would actually have to change
Continuous post-approval monitoring. The model breaks because trust is decided once, while behaviour changes continuously. Closing the gap means watching after approval, not just at the moment of approval.
Ownership and provenance transparency. A visible, auditable record when an extension changes hands. That is the route that carried the GitLab sixteen straight past every review signal.
Will you look at them the same again?
From the store. Minimal manifest. Benign purpose.
Your approved extensions were approved once. That approval relied on signals these attacks are designed never to trigger.
Sources
- Sekoia, Targeted supply chain attack against Chrome browser extensions (22 January 2025)www.sekoia.com/blog/targeted-supply-chain-attack-against-chrome-browser-extensions
- SecurityWeek, Cyberhaven Chrome extension hack linked to widening supply chain campaign, citing Secure Annex (31 December 2024)www.securityweek.com/cyberhaven-chrome-extension-hack-linked-to-widening-supply-chain-campaign/
- The Register, Supply chain attack on Chrome extensions, citing Booz Allen Hamilton (22 January 2025)www.theregister.com/2025/01/22/supply_chain_attack_chrome_extension/
- GitLab Threat Intelligence, Malicious browser extensions (13 February 2025)gitlab-com.gitlab.io/gl-security/security-tech-notes/threat-intelligence-tech-notes/malicious-browser-extensions-feb-2025/
- Malwarebytes, Sleeper browser extensions woke up as spyware on 4 million devices, reporting Koi Security research on ShadyPanda (2 December 2025)www.malwarebytes.com/blog/news/2025/12/sleeper-browser-extensions-woke-up-as-spyware-on-4-million-devices
- The Register, Malicious Chrome and Edge browser extensions, ShadyPanda (1 December 2025)www.theregister.com/2025/12/01/chrome_edge_malicious_browser_extensions/
- The Hacker News, DarkSpectre browser extension campaigns (31 December 2025)thehackernews.com/2025/12/darkspectre-browser-extension-campaigns.html
- Malwarebytes, Firefox joins Chrome and Edge as sleeper extensions spy on users, GhostPoster (19 January 2026)www.malwarebytes.com/blog/news/2026/01/firefox-joins-chrome-and-edge-as-sleeper-extensions-spy-on-users
- Google, Chrome Web Store review processdeveloper.chrome.com/docs/webstore/review-process
- Google, Chrome Web Store program policies, code readability requirementsdeveloper.chrome.com/docs/webstore/program-policies/code-readability
- Australian Signals Directorate, ISM Guidelines for System Hardening (ISM-1235, ISM-1412)www.cyber.gov.au/resources-business-and-government/essential-cyber-security/ism/cyber-security-guidelines/guidelines-system-hardening
- Australian Signals Directorate, Essential Eight Maturity Modelwww.cyber.gov.au/resources-business-and-government/essential-cyber-security/essential-eight/essential-eight-maturity-model
- Australian Signals Directorate, Essential Eight maturity model and ISM mapping (October 2024)cyber.gov.au/sites/default/files/2025-03/Essential%20Eight%20maturity%20model%20and%20ISM%20mapping%20%28October%202024%29.pdf
- Google Chrome Enterprise, Set Chrome app and extension policies (ExtensionSettings, runtime_blocked_hosts)support.google.com/chrome/a/answer/9867568
- Google Chrome Enterprise, View app and extension usage detailssupport.google.com/chrome/a/answer/9226555
- Pantelaios and Kapravelos, Manifest V3 Unveiled: Navigating the New Era of Browser Extensions, arXiv:2404.08310 (2024)arxiv.org/abs/2404.08310
- HackTricks, Browser Extension Pentesting Methodologybook.hacktricks.xyz/pentesting-web/browser-extension-pentesting-methodology