Skip to main content
  1. Blog/

The Polyfill.io Supply Chain Attack — A Wake-Up Call for CDN Trust

Osmond van Hemert
Author
Osmond van Hemert
Table of Contents
Supply Chain Security - This article is part of a series.
Part : This Article

If you’re running a website that includes a script tag pointing to cdn.polyfill.io, stop reading this and remove it immediately. Seriously. The polyfill.io domain — which has been serving JavaScript polyfills to over 100,000 websites — was acquired by a Chinese company called Funnull earlier this year, and this week security researchers at Sansec confirmed that the domain is now injecting malicious code into websites. The code redirects mobile users to scam sites using a sophisticated detection mechanism that avoids triggering on admin browsers, web crawlers, or analytics tools.

This is one of the most impactful supply chain attacks we’ve seen in the web ecosystem, and it highlights a fundamental problem with how we’ve been building websites for over a decade.

What Happened
#

Polyfill.io was originally created by Andrew Betts at the Financial Times as an open-source service. It served JavaScript polyfills — compatibility code that adds modern browser features to older browsers. The service was simple and useful: include one script tag, and your site would automatically serve the right polyfills based on the visitor’s browser. At its peak, polyfill.io was used by over 100,000 websites.

In February 2024, the polyfill.io domain and associated GitHub account were acquired by a company called Funnull, which operates a CDN primarily serving Chinese markets. Andrew Betts immediately warned on social media that he had no involvement with the sale and recommended removing the dependency. Cloudflare and Fastly both set up alternative endpoints to serve polyfills safely.

Despite these warnings, tens of thousands of sites continued loading scripts from cdn.polyfill.io. This week, Sansec’s analysis confirmed the worst-case scenario: the domain is now serving modified JavaScript that includes malicious code. The injected code is sophisticated — it only activates on mobile devices, uses timing-based delays to avoid detection, and specifically avoids executing when it detects web analytics tools, ad tech platforms, or known web crawlers.

The Technical Details
#

The malicious code injection is cleverly implemented. The polyfill.io CDN still serves legitimate polyfill code, but periodically injects additional JavaScript that:

  1. Fingerprints the visitor: checks the User-Agent string for mobile browsers, specifically targeting Android devices
  2. Avoids detection: checks for the presence of analytics tools (Google Analytics, Google Tag Manager), web crawlers (Googlebot), and developer tools before activating
  3. Uses timing obfuscation: delays execution and only triggers on certain page loads, making it harder to reproduce consistently
  4. Redirects to scam sites: sends mobile users to fake Google Analytics domains that lead to sports betting and other scam sites

The sophistication of the evasion techniques means that most automated monitoring tools wouldn’t catch the injection. If you’re testing your site from a desktop browser with developer tools open, the malicious code deliberately doesn’t execute. This is social engineering at the infrastructure level.

The Deeper Problem: CDN Trust
#

This attack exploits a fundamental weakness in web architecture: the implicit trust we place in third-party script sources. When you include a <script src="https://cdn.example.com/library.js"> tag in your HTML, you’re giving that domain the ability to execute arbitrary code in your users’ browsers. If that domain changes hands, serves compromised code, or is hijacked, you have no protection.

We’ve known about this risk theoretically for years, but polyfill.io makes the risk tangible. Here’s why this particular case is so concerning:

Scale: Over 100,000 websites affected, including major brands that should know better.

Legitimacy of origin: This wasn’t a typosquatting attack or a compromised package. It was the legitimate, original domain that developers had intentionally included.

Domain ownership transfer: The attack vector wasn’t technical — it was a business transaction. Someone bought the domain and its associated trust.

Warning ignored: The original author explicitly warned the community months before the malicious code appeared, and thousands of sites still didn’t act.

What You Should Do Right Now
#

If you maintain any websites, here’s your immediate action plan:

Audit your script tags. Search your HTML templates, CMS themes, and build output for any references to polyfill.io. Remove them immediately.

Assess if you even need polyfills. In 2024, the browsers that needed polyfills (mainly IE 11 and older) are effectively extinct. Most modern browsers support ES6+ features natively. Check caniuse.com for your target features — you probably don’t need polyfills at all anymore.

If you genuinely need polyfills, use Cloudflare’s alternative at cdnjs.cloudflare.com/polyfill/ or Fastly’s at polyfill-fastly.io. Better yet, bundle them with your build process so you control the code.

Implement Subresource Integrity (SRI). For any third-party script you do load, use the integrity attribute on your script tags. This ensures the browser only executes the script if its hash matches what you expect. SRI wouldn’t have prevented the initial compromise if the polyfill code was dynamically generated per-request (which it was), but it’s a critical defense for static CDN resources.

Use Content Security Policy (CSP) headers. Restrict which domains can serve executable scripts on your pages. This limits the blast radius of any single compromised CDN.

Monitor your dependencies. Set up automated scanning for your production sites that checks for unexpected script sources or content changes.

My Take
#

This incident frustrates me because it was entirely preventable. Not just the attack itself, but the vulnerability pattern. I’ve been arguing for years that loading JavaScript from domains you don’t control is an underappreciated risk. The convenience of CDN-hosted libraries comes with an implicit trust relationship that most developers never think about.

The web development community has done excellent work on package-level supply chain security — lockfiles, audit tools, dependency scanning. But we’ve largely ignored the CDN layer, treating it as a networking optimization rather than a security boundary. Polyfill.io proves that the domain serving your scripts is as critical as the code in your node_modules.

The uncomfortable truth is that this attack was successful not because of technical sophistication but because of organizational inertia. Warnings went out in February. The attack was confirmed in June. Four months of clear, public warnings, and over 100,000 sites were still vulnerable. That’s not a technology problem — it’s a process problem.

If there’s one takeaway from this incident, it’s this: treat every third-party script source as a dependency that can be compromised, and minimize them accordingly. Self-host what you can, use SRI for what you can’t, and maintain an inventory of every external domain your site trusts with code execution. The web’s trust model is fragile, and this week proved it.

Supply Chain Security - This article is part of a series.
Part : This Article

Related