Frontend Development 8 min read

Using Web Workers to Prevent UI Blocking During Large File Downloads

This article explains why downloading large files blocks the UI in single‑threaded JavaScript, and demonstrates how to offload the heavy processing to Web Workers with practical code examples, allowing the page to remain responsive while the download proceeds.

Rare Earth Juejin Tech Community
Rare Earth Juejin Tech Community
Rare Earth Juejin Tech Community
Using Web Workers to Prevent UI Blocking During Large File Downloads

The article starts with a common problem: when a large file is downloaded, the browser shows a perpetual loading spinner and the UI becomes unresponsive because JavaScript runs on a single thread.

It explains that the single‑threaded nature of JavaScript means intensive CPU work (such as generating or processing large data) blocks the UI, and simply removing the spinner does not solve the underlying issue.

To resolve this, the author proposes using Web Workers , which run scripts in background threads, keeping the UI thread free. The worker can perform heavy calculations or I/O, then post the result back to the main thread.

Basic Usage

Creating a dedicated worker from the main thread:

const myWorker = new Worker("worker.js"); // worker.js is the script URI

Communication between the main thread and the worker uses postMessage and onmessage :

myWorker.postMessage(data);
myWorker.onmessage = (event) => {
  const wb = event.data;
  // writeFile runs on the main thread, may cause a brief pause
  writeFile(wb, 'test.xlsx');
  ElMessage.success('Download task is running in the background, you can continue using the UI');
};

In the worker script, you can import libraries with importScripts() and process the data:

importScripts("./xlsx.js");
self.onmessage = (e) => {
  const ws = XLSX.utils.json_to_sheet(e.data);
  const wb = XLSX.utils.book_new();
  XLSX.utils.book_append_sheet(wb, ws, 'Sheet1');
  self.postMessage(wb);
  self.close();
};

Additional Details

Shared workers and Service Workers are mentioned as alternatives for multi‑page communication and network interception.

Event listeners such as onmessage and postMessage must be attached to the worker object in the main thread, while the worker itself can use the global scope directly.

Workers should be terminated explicitly with myWorker.terminate() or self.close() to free resources.

Using workers for small files may be unnecessary overhead.

References

MDN documentation on Web Workers, Shared Workers, and Service Workers, as well as code repositories for examples.

Git repository for the full project: https://gitee.com/Big_Cat-AK-47/vue-project.git

FrontendJavaScriptWeb WorkersMultithreadingfile downloadUI Blocking
Rare Earth Juejin Tech Community
Written by

Rare Earth Juejin Tech Community

Juejin, a tech community that helps developers grow.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.