1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98
| importScripts( 'https://cdn.jsdelivr.net/npm/localforage@1.7.3/dist/localforage.min.js' );
const ENDPOINT = 'https://your-domain/post-request';
const bin2Hex = (buffer) => { let digest = ''; const dataView = new DataView(buffer); for (let i = 0, len = dataView.byteLength; i < len; i += 4) { let value = dataView.getUint32(i); let hex = value.toString(16); let padding = '00000000'; let paddedValue = (padding + hex).slice(-padding.length); digest += paddedValue; }
return digest; };
const postRequestFetchListener = (fetchEvent) => { const requestUrl = fetchEvent.request.url; const method = fetchEvent.request.method.toUpperCase(); if (!(method === 'POST' && requestUrl === ENDPOINT)) { return; }
fetchEvent.respondWith( fetchEvent.request .clone() .arrayBuffer() .then((buffer) => { const requestBody = String.fromCharCode.apply( null, new Uint8Array(buffer) ); if (requestBody.includes('cache=1')) { return crypto.subtle.digest('SHA-1', buffer); }
return Promise.reject(); }) .then((sha1Buffer) => { const sha1Hash = bin2Hex(sha1Buffer); console.log('SHA1 Hash => ', sha1Hash);
return localforage.getItem(sha1Hash).then((cachedResponse) => { if (cachedResponse) { console.log('Cached repsonse => ', cachedResponse); return new Response(cachedResponse, { status: 200, statusText: 'OK', headers: { 'Content-Length': cachedResponse.length, 'Content-Type': 'application/json', 'X-SW-Cache-Hit': 1, 'X-SW-Cache-Type': 'POST', }, }); }
return fetch(fetchEvent.request).then((response) => { console.log('Fetching response => ', response.clone());
if (200 <= response.status && response.status < 400) { response .clone() .text() .then((textResponse) => { console.log('Caching response => ', textResponse); return localforage.setItem(sha1Hash, textResponse); }); }
return response; }); }); }) .catch(() => fetch(fetchEvent.request)) ); };
self.addEventListener('fetch', postRequestFetchListener);
|