The HTML 5 specification introduces a new technology called Web Workers, allowing developers to spawn new threads for processing JavaScript code. This is a major improvement from the current state of the web, as it allows JavaScript code to execute outside of the UI thread, so your application is still responsive during long-running scripts. However, due to the nature of Web Workers there are restrictions to what they can and cant do, and how to interact with them. Today
s article will explain what they are and how to use Web Workers.
How to do it…
To start a Web Worker, you point it at a JavaScript file:var myWorker = new Worker("myworker.js");
Once you have a worker, you can subscribe to message events from the worker:
myWorker.onmessage = function(event) { console.log("Web Worker returned: " + event.data); };
Additionally, you can subscribe to error events from the worker:
myWorker.onerror = function(event) { console.log("There was an error in " + event.filename + " at " + event.lineno + ": " + event.message"); };
A message can be passing into the Web Worker using:
myWorker.postMessage({foo:bar}); // then inside the Web Workers code onmessage = function(event) { postMessage(event.data.foo + " ==bar"); };
The scripts executed by the Web Worker ("myworker.js" in this example) have a global function that allows them to import other scripts:
importScripts("foo.js", "bar.js", …);
And a Web Worker can be stopped by calling:
myWorker.terminate();
How it works…
Instantiating a new Web Worker creates a new processing thread that executes the desired script. The thread executes until it is finished or theterminate()
function is called. The code executed by the Web Worker is normal JavaScript, but does not have access to the DOM, since making the DOM threadsafe would break the web. If you need to manipulate the DOM, your Web Worker should send messages to its creator, which in turn should update the DOM.You can pass data to and from the Web Worker using the postMessage
function. Inside the Web Worker postMessage
is a global function that accepts an object as its only argument. This will trigger the myWorker.onmessage
callback function. Where the event.data
property will be set to the object passed into postMessage
. To pass data into the Web Worker, call the myWorker.postMessage
function and pass in an object as its only argument. This will fire the global onmessage
function inside of the Web Worker, and again event.data
will be the object.
Objects that are passed through the postMessage
infrastructure should serialization, meaning it does not contain functions or cyclical references. You may pass simple values such as Strings and Numbers, or more complex values such as Objects and Arrays. All values are serialized to JSON for transportation between threads.
The onerror
callback function is fired when a runtime error occurs while the Web Worker is executing. The callback event has three properties: the error message
, the offending filename
, and the line number that through the error (lineno
).
Additionally, web workers can be used to send IO requests using the XMLHttpRequest
object, but the responseXML
and channel
properties are always null
. You can also spawn sub Web Workers from inside of a running Web Worker to fork tasks. This can be particularly useful one machines that have multiple processors.
Theres more…
The issue with Web Workers are that they are not supported by all browsers. They are supported by FireFox 3.5, Safari 4, and Chrome. They are not supported by IE and so far IE has not announced supporting them in IE 9 either. However, just because they arent supported by every browsers, doesnt mean we shouldn
t start using them. Developers just need to implement them in a way that is backwards compatible, only using Web Workers if available, and falling back to standard JavaScript.s article, Computing with JavaScript Web Workers, for more ideas and a working example.I have not seen a wide use of Web Workers in mainstream applications yet, but I am hopeful it will happen soon. Probably the most applicable technology for leveraging Web Workers is in conjunction with the Canvas element. There can be a lot of number crunching required for 2d and 2.5d animations, whose behavior would be improved by leveraging Web Workers.
There are definitely other useful applications for Web Workers, feel free to leave your ideas in the comment section.
See also
- See the FireFox MDC document for more details on how to use Web Workers.
- See John Resig
t support them.See the Web Worker Specification for the exact implementation details.