Two way communication between ServiceWorker and main thread is easily possible with MessageChannel API.

Let the code do the talking:

In your app.js have a simple sendMessage method that looks like:

1 2 3 4 5 6 7 8 9 function sendMessage ( message ) { return new Promise (( resolve , reject ) => { const messageChannel = new MessageChannel (); messageChannel . port1 . onmessage = function ( event ) { resolve ( ` Received a direct message from the ServiceWorker : $ { event . data } ` ); }; navigator . serviceWorker . controller . postMessage ( message , [ messageChannel . port2 ]) }); }

And in your sw.js recive and respond to the message:

1 2 3 4 self . addEventListener ( 'message' , function ( event ) { console . log ( ` Received a message from main thread : $ { event . data } ` ); event . ports [ 0 ]. postMessage ( ` Roger that ! - "${event.data}" ` ); });

Now from your app.js if you want to send a message to service worker and get a reponse from it you would:

1 2 3 var log = console . log . bind ( console ); var error = console . error . bind ( console ); sendMessage ( 'hello' ). then ( log , error ). catch ( error );

This would log something like: