@grafana/faro-core
Version:
Core package of Faro.
66 lines • 2.43 kB
JavaScript
const DEFAULT_SEND_TIMEOUT_MS = 250;
const DEFAULT_BATCH_ITEM_LIMIT = 50;
export class BatchExecutor {
constructor(sendFn, options) {
var _a, _b;
this.signalBuffer = [];
this.itemLimit = (_a = options === null || options === void 0 ? void 0 : options.itemLimit) !== null && _a !== void 0 ? _a : DEFAULT_BATCH_ITEM_LIMIT;
this.sendTimeout = (_b = options === null || options === void 0 ? void 0 : options.sendTimeout) !== null && _b !== void 0 ? _b : DEFAULT_SEND_TIMEOUT_MS;
this.paused = (options === null || options === void 0 ? void 0 : options.paused) || false;
this.sendFn = sendFn;
this.flushInterval = -1;
if (!this.paused) {
this.start();
}
// Send batched/buffered data when user navigates to new page, switches or closes the tab, minimizes or closes the browser.
// If on mobile, it also sends data if user switches from the browser to a different app.
document.addEventListener('visibilitychange', () => {
if (document.visibilityState === 'hidden') {
this.flush();
}
});
}
addItem(item) {
if (this.paused) {
return;
}
this.signalBuffer.push(item);
if (this.signalBuffer.length >= this.itemLimit) {
this.flush();
}
}
start() {
this.paused = false;
if (this.sendTimeout > 0) {
this.flushInterval = window.setInterval(() => this.flush(), this.sendTimeout);
}
}
pause() {
this.paused = true;
clearInterval(this.flushInterval);
}
groupItems(items) {
const itemMap = new Map();
items.forEach((item) => {
const metaKey = JSON.stringify(item.meta);
let currentItems = itemMap.get(metaKey);
if (currentItems === undefined) {
currentItems = [item];
}
else {
currentItems = [...currentItems, item];
}
itemMap.set(metaKey, currentItems);
});
return Array.from(itemMap.values());
}
flush() {
if (this.paused || this.signalBuffer.length === 0) {
return;
}
const itemGroups = this.groupItems(this.signalBuffer);
itemGroups.forEach(this.sendFn);
this.signalBuffer = [];
}
}
//# sourceMappingURL=batchExecutor.js.map