Permalink
Cannot retrieve contributors at this time
var matomoAnalytics = {initialize: function (options) { | |
if ('object' !== typeof options) { | |
options = {}; | |
} | |
var maxLimitQueue = options.queueLimit || 50; | |
var maxTimeLimit = options.timeLimit || (60 * 60 * 24); // in seconds... | |
// same as configured in in tracking_requests_require_authentication_when_custom_timestamp_newer_than | |
function getQueue() | |
{ | |
return new Promise(function(resolve, reject) { | |
// do a thing, possibly async, then... | |
if (!indexedDB) { | |
reject(new Error('No support for IndexedDB')); | |
return; | |
} | |
var request = indexedDB.open("matomo", 1); | |
request.onerror = function() { | |
console.error("Error", request.error); | |
reject(new Error(request.error)); | |
}; | |
request.onupgradeneeded = function(event) { | |
console.log('onupgradeneeded') | |
var db = event.target.result; | |
if (!db.objectStoreNames.contains('requests')) { | |
db.createObjectStore('requests', {autoIncrement : true, keyPath: 'id'}); | |
} | |
}; | |
request.onsuccess = function(event) { | |
var db = event.target.result; | |
let transaction = db.transaction("requests", "readwrite"); | |
let requests =transaction.objectStore("requests"); | |
resolve(requests); | |
}; | |
}); | |
} | |
function syncQueue () { | |
// check something in indexdb | |
return getQueue().then(function (queue) { | |
queue.openCursor().onsuccess = function(event) { | |
var cursor = event.target.result; | |
if (cursor && navigator.onLine) { | |
cursor.continue(); | |
var queueId = cursor.value.id; | |
var secondsQueuedAgo = ((Date.now() - cursor.value.created) / 1000); | |
secondsQueuedAgo = parseInt(secondsQueuedAgo, 10); | |
if (secondsQueuedAgo > maxTimeLimit) { | |
// too old | |
getQueue().then(function (queue) { | |
queue.delete(queueId); | |
}); | |
return; | |
} | |
console.log("Cursor " + cursor.key); | |
var init = { | |
headers: cursor.value.headers, | |
method: cursor.value.method, | |
} | |
if (cursor.value.body) { | |
init.body = cursor.value.body; | |
} | |
if (cursor.value.url.includes('?')) { | |
cursor.value.url += '&cdo=' + secondsQueuedAgo; | |
} else if (init.body) { | |
// todo test if this actually works for bulk requests | |
init.body = init.body.replace('&idsite=', '&cdo=' + secondsQueuedAgo + '&idsite='); | |
} | |
fetch(cursor.value.url, init).then(function (response) { | |
console.log('server response', response); | |
if (response.status < 400) { | |
getQueue().then(function (queue) { | |
queue.delete(queueId); | |
}); | |
} | |
}).catch(function (error) { | |
console.error('Send to Server failed:', error); | |
throw error | |
}) | |
} | |
else { | |
console.log("No more entries!"); | |
} | |
}; | |
}); | |
} | |
function limitQueueIfNeeded(queue) | |
{ | |
var countRequest = queue.count(); | |
countRequest.onsuccess = function(event) { | |
if (event.result > maxLimitQueue) { | |
// we delete only one at a time because of concurrency some other process might delete data too | |
queue.openCursor().onsuccess = function(event) { | |
var cursor = event.target.result; | |
if (cursor) { | |
queue.delete(cursor.value.id); | |
limitQueueIfNeeded(queue); | |
} | |
} | |
} | |
} | |
} | |
self.addEventListener('sync', function(event) { | |
if (event.tag === 'matomoSync') { | |
syncQueue(); | |
} | |
}); | |
self.addEventListener('fetch', function (event) { | |
let isOnline = navigator.onLine; | |
let isTrackingRequest = (event.request.url.includes('/matomo.php') | |
|| event.request.url.includes('/piwik.php')); | |
let isTrackerRequest = event.request.url.endsWith('/matomo.js') | |
|| event.request.url.endsWith('/piwik.js'); | |
if (isTrackerRequest) { | |
if (isOnline) { | |
syncQueue(); | |
} | |
caches.open('matomo').then(function(cache) { | |
return cache.match(event.request).then(function (response) { | |
return response || fetch(event.request).then(function(response) { | |
cache.put(event.request, response.clone()); | |
return response; | |
}); | |
}); | |
}) | |
} else if (isTrackingRequest && isOnline) { | |
syncQueue(); | |
event.respondWith(fetch(event.request)); | |
} else if (isTrackingRequest && !isOnline) { | |
var headers = {}; | |
for (const [header, value] of event.request.headers) { | |
headers[header] = value; | |
} | |
let requestInfo = { | |
url: event.request.url, | |
referrer : event.request.referrer, | |
method : event.request.method, | |
referrerPolicy : event.request.referrerPolicy, | |
headers : headers, | |
created: Date.now() | |
}; | |
event.request.text().then(function (postData) { | |
requestInfo.body = postData; | |
getQueue().then(function (queue) { | |
queue.add(requestInfo); | |
limitQueueIfNeeded(queue); | |
return queue; | |
}); | |
}); | |
} | |
}); | |
} | |
}; |