UNPKG

@logtail/next

Version:

Better Stack Telemetry Next.js client

54 lines (44 loc) 1.7 kB
import { NextWebVitalsMetric } from 'next/app'; import { config, isBrowser, isVercel, Version } from '../config'; import { throttle } from '../shared'; const url = config.getWebVitalsEndpoint(); export declare type WebVitalsMetric = NextWebVitalsMetric & { route: string }; const throttledSendMetrics = throttle(sendMetrics, 1000); let collectedMetrics: WebVitalsMetric[] = []; export function reportWebVitalsWithPath(metric: NextWebVitalsMetric, route: string) { collectedMetrics.push({ route, ...metric }); // if env vars are not set, do nothing, // otherwise devs will get errors on dev environments if (!config.isEnvVarsSet()) { return; } throttledSendMetrics(); } function sendMetrics() { const body = JSON.stringify(config.wrapWebVitalsObject(collectedMetrics)); const headers: HeadersInit = { 'Content-Type': 'application/json', 'User-Agent': 'next-logtail/v' + Version, }; if (config.token) { headers['Authorization'] = `Bearer ${config.token}`; } const reqOptions: RequestInit = { body, method: 'POST', keepalive: true, headers }; function sendFallback() { // Do not leak network errors; does not affect the running app fetch(url, reqOptions).catch(console.error); } if (isBrowser && isVercel && navigator.sendBeacon) { try { // See https://github.com/vercel/next.js/pull/26601 // Navigator has to be bound to ensure it does not error in some browsers // https://xgwang.me/posts/you-may-not-know-beacon/#it-may-throw-error%2C-be-sure-to-catch navigator.sendBeacon.bind(navigator)(url, body); } catch (err) { sendFallback(); } } else { sendFallback(); } collectedMetrics = []; }