UNPKG

@zendesk/retrace

Version:

define and capture Product Operation Traces along with computed metrics with an optional friendly React beacon API

74 lines 3.3 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.generateUseBeacon = void 0; const react_1 = require("react"); const ErrorBoundary_1 = require("../ErrorBoundary"); /** * The job of the beacon: * emit component-render-start, component-render, component-unmount entries * (or hook-render-start, hook-render, hook-unmount based on the isHook option) */ const generateUseBeacon = (traceManager) => ({ isHook = false, ...config }) => { const renderCountRef = (0, react_1.useRef)(0); renderCountRef.current += 1; const { attributes, renderedOutput } = config; const status = config.error ? 'error' : 'ok'; const isIdle = config.isIdle ?? (renderedOutput === 'content' || renderedOutput === 'error'); const relatedTo = config.relatedTo; const parentSpanRef = (0, react_1.useRef)(); if (config.parentSpan) { parentSpanRef.current = config.parentSpan; } const renderStartEntry = traceManager.startRenderSpan({ ...config, kind: isHook ? 'hook' : 'component', relatedTo, attributes, status, renderCount: renderCountRef.current, isIdle, parentSpan: parentSpanRef.current, }); const renderStartRef = (0, react_1.useRef)(renderStartEntry); renderStartRef.current = renderStartEntry; // Beacon effect for tracking 'component-render'. This will fire after every render as it does not have any dependencies: (0, react_1.useEffect)(() => { const maybeNewParent = renderStartRef.current.resolveParent(true); parentSpanRef.current = maybeNewParent ?? parentSpanRef.current; const currentTrace = traceManager.currentTraceContext; if (currentTrace && !currentTrace.recordedItems.has(renderStartRef.current.span.id)) { // handle edge case where the component mounted before the trace was started renderStartRef.current = traceManager.createAndProcessSpan({ ...renderStartRef.current.span, parentSpan: parentSpanRef.current, // if startTime is before the trace start time, we set it to undefined // to ensure the span is added to the trace startTime: renderStartRef.current.span.startTime.now < currentTrace.input.startTime.now ? undefined : renderStartRef.current.span.startTime, }); } traceManager.endRenderSpan(renderStartRef.current.span); }); // Beacon effect for tracking 'component-unmount' entries (0, ErrorBoundary_1.useOnComponentUnmount)((errorBoundaryMetadata) => { traceManager.createAndProcessSpan({ ...config, relatedTo, type: isHook ? 'hook-unmount' : 'component-unmount', attributes, error: errorBoundaryMetadata?.error, errorInfo: errorBoundaryMetadata?.errorInfo, status: errorBoundaryMetadata?.error ? 'error' : 'ok', renderCount: renderCountRef.current, isIdle, parentSpan: renderStartRef.current?.span, }); }, [config.name]); return renderStartEntry; }; exports.generateUseBeacon = generateUseBeacon; //# sourceMappingURL=hooks.js.map