ServiceWorker(サービスワーカー)とは何か


ServiceWorkerの基本 | messageイベント

Demo

HTML


	<button type="button" class="btn btn-primary" onclick="test1();">テスト1</button>
	

JavaScript


$(()=>{
	if (navigator.serviceWorker) {
	 navigator.serviceWorker.register('./sw.js', { scope: './' })
	 .then(function(reg) {
		console.log('Service workerの登録に成功しました。 Scope は ' + reg.scope);
	 }).catch(function(error) {
		console.log('Service workerの登録に失敗しました。' + error);
	 });

	 navigator.serviceWorker.addEventListener('message', event => {
		// event は MessageEvent オブジェクトです
		console.log(`${event.data}はおいしい`);
	 });
	
	}
	
})


function test1(){

	// ServiceWorkerにメッセージを送信する
	 navigator.serviceWorker.ready.then( registration => {
		let msg1 = 'ウナギ';
		console.log(msg1);
		registration.active.postMessage(msg1);
	 });

}
	

サービスワーカー(sw.js)


// Service Worker インストール時に実行される
self.addEventListener('install', (event) => {
	console.log('service worker install');
});

// 初回の画面表示のときに表示されるようだ。2回目以降の画面表示からは実行されない。installイベントが完了後にactivateイベントが発生する。
self.addEventListener('activate', (event) => {
  console.info('activate', event);
});

self.addEventListener('fetch', (event) => {
	console.log('service worker fetch ... ' + event.request);
});

// サービスワーカー内
self.addEventListener('message', event => {
  // event は ExtendableMessageEvent オブジェクトです
 let msg2 = `${event.data}のエサ`;
 console.log(msg2);

  event.source.postMessage(msg2);
});
	

fetchイベント

Demo3

HTML


<div>
サービスワーカーを介さず直接フロントエンドからバックエンドのFetch APIによる非同期通信をする。(いつもの非同期通信)
するとサービスワーカー内のfetchイベントが発動する。<br>
<button type="button" class="btn btn-primary" onclick="test2();">テスト2:fetchのテスト</button>
<aside>
(ログはブラウザのコンソールに出力。Windows+ChromeならF12キーでレスポンスを確認してね。)
</aside>
</div>

<div style="margin-top:2em;">
サービスワーカーからバックエンドへFetch APIによる非同期通信を行う。
サービスワーカーからも非同期通信ができることができる。ただし、Fetch APIしか使えず従来のXHRは使えない。<br>
なお、この非同期通信を行ったときもサービスワーカー内のfetchイベントが発動する。<br>
<button type="button" class="btn btn-primary" onclick="test3();">テスト3:fetchのテスト</button>
</div>
	

JavaScript(script.js)


$(()=>{
	if (navigator.serviceWorker) {
	  navigator.serviceWorker.register('./sw.js', { scope: './' })
	  .then(function(reg) {
		console.log('Service workerの登録に成功しました。 Scope は ' + reg.scope);
	 }).catch(function(error) {
		console.log('Service workerの登録に失敗しました。' + error);
	 });

	  navigator.serviceWorker.addEventListener('message', event => {
		// event は MessageEvent オブジェクトです
		console.log(`${event.data}はおいしい`);
	 });
	
	}
	
})


function test1(){

		// ServiceWorkerにメッセージを送信する
	 navigator.serviceWorker.ready.then( registration => {
		let msg1 = 'ウナギ';
		console.log(msg1);
		registration.active.postMessage(msg1);
	  });

}

// fetchのテスト
function test2(){
	$('#res').html('abc');
	fetch("./backend.php")
	  .then(response => {
		console.log('response');
		console.log(response);
		return response.json();
	  })
	  .then(data => {
		console.log('data');
		console.log(data);
		$('#res').html(JSON.stringify(data));
	  })
	  .catch(error => {
		console.log(error);
		console.log("失敗しました");
	});

}

function test3(){

	// ServiceWorkerにメッセージを送信する
	 navigator.serviceWorker.ready.then( registration => {
		let msg1 = 'test3_action';
		console.log(msg1);
		registration.active.postMessage(msg1);
	  });

}
	

サービスワーカー sw.js


// Service Worker インストール時に実行される
self.addEventListener('install', (event) => {
	console.log('service worker install. demo3.');
});

// installイベント後に実行される。基本的に初回アクセスの時にのみ実行。
self.addEventListener('activate', (event) => {
	console.log('activate', event);
});

// cssやjsなどファイル読み込み、Fetch APIによる非同期通信時
self.addEventListener('fetch', (event) => {
	console.log('service worker fetch ');
	console.log(event.request);
});

// フロントエンドとサービスワーカーでのやりとりはここで行う。
self.addEventListener('message', event => {
	// event は ExtendableMessageEvent オブジェクトです
	let msg2 = `${event.data}のエサ3-2`;
	console.log(msg2);
	
	if(event.data == 'test3_action'){
		console.log('test3_action 2');
		
		// サービスワーカー内ではもFetch APIが使用可能である。
		fetch("./backend.php")
		  .then(response => {
			console.log('response');
			console.log(response);
			return response.json();
		  })
		  .then(data => {
			console.log('data');
			console.log(data);
			
		  })
		  .catch(error => {
			console.log(error);
			console.log("失敗しました");
		});
	}

	event.source.postMessage(msg2);
});
	

バックエンド backend.php


<?php

//データ加工や取得
$res = ['success'=>1,'yagi'=>'山羊','kani'=>'蟹','same'=>'鮫'];

// JSONに変換し、通信元に返す。
$json_str = json_encode($res, JSON_HEX_TAG | JSON_HEX_QUOT | JSON_HEX_AMP | JSON_HEX_APOS);
echo $json_str;