I spent a number of years working in the WordPress agency space, and during that time, we frequently received requests from clients asking us to improve their website performance. They would run Lighthouse audits and come to us concerned that their sites weren’t meeting the performance standards they wanted.
Weâd dive into their custom codebase and find optimizations, but often, the biggest culprits werenât their codeâthey were third-party scripts like Google Analytics, Google Tag Manager, Intercom chat widgets, advertising networks, and so on. Weâd report our findings and hear, âOh, well, we have to have thoseâŚbut canât we make it faster anyway?â
That tensionâbetween essential third-party functionality and website speedâis a challenge many web developers face. Fortunately, thereâs a compelling solution that helps strike a balance: Partytown.
This article will cover:
- The performance issues that can be caused by third-party scripts
- What PartyTown is and how it can alleviate those issues
- An example Next.js application to demonstrate the impact PartyTown can have
- How you can implement PartyTown in your own Next.js app
A video version of this content is also available here:
Prerequisites
To benefit from this article, you should be familiar with the following:
- JavaScript fundamentals
- The basics of how web browsers load and execute scripts
- Tools like Lighthouse for performance auditing
- The structure of a Next.js project (specifically using the App Router)*
* Even if youâre not using Next.js, you can still learn the core concept of Partytown from this article and integrate it into your preferred framework using one of Partytownâs Integration Guides.
Understanding the Problem: Main Thread Overload
In modern web applications, the browserâs main thread is where critical tasks like rendering, user interaction, and layout updates occur. But third-party scripts often hog this thread, leading to sluggish performance. Chromeâs Lighthouse documentation breaks down how script execution dominates the main thread, especially from third-party code.
These scripts can:
- Block rendering
- Cause input delay
- Significantly impact metrics like FID (First Input Delay) and TTI (Time to Interactive)
While some optimization techniques helpâlike adding async
or defer
attributes to <script>
tags (MDN reference), or using tools like @next/third-partiesâtheyâre often not enough.
Meet Partytown
Partytown is an open-source library from Builder.io that offloads third-party scripts to a web worker, freeing up the main thread. This means your appâs critical work (like rendering UI and responding to user input) can continue smoothly while third-party scripts run in isolation.
Partytown is currently in beta and actively developed. While it doesn’t support every use case yet, it provides a powerful way to boost site performance.
Why is it called “Partytown”?
The name âPartytownâ is a playful metaphor:
- The main thread = your appâs âdowntown,â where essential work happens.
- Third-party scripts = noisy neighbors cluttering up your downtown.
Partytown moves those noisy neighbors out to the suburbsâa separate part of townâso they can âpartyâ without disturbing downtownâs flow! đ In other words, theyâre offloaded to a web worker.
Before You Reach for Partytown
Before integrating Partytown, consider these best practices:
- Add
async
ordefer
to third-party<script>
tags so they don’t block rendering. Learn more on MDN. - Use the @next/third-parties package for smarter loading in Next.js projects (experimental as of this writing).
- Follow performance tips on web.dev to minimize script impact.
- Use Next.jsâs <Script> component with a
strategy
prop:beforeInteractive
â for critical scriptsafterInteractive
â for non-blocking scriptslazyOnload
â loads during idle timeworker
â (experimental) loads in a worker using Partytown, but only works with Pages Router for now, not the App Router (Next.js script docs).
I recommend implementing these best practices first to optimize third-party scripts, then running a Lighthouse audit to test the siteâs performance, paying particular attention to the “Minimize main-thread work” and “Reduce the impact of third-party code” sections of the report. Then, if you find that third-party scripts are still an appreciable performance issue, consider using Partytown to offload them from the main thread to web workers.
Testing Partytownâs Impact
Next, letâs run a few Lighthouse performance audits on a Next.js project that uses several third-party scripts. Weâll run one test with Partytown disabled and a second one with it enabled to measure its impact.
To get started, you can clone this example repository that demonstrates Partytown in action. Once you clone it, you can run npm install
to install its dependencies, then npm run dev
to get it running locally at http://localhost:3000.
This example project loads these third-party scripts:
- slow-script.js: a generic script I wrote for testing that blocks the main thread for 300ms
- fake-ads.js: a script I wrote that simulates advertisement scripts that block the thread, inject iframes, and load large images
- Google Tag Manager
- Intercom chat widget
Test 1: Without Partytown
You can disable Partytown in the example project by commenting out the <Partytown debug={true} forward={["dataLayer.push"]} />
line and removing type="text/partytown"
from each of the scripts in src/app/layout.tsx
.
Running a Lighthouse performance audit from the Chrome DevTools should then yield a result like this:

Note that the overall performance score is only 70/100, and that two of the main culprits are the âMinimize main-thread workâ and âReduce the impact of third-party codeâ items on the list.
If you open the Chrome DevTools and view the Sources
tab, you can confirm that the main thread (labeled âtopâ) is doing all the work required by the third-party scripts:

Test 2: With Partytown
Now, restore the <Partytown debug={true} forward={["dataLayer.push"]} />
line and the type="text/partytown"
prop for each of the Script
components. This will enable Partytown.
Run another Lighthouse performance audit to see a result like this:

Note that the performance score is now 99/100, and that the âMinimize main-thread workâ and âReduce the impact of third-party codeâ are no longer present on the list of issues. Vastly improved!
If you open the Chrome DevTools and view the Sources
tab, you can see that the main thread (labeled âtopâ) is still taking care of rendering the page, but that a new âPartytown đâ web worker has been added to the list. This âPartytown đâ web worker is now doing the work required by the third-party scripts:

The Takeaway
Take a step back and remember that for both the âWithout Partytownâ and âWith Partytownâ tests we ran, the browser had to download, parse, compile, and execute exactly the same third-party JavaScript code. The difference is that in the first test, the browserâs main thread had to do all of that work in addition to rendering the page, but in the second test, the third-party JS work was done by web workers running in a separate thread instead.
Implementing Partytown in a Next.js App Router Project
You can follow the steps below to implement Partytown in your own Next.js App Router projects.
â ď¸ Be aware of trade-offs when using Partytown. Some scripts may not behave identically in a web worker. Review Partytownâs trade-offs before deploying to production.
Steps to Add Partytown
- Install Partytown:
npm install @builder.io/partytown
- Add a command to copy Partytown scripts
Add the script below to thescripts
object in yourpackage.json
file, save it, then runnpm run partytown
to run the script and copy Partytownâs scripts into yourpublic
directory.
"scripts": {
  // ...
  "partytown": "partytown copylib public/~partytown"
},
Code language: JSON / JSON with Comments (json)
Optionally, you can also add this partytown
command to the dev
and/or build
scripts to copy Partytownâs files whenever the development server starts or the production app is built. Example:
"scripts": {
  // ...
  "dev": "npm run partytown && next dev --turbopack",
  "build": "npm run partytown && next build",
  "partytown": "partytown copylib public/~partytown"
},
Code language: JSON / JSON with Comments (json)
- Load Partytown in your
RootLayout
In src/app/layout.tsx
, add this line to import the Partytown component:
import { Partytown } from "@qwik.dev/partytown/react";
Code language: JavaScript (javascript)
Then render it inside the <head>
element, like this:
<head>
  // ...
  <Partytown forward={["dataLayer.push"]} />
</head>
Code language: HTML, XML (xml)
Partytownâs Configuration page lists all the options that can be passed to the Partytown component. Included among them is a debug
option you can enable with debug={true}
if you encounter any issues and need to debug them.
- Add
type="text/partytown"
to Scripts
Pass a type="text/partytown"
prop to the scripts youâd like to load via Partytown. If you have a script you want to remain on the main thread instead, simply omit the type="text/partytown"
prop for that script.
<Script
src="https://cdn.jsdelivr.net/.../slow-script.js"
type="text/partytown"
/>
Code language: HTML, XML (xml)
Hereâs what the full root layout file might look like:
import Script from "next/script";
import { Partytown } from "@qwik.dev/partytown/react";
export default function RootLayout({
children,
}: Readonly<{
children: React.ReactNode;
}>) {
return (
<html lang="en">
<head>
<Partytown forward={["dataLayer.push"]} />
</head>
<body>
{children}
{/* Slow third-party script */}
<Script
src="https://cdn.jsdelivr.net/gh/kellenmace/partytown-nextjs/third-party-scripts/slow-script.js"
type="text/partytown"
/>
Code language: JavaScript (javascript)
After implementing this, open Chrome DevTools and check the Sources
tab. Youâll see the third-party scripts now load in a web worker (rather than under the main âtopâ frame), confirming that Partytown is working, just as we did in our tests.
Conclusion
Third-party scripts are necessary, but they can be performance killers. Partytown offers a creative, effective way to keep them around without dragging down your appâs speed. By offloading them to a web worker, your main thread stays responsive and users get a faster experience.
As web developers, itâs up to us to make smart trade-offs. And when it comes to performance vs. functionality, Partytown helps us have our cake and eat it too.
To learn more, check out:
Happy coding, and enjoy the party (out of town)! đ