Third-Party JavaScript
Stats as of 2026-09-18 21:49 UTC — last scan: 2026-09-18
250 scan batches run
87,690 of 87,696 available pages scanned (100.0% coverage) 79,451 of 87,690 scanned pages were reachable (90.6%) 37,120 reachable pages loaded at least one third-party script (46.7% of reachable) 46,836 known third-party service loads identified 26 unique known services across 17 categories
Third-Party JavaScript by Country
| Country | Scanned | Available | Reachable | URLs with 3rd-Party JS | Known Service Loads | JS URLs /100 Reachable | Known Loads /100 Reachable | Last Scan |
|---|---|---|---|---|---|---|---|---|
| Austria | 822 | 822 | 787 | 275 | 52 | 34.9 | 6.6 | 2026-08-25 |
| Belgium | 1,329 | 1,329 | 1,238 | 641 | 728 | 51.8 | 58.8 | 2026-09-15 |
| Bulgaria | 353 | 353 | 305 | 129 | 164 | 42.3 | 53.8 | 2026-08-24 |
| Canada | 4,469 | 4,469 | 4,216 | 2,428 | 3,433 | 57.6 | 81.4 | 2026-09-03 |
| Croatia | 257 | 257 | 254 | 138 | 192 | 54.3 | 75.6 | 2026-08-25 |
| Czechia | 866 | 866 | 798 | 479 | 792 | 60.0 | 99.2 | 2026-08-25 |
| Denmark | 1,536 | 1,536 | 1,507 | 821 | 2,081 | 54.5 | 138.1 | 2026-09-12 |
| Estonia | 401 | 401 | 385 | 135 | 121 | 35.1 | 31.4 | 2026-08-25 |
| Finland | 199 | 199 | 189 | 46 | 26 | 24.3 | 13.8 | 2026-08-25 |
| France | 10,009 | 10,009 | 9,094 | 4,166 | 2,464 | 45.8 | 27.1 | 2026-09-11 |
| Germany | 6,599 | 6,599 | 6,295 | 1,661 | 1,057 | 26.4 | 16.8 | 2026-09-17 |
| Greece | 1,752 | 1,752 | 1,618 | 783 | 1,120 | 48.4 | 69.2 | 2026-08-30 |
| Hungary | 392 | 392 | 296 | 128 | 196 | 43.2 | 66.2 | 2026-08-25 |
| Iceland | 145 | 145 | 143 | 78 | 46 | 54.5 | 32.2 | 2026-08-26 |
| Ireland | 536 | 536 | 499 | 268 | 724 | 53.7 | 145.1 | 2026-08-26 |
| Italy | 5,351 | 5,351 | 4,400 | 1,586 | 1,424 | 36.0 | 32.4 | 2026-09-08 |
| Latvia | 803 | 803 | 762 | 261 | 288 | 34.3 | 37.8 | 2026-08-26 |
| Lithuania | 122 | 122 | 112 | 57 | 113 | 50.9 | 100.9 | 2026-08-26 |
| Luxembourg | 573 | 573 | 481 | 348 | 134 | 72.3 | 27.9 | 2026-08-26 |
| Malta | 610 | 610 | 595 | 466 | 1,276 | 78.3 | 214.5 | 2026-08-26 |
| Netherlands | 945 | 945 | 902 | 361 | 280 | 40.0 | 31.0 | 2026-08-27 |
| Norway | 249 | 249 | 243 | 137 | 112 | 56.4 | 46.1 | 2026-08-26 |
| Poland | 14,951 | 14,951 | 13,461 | 6,925 | 9,822 | 51.4 | 73.0 | 2026-09-14 |
| Portugal | 3,508 | 3,508 | 2,807 | 1,101 | 1,918 | 39.2 | 68.3 | 2026-09-18 |
| Cyprus | 29 | 29 | 29 | 13 | 15 | 44.8 | 51.7 | 2026-08-26 |
| Romania | 807 | 807 | 343 | 250 | 254 | 72.9 | 74.1 | 2026-09-12 |
| Slovakia | 442 | 442 | 413 | 218 | 273 | 52.8 | 66.1 | 2026-08-27 |
| Slovenia | 214 | 214 | 207 | 56 | 82 | 27.1 | 39.6 | 2026-08-24 |
| Spain | 6,091 | 6,091 | 4,990 | 2,437 | 2,407 | 48.8 | 48.2 | 2026-09-10 |
| Sweden | 1,702 | 1,702 | 1,546 | 509 | 309 | 32.9 | 20.0 | 2026-09-11 |
| Switzerland | 2,123 | 2,123 | 2,067 | 408 | 447 | 19.7 | 21.6 | 2026-08-29 |
| United Kingdom | 19,511 | 19,511 | 18,475 | 9,811 | 14,486 | 53.1 | 78.4 | 2026-09-16 |
Hover or focus any non-zero country-table count to preview matching pages. Activate the number to keep the preview open and download a CSV for that country and metric from Download machine-readable third-party tools data (JSON).
Top Third-Party Services
| # | Service | Loads |
|---|---|---|
| 1 | Google Analytics (GA4) | 8,529 |
| 2 | cdnjs (Cloudflare CDN) | 7,581 |
| 3 | jsDelivr CDN | 6,937 |
| 4 | Google reCAPTCHA | 4,816 |
| 5 | Google Tag Manager | 4,101 |
| 6 | Google Hosted Libraries | 3,266 |
| 7 | unpkg CDN | 2,879 |
| 8 | jQuery | 2,792 |
| 9 | Font Awesome | 1,947 |
| 10 | Bootstrap | 959 |
| 11 | Cookiebot | 828 |
| 12 | Facebook Pixel | 472 |
| 13 | CookieInformation | 418 |
| 14 | Adobe Dynamic Tag Management / Launch | 302 |
| 15 | OneTrust | 292 |
| 16 | Sentry | 223 |
| 17 | Cloudflare Turnstile / Challenge | 192 |
| 18 | Google Analytics (Universal) | 85 |
| 19 | Usercentrics | 60 |
| 20 | Matomo Cloud | 48 |
Top Services by Page Prevalence
| # | Service | Reachable Pages | Prevalence of Reachable Pages |
|---|---|---|---|
| 1 | Google Analytics (GA4) | 8,299 | 44.9% |
| 2 | jsDelivr CDN | 4,601 | 24.9% |
| 3 | Google reCAPTCHA | 4,536 | 24.6% |
| 4 | cdnjs (Cloudflare CDN) | 3,995 | 21.6% |
| 5 | Google Tag Manager | 3,910 | 21.2% |
| 6 | Google Hosted Libraries | 2,942 | 15.9% |
| 7 | unpkg CDN | 2,249 | 12.2% |
| 8 | jQuery | 2,213 | 12.0% |
| 9 | Font Awesome | 1,527 | 8.3% |
| 10 | Bootstrap | 952 | 5.2% |
| 11 | Cookiebot | 808 | 4.4% |
| 12 | Facebook Pixel | 455 | 2.5% |
| 13 | CookieInformation | 418 | 2.3% |
| 14 | Adobe Dynamic Tag Management / Launch | 299 | 1.6% |
| 15 | OneTrust | 218 | 1.2% |
| 16 | Sentry | 210 | 1.1% |
| 17 | Cloudflare Turnstile / Challenge | 192 | 1.0% |
| 18 | Google Analytics (Universal) | 84 | 0.5% |
| 19 | Usercentrics | 60 | 0.3% |
| 20 | Matomo Cloud | 48 | 0.3% |
Top Service Categories
| # | Category | Loads |
|---|---|---|
| 1 | CDN | 20,663 |
| 2 | Analytics | 9,461 |
| 3 | JavaScript Library | 6,058 |
| 4 | Security | 5,008 |
| 5 | CAPTCHA | 4,816 |
| 6 | Tag Manager | 4,403 |
| 7 | Icon Library | 1,947 |
| 8 | Cookie Consent | 1,598 |
| 9 | UI Framework | 959 |
| 10 | Advertising | 472 |
| 11 | Error Tracking | 223 |
| 12 | Payments | 42 |
| 13 | Customer Support | 29 |
| 14 | Chat | 29 |
| 15 | CRM | 13 |
Category Balance
Infrastructure-heavy categories (CDNs, core libraries, and UI assets):
| # | Infrastructure Category | Loads |
|---|---|---|
| 1 | CDN | 20,663 |
| 2 | JavaScript Library | 6,058 |
| 3 | Icon Library | 1,947 |
| 4 | UI Framework | 959 |
Policy-relevant categories (tracking, consent, support, and security tooling):
| # | Policy-Relevant Category | Loads |
|---|---|---|
| 1 | Analytics | 9,461 |
| 2 | Security | 5,008 |
| 3 | CAPTCHA | 4,816 |
| 4 | Tag Manager | 4,403 |
| 5 | Cookie Consent | 1,598 |
| 6 | Advertising | 472 |
| 7 | Error Tracking | 223 |
| 8 | Payments | 42 |
| 9 | Customer Support | 29 |
| 10 | Chat | 29 |
| 11 | CRM | 13 |
| 12 | Marketing | 13 |
| 13 | Heatmaps | 1 |
Unknown Third-Party Hosts (Review Queue)
| # | Host | Loads | Reachable Pages |
|---|---|---|---|
| 1 | cdn.ent.auvergnerhonealpes.fr |
15,298 | 1,650 |
| 2 | cdn.ecollege.haute-garonne.fr |
2,498 | 270 |
| 3 | translate.google.com |
2,295 | 2,292 |
| 4 | maps.googleapis.com |
1,759 | 1,741 |
| 5 | www.cqc.org.uk |
1,712 | 1,699 |
| 6 | static.parastorage.com |
1,572 | 147 |
| 7 | content.powerapps.com |
1,546 | 128 |
| 8 | www.styleguide.sachsen.de |
1,279 | 320 |
| 9 | cc.cdn.civiccomputing.com |
955 | 949 |
| 10 | ajax.aspnetcdn.com |
901 | 445 |
| 11 | static.addtoany.com |
867 | 850 |
| 12 | dksxg5o1pn16c.cloudfront.net |
762 | 56 |
| 13 | d2m1owqtx0c1qg.cloudfront.net |
762 | 396 |
| 14 | cdn-cookieyes.com |
761 | 757 |
| 15 | cdn.xl.pt |
709 | 13 |
These hosts were seen as third-party script sources but did not match a known service signature. Review this queue regularly and promote stable, policy-relevant hosts into the signature list.
📥 Machine-readable results: Download machine-readable third-party tools data (JSON)
Overview
This scan identifies third-party JavaScript loaded by government websites, including analytics tags, tag managers, cookie-consent tools, CDNs, customer support widgets, and other externally hosted scripts.
The goal is to make the external dependencies used across European government sites easier to inspect. This helps answer questions like:
- Which analytics or advertising vendors appear most often?
- How common are third-party CDNs and consent managers?
- Which countries lean more heavily on externally hosted web tooling?
The scanner looks at every <script src="..."> on a page, excludes
same-origin scripts, and then tries to match known services such as Google Tag
Manager, Google Analytics, Matomo Cloud, OneTrust, Cookiebot, Cloudflare,
Microsoft Clarity, HubSpot, and more.
Why This Matters
Third-party JavaScript can affect:
- Privacy: analytics, advertising, and tracking integrations may send data to external services.
- Security: externally hosted libraries and widgets increase supply-chain risk.
- Resilience: a page may depend on third-party infrastructure outside the control of the public authority.
- Performance: extra scripts often increase page weight and network cost.
This page gives an EU-wide view of those dependencies.
Usage
Scan a single country
python3 -m src.cli.scan_third_party_js --country ICELAND --rate-limit 1.0
Scan all countries
python3 -m src.cli.scan_third_party_js --all --rate-limit 1.0
Scan all countries with a runtime cap
python3 -m src.cli.scan_third_party_js --all --max-runtime 110 --rate-limit 1.0
Command-line options
| Option | Default | Description |
|---|---|---|
--country CODE |
— | Country code to scan (for example FRANCE or ICELAND) |
--all |
— | Scan all countries in the TOON directory |
--toon-dir PATH |
data/toon-seeds/countries |
Directory with .toon seed files |
--rate-limit N |
1.0 |
Maximum HTTP requests per second |
--max-runtime N |
0 (no limit) |
Maximum runtime in minutes for graceful CI stops |
GitHub Actions
The Scan Third-Party JavaScript workflow
(.github/workflows/scan-third-party-js.yml) runs automatically every 6 hours
and can also be triggered manually from the Actions tab.
Artifacts uploaded after each run:
| Artifact | Contents |
|---|---|
3pjs-scan-<run_number> |
data/metadata.db, scan output log, annotated *_3pjs.toon files |
validation-metadata |
data/metadata.db shared with the other scanners |
Output
Annotated TOON file
Each page entry in the output *_3pjs.toon file gains a third_party_js
field:
{
"url": "https://example.gov/",
"third_party_js": [
{
"src": "https://www.googletagmanager.com/gtm.js?id=GTM-XXXX",
"host": "www.googletagmanager.com",
"service_name": "Google Tag Manager",
"version": "GTM-XXXX",
"categories": ["Tag Manager"]
}
]
}
If scanning failed for a URL, a third_party_js_error field is added instead.
Database table
Results are stored in the url_third_party_js_results table:
| Column | Type | Description |
|---|---|---|
url |
TEXT | Page URL |
country_code |
TEXT | Country identifier |
scan_id |
TEXT | Unique scan run ID |
is_reachable |
INTEGER | 1 = page fetched successfully |
scripts |
TEXT | JSON array of third-party script records |
error_message |
TEXT | Error message if the page fetch failed |
scanned_at |
TEXT | ISO-8601 timestamp |