@groundcover/browser 0.0.35 → 0.0.36

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1 +1 @@
1
- "use strict";var e=require("fflate"),t=require("error-stack-parser"),n=require("web-vitals");function s(e){return e&&e.__esModule?e:{default:e}}var i=s(t),r=console.log.bind(console),o=class e{constructor(){this.isDebugEnabled=!1,this.prefix=""}static initialize(t){return e.instance||(e.instance=new e),t&&(e.instance.isDebugEnabled=t.debug??!1,e.instance.prefix=t.prefix??""),e.instance}static getInstance(t){return e?.instance||e.initialize(t)}formatMessage(e){return`[${(new Date).toISOString()}] ${this.prefix} ${e}`}log(e,...t){this.isDebugEnabled&&r(this.formatMessage(e),...t)}updateConfig(e){this.isDebugEnabled=e.debug??this.isDebugEnabled,this.prefix=e.prefix??this.prefix}},a=o.getInstance();function l(e){a.log("[error-handler.handleError] called",e,{groundcoverIgnore:!0})}var c={batchSize:10,batchTimeout:1e4,eventSampleRate:1,sessionSampleRate:1,environment:"development",debug:!1,enableCompression:!0,maskFields:[],enabledEvents:[],tracePropagationUrls:[]},h=class{constructor(e){this.dsn=e.dsn,this.appId=e.appId,this.cluster=e.cluster,this.apiKey=e.apiKey,this.environment=e.environment,this.namespace=e.namespace,this.userIdentifier=e.userIdentifier||null,this.options={...c,...e.options}}getEndpoint(){return this.dsn}},d=class{constructor(){this.generateTraceId=g(16),this.generateSpanId=g(8),this.generateId=g(16)}},u=Array(32);function g(e){return function(){for(let t=0;t<2*e;t++)u[t]=Math.floor(16*Math.random())+48,u[t]>=58&&(u[t]+=39);return String.fromCharCode.apply(null,u.slice(0,2*e))}}var p=class e{constructor(){this.config=null,this.logger=o.getInstance(),this.sessionId=null,this.idGenerator=new d}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(e){this.config||(this.config=new h(e))}getConfig(){return this.config?this.config:(this.logger.log("[config-manager] configuration not initialized"),null)}getSessionId(){if(this.sessionId)return this.sessionId;const e=globalThis?.sessionStorage?.getItem("gcId");return e||""}setSessionId(e){this.sessionId=e,globalThis?.sessionStorage?.setItem("gcId",e)}updateConfig(e){this.logger.log("[config-manager] updateConfig called"),this.config?(e?.options&&(this.logger.log("[config-manager] updating options"),this.config.options={...this.config.options,...e.options}),e?.userIdentifier&&(this.logger.log("[config-manager] updating user identifier"),this.config.userIdentifier={...this.config.userIdentifier,...e.userIdentifier})):this.logger.log("[config-manager] configuration not initialized")}},m="object"==typeof globalThis?globalThis:"object"==typeof self?self:"object"==typeof window?window:"object"==typeof global?global:{},f=p.getInstance(),v=new d;function y(){const e=f?.getConfig()?.options?.eventSampleRate;return!(void 0!==e&&!Number.isNaN(e))||Math.random()<=e}function E(e,t=""){return Object.entries(e).reduce(((e,[n,s])=>{const i=t?`${t}.${n}`:n;return"object"==typeof s&&null!==s?Object.assign(e,E(s,i)):e[i]=s,e}),{})}function b(e){const t=1e6*Date.now(),n=v.generateId(),s=e.spanId||v.generateSpanId(),i=e.traceId||v.generateTraceId(),r=e.parentSpanId||"",o=E(e.attributes||{}),a=function(){const e=m?.location;return e?{path:e.hash&&!e.hash.match(/^#[a-z0-9-]+$/i)&&e.hash.startsWith("#/")?e.hash:e.pathname,url:e.href,title:m?.document?.title||""}:{path:"",url:"",title:m?.document?.title||""}}(),l={type:e.type,id:n,spanId:s,parentSpanId:r,traceId:i,attributes:{...o,location:a}};return e.span_name&&(l.span_name=e.span_name),"network"===e.type?(l.start_timestamp=e.timestamp||t,l.end_timestamp=e?.end_timestamp):l.timestamp=t,l}var w=class{constructor(){this.logger=o.getInstance(),this.config=p.getInstance()}compress(t){const n=this.config.getConfig();if(!n?.options?.enableCompression)return{data:(new TextEncoder).encode(t),isCompressed:!1};try{const n=e.strToU8(t);return{data:e.gzipSync(n),isCompressed:!0}}catch(e){return{data:(new TextEncoder).encode(t),isCompressed:!1}}}async send(e){const t=this.config.getConfig();if(t)try{t?.options?.debug&&this.logger.log("Sending batch:",e,{groundcoverIgnore:!0});const n=t.apiKey,s=this.buildEndpoint();if(!n)return void this.logger.log("No API key found");const i=JSON.stringify(e),{data:r,isCompressed:o}=this.compress(i);fetch(s,{method:"POST",headers:{"Content-Type":"application/json",apikey:n,"Content-Encoding":o?"gzip":""},body:r}).catch((e=>{this.logger.log("Network error while sending batch:",e,{groundcoverIgnore:!0})}))}catch(e){t.options.debug&&this.logger.log("Failed to send batch:",e,{groundcoverIgnore:!0})}}buildEndpoint(){const e=this.config.getConfig();if(!e)return"";const{dsn:t}=e;return`${t}/json/rum`}},I=class e{constructor(){this.events=[],this.timeoutId=null,this.config=p.getInstance(),this.initialized=!1,this.transporter=new w}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(){try{if(this.initialized)return;this.scheduleFlush(),globalThis.addEventListener("unload",(()=>{this.flush()})),this.initialized=!0}catch(e){l(e)}}addEvent(e){if(e&&this.initialized)try{const t=this.config.getConfig()?.options?.beforeSend;if(t&&!t(e))return;this.events.push(e);const n=this.config.getConfig()?.options?.batchSize||100;this.events.length>=n&&"dom.event"!==e.type&&this.flush()}catch(e){l(e)}}flush(){try{if(0===this.events.length||!this.initialized)return;this.transporter.send({sessionAttributes:this.getSessionAttributes(),events:this.events}),this.events=[],this.scheduleFlush()}catch(e){l(e)}}scheduleFlush(){try{null!==this.timeoutId&&(m.clearTimeout(this.timeoutId),this.timeoutId=null);const e=this.config.getConfig()?.options?.batchTimeout;if(!e)return;this.timeoutId=m.setTimeout((()=>{this.timeoutId=null,this.flush()}),e)}catch(e){l(e)}}detectBrowser(){const e=navigator.userAgent;let t="unknown",n="unknown";const s=navigator.platform||"unknown",i=/Mobile|Android|iPhone|iPad|iPod/i.test(e);return/Edg/.test(e)?(t="Edge",n=e.match(/Edg\/([\d.]+)/)?.[1]||n):/Chrome/.test(e)&&!/Chromium/.test(e)?(t="Chrome",n=e.match(/Chrome\/([\d.]+)/)?.[1]||n):/Firefox/.test(e)?(t="Firefox",n=e.match(/Firefox\/([\d.]+)/)?.[1]||n):/Safari/.test(e)&&!/Chrome/.test(e)?(t="Safari",n=e.match(/Version\/([\d.]+)/)?.[1]||n):/Trident/.test(e)?(t="Internet Explorer",n=/rv:([^)]+)\)/i.test(e)?e.match(/rv:([^)]+)\)/i)?.[1]||n:e.match(/MSIE ([^;]+)/)?.[1]||n):/OPR/.test(e)&&(t="Opera",n=e.match(/OPR\/([\d.]+)/)?.[1]||n),{name:t,version:n,platform:s,language:navigator.language,mobile:i}}getSessionAttributes(){const e=this.detectBrowser();return{cluster:this.config.getConfig()?.cluster||"",env:this.config.getConfig()?.environment||"",namespace:this.config.getConfig()?.namespace||"",session_id:this.config.getSessionId(),user:this.config.getConfig()?.userIdentifier||{},"service.name":this.config.getConfig()?.appId,userAgent:navigator.userAgent,browser:e}}};I.instance=null;var L=I,T=class{constructor(){this.logger=o.getInstance(),this.eventsPool=L.getInstance()}};function C({text:e,maxLength:t=1e4}){return e?e.length<=t||"string"!=typeof e?e:e.substring(0,t):""}var S,_=class extends T{constructor(){super(...arguments),this.eventHandlers=[],this.capturedEvents=["click","change","keydown","select","submit"],this.getShouldMaskText=e=>["password"===e.target?.type,e.target?.id?.toLowerCase().includes("password"),e.target?.id?.toLowerCase().includes("credit-card"),e.target?.id?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.getAttribute("data-private")].some((e=>e)),this.getKeyCode=e=>{if(e instanceof KeyboardEvent&&e.code&&"Dead"!==e.key){const t=this.getShouldMaskText({target:e.target});return t||t?"*":e.key}return""},this.getText=e=>C({text:e.target.innerText||""}),this.getSelector=e=>e.target instanceof Element&&this.generateSelector(e.target)||"",this.getCoordinates=e=>{if({mouseup:!0,mousedown:!0,mousemove:!0,mouseover:!0}[e.type]){const{clientX:t,clientY:n}=e||{};return{clientX:t,clientY:n}}return null}}initialize(){try{this.logger.log("[dom-events-listener.initialize] called"),this.capturedEvents?.forEach((e=>{const t=e=>{try{this.handleEvent(e)}catch(e){l(e)}};this.eventHandlers.push({type:e,handler:t}),m?.addEventListener(e,t)}))}catch(e){l(e)}}destroy(){this.eventHandlers.forEach((({type:e,handler:t})=>{global?.removeEventListener?.(e,t)})),this.eventHandlers=[]}handleEvent(e){try{if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}}buildEvent(e){const t=this.getSelector(e),n=this.getCoordinates(e),s=e.target,i=this.getKeyCode(e),r=this.getText(e);this.logger.log("[dom-events-listener.buildEvent] called");return b({type:"dom.event",attributes:{dom_event_selector:t,dom_event_key_code:i,dom_event_type:e.type,dom_event_coordinates:n||{clientX:0,clientY:0},dom_event_target:{id:s.id,tagName:s.tagName,className:s.className,text:r}}})}queueEvent(e){try{this.logger.log("[dom-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}generateSelector(e,t={}){if(!e||!e.nodeType||e.nodeType!==Node.ELEMENT_NODE)return"";const n=t.root||document.body||document.documentElement,s=t.maxAttempts||10,i=t.priorityAttributes||["id","class","name","aria-label","type","title","alt"];if("html"===e.tagName?.toLowerCase())return"html";let r="",o=0,a=e;const l=[];for(;a&&a!==n&&a!==document.documentElement&&o<s;){let e=a.tagName?.toLowerCase()||"";try{const t=a.getAttribute("id");if(t&&/^[a-zA-Z][\w-]*$/.test(t))return`#${t}`;if(a.classList?.length){const t=Array.from(a.classList).filter((e=>e&&"string"==typeof e)).map((e=>`.${e}`));t.length&&(e+=t.join(""))}for(const t of i)if("id"!==t&&"class"!==t)try{const n=a.getAttribute(t);n&&(e+=`[${t}="${n.replace(/"/g,'\\"')}"]`)}catch(e){}}catch(t){e=a.tagName?.toLowerCase()||"*"}l.unshift(e||"*"),r=l.join(" > ");try{if(1===n.querySelectorAll(r).length)return r}catch(e){l.shift(),r=l.join(" > ")}try{a=a.parentElement}catch(e){break}o++}return r||"*"}},q=["log","info","warn","error","assert","trace"],z=class extends T{constructor(){super(...arguments),this.originalConsole=null,this.isInitialized=!1}initialize(){if(!this.isInitialized)try{this.originalConsole=this.captureConsoleMethods(),q.forEach((e=>{e in console&&(console[e]=(...t)=>{try{this.handleEvent(t,e)}catch(e){l(e)}finally{this.originalConsole?.[e]&&this.originalConsole[e](...t)}})})),this.isInitialized=!0}catch(e){l(e)}}destroy(){try{if(!this.isInitialized)return;q.forEach((e=>{this.originalConsole&&this.originalConsole[e]&&(console[e]=this.originalConsole[e])})),this.isInitialized=!1}catch(e){l(e)}}handleEvent(e,t){try{if(!y())return;const n=this.formatMessage(Array.isArray(e)?e:[e]);if(!n||n?.includes("groundcoverIgnore"))return;const s=this.buildEvent({message:n,level:t});this.queueEvent(s)}catch(e){l(e)}}buildEvent({message:e,level:t}){return b({type:"log",attributes:{message:C({text:e}),level:t}})}queueEvent(e){try{this.logger.log("[logs-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}formatMessage(e){if(!Array.isArray(e))return String(e);try{return e.map((e=>{if(void 0===e)return"undefined";if(null===e)return"null";if("object"==typeof e)try{return JSON.stringify(e)}catch{return Object.prototype.toString.call(e)}return String(e)})).join(" ")}catch(e){return l(e),"[Error formatting console message]"}}captureConsoleMethods(){const e={};try{q.forEach((t=>{console&&"function"==typeof console[t]&&(e[t]=console[t].bind(console))}))}catch(e){l(e)}return e}},x=class extends T{constructor(){super(...arguments),this.maxBodyLength=5e3,this.config=p.getInstance(),this.idGenerator=new d,this.handleEvent=e=>{try{if(this.shouldIgnoreRequest(e.url))return;if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}},this.buildEvent=e=>{let t=e.url,n=e.url;this.logger.log("[network-events-listener.buildEvent] called",{event:e});try{t=new URL(e.url).pathname}catch(t){n=new URL(e.url,globalThis.location.href).href}this.logger.log("[network-events-listener.buildEvent] fullUrl",{fullUrl:n});const s=this.formatHeaders(e.request.headers),i=this.formatHeaders(e.response.headers),r=e.method?.toUpperCase()||"UNKNOWN",o=e.request.headers.traceparent,a=o?.split("-")?.[1]||"",l=o?.split("-")?.[2]||"",c={type:"HTTP",operation:{name:r},resource_name:t,status:e.status?.toString(),subType:r,url:{full:n},http:{route:t,path:t,method:e.method,status:e.status?.toString(),request:{headers:s,method:e.method},response:{headers:i,status_code:e.status?.toString()}},error:e?.error?.type?{type:e.error?.type||"Unknown error"}:void 0,gc:{request:{body:C({text:e.request.body,maxLength:this.maxBodyLength})},response:{body:C({text:e.response.body,maxLength:this.maxBodyLength})}}};return b({type:"network",timestamp:e?.timestamp&&!Number.isNaN(e.timestamp)?1e6*e.timestamp:void 0,end_timestamp:e?.end_time&&!Number.isNaN(e.end_time)?1e6*e.end_time:void 0,span_name:`${e.method} ${t}`,attributes:c,traceId:a,spanId:l})}}initialize(){this.logger.log("[network-events-listener.initialize] called"),this.patchXHR(),this.patchFetch()}destroy(){globalThis.XMLHttpRequest.prototype.open=globalThis.XMLHttpRequest.prototype.open,globalThis.XMLHttpRequest.prototype.send=globalThis.XMLHttpRequest.prototype.send,globalThis.fetch=globalThis.fetch}shouldIgnoreRequest(e){try{const t=this.config.getConfig()?.getEndpoint();if(t&&e.includes(t))return!0;if([".tsx",".jsx",".css"].some((t=>e.toLowerCase().endsWith(t))))return!0;return(this.config.getConfig()?.options?.excludedUrls||[]).some((t=>{if(t instanceof RegExp)return t.test(e);if("string"==typeof t&&(t.includes("*")||t.includes("?"))){const n=t.replace(/[.+?^${}()|[\]\\]/g,"\\$&").replace(/\*/g,".*").replace(/\?/g,".");return new RegExp(n).test(e)}return e===t}))}catch(e){return l(e),!1}}queueEvent(e){try{this.logger.log("[network-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}patchXHR(){const e=this,t=globalThis.XMLHttpRequest.prototype.open,n=globalThis.XMLHttpRequest.prototype.send,s=globalThis.XMLHttpRequest.prototype.setRequestHeader;let i;globalThis.XMLHttpRequest.prototype.open=function(n,s,r=!0,o,a){if(i=Date.now(),e.shouldIgnoreRequest(s.toString()))return t.apply(this,[n,s,r,o,a]);const l=new URL(s.toString(),globalThis.location.href).href;return this._requestMethod=n,this._requestUrl=l,this._requestHeaders={},t.apply(this,[n,s,r,o,a])},globalThis.XMLHttpRequest.prototype.setRequestHeader=function(e,t){return this._requestHeaders&&(this._requestHeaders[e]=t),s.apply(this,[e,t])},globalThis.XMLHttpRequest.prototype.send=function(...t){const s=this._requestUrl?.toString();if(!s||e.shouldIgnoreRequest(s))return n.apply(this,t);if(e.shouldAddTraceHeader(s)){const t=e.getTraceparentHeader();t&&(this.setRequestHeader("traceparent",t.traceparent),this._requestHeaders.traceparent=t.traceparent)}return this._requestBody=t[0]||"",this.addEventListener("load",(()=>{const t=Date.now(),n={};this.getAllResponseHeaders().split(/\r?\n/).forEach((e=>{const[t,s]=e.split(": ");t&&s&&(n[t.trim()]=s.trim())}));const s={timestamp:i,end_time:t,method:this._requestMethod,url:this._requestUrl,body:this._requestBody,status:this.status,request:{headers:this._requestHeaders||{},body:this._requestBody},response:{headers:n,body:this.responseText||this.response||""}};e.handleEvent(s)})),n.apply(this,t)}}patchFetch(){const e=globalThis.fetch;globalThis.fetch=(...t)=>{const n=Date.now();let[s,i]=t;i={...i||{}};const r=i?.method||"GET",o=i?.body||"",a=s instanceof Request?s.url:s.toString();if(this.shouldIgnoreRequest(a))return e.apply(globalThis,t);const l=this.shouldAddTraceHeader(a);if(i&&!i.headers&&(i.headers={}),i||(t[1]={},i=t[1]),l){const e=this.getTraceparentHeader();e&&(i?.headers instanceof Headers?i.headers.set("traceparent",e.traceparent):i.headers={...i.headers,traceparent:e.traceparent})}const c={};return i?.headers&&(i.headers instanceof Headers?i.headers.forEach(((e,t)=>{c[t]=e})):"object"==typeof i.headers&&Object.assign(c,i.headers)),e.apply(globalThis,t).then((async e=>{const t=Date.now(),s=e.clone();let i="";const l={};s.headers.forEach(((e,t)=>{l[t]=e}));try{i="text/event-stream"===l["content-type"]?"[unreadable response body]":await s.text()}catch(e){i="[unreadable response body]"}this.logger.log("[network-events-listener.patchFetch] called",{url:a});const h={method:r,url:a,timestamp:n,body:o.toString(),status:s.status,end_time:t,request:{headers:c,body:o.toString()},response:{headers:l,body:i}};return this.handleEvent(h),e})).catch((e=>{const t=Date.now();let n="NetworkError";const s=e.message||"Unknown network error";e instanceof TypeError&&s.includes("Failed to fetch")?n="ERR_NETWORK_FAILURE":s.includes("Name not resolved")?n="ERR_NAME_NOT_RESOLVED":s.includes("Connection refused")&&(n="ERR_CONNECTION_REFUSED");const i={method:r,url:a,body:o.toString(),status:0,end_time:t,request:{headers:c,body:o.toString()},response:{headers:{},body:""},error:{type:n}};throw this.handleEvent(i),e}))}}formatHeaders(e){const t=["authorization","cookie","set-cookie"];return Object.entries(e)?.reduce(((e,[n,s])=>{const i=n.toLowerCase();return t.includes(i)||/(token|key|secret|password)/i.test(i)?e[n]="[REDACTED]":e[n]=C({text:s}),e}),{})}getTraceparentHeader(){const e=this.idGenerator.generateSpanId(),t=this.idGenerator.generateTraceId();return{traceparent:`00-${t}-${e}-01`,traceId:t,spanId:e}}shouldAddTraceHeader(e){const t=this.config.getConfig();if(this.logger.log("[network-events-listener.shouldAddTraceHeader] called",{url:e,config:t}),!t||!t.options.tracePropagationUrls||!t.options.tracePropagationUrls?.length)return!1;const n=t.options.tracePropagationUrls.some((t=>{const n=t.replace(/\*/g,".*"),s=new RegExp(`^${n}$`),i=e.startsWith("/")?new URL(e,globalThis.location.href).pathname:e;return s.test(i)}));return this.logger.log("[network-events-listener.shouldAddTraceHeader] result",{url:e,result:n}),n}},R=class extends T{constructor(){super(...arguments),this.handleEvent=(e,t)=>{this.logger.log("[errors-events-listener.handleEvent] called");try{let n;if(e instanceof Error)n=e,this.enhanceError(n);else if(e instanceof ErrorEvent){if(n=e.error||new Error(e.message||"Unknown error"),/Script error\.?/.test(n.message))return;this.enhanceError(n,e)}else{if(!(e instanceof PromiseRejectionEvent))return;n=this.createUnhandledRejectionError(e)}const s=this.buildEvent(n,t);this.queueEvent(s)}catch(e){l(e)}}}initialize(){m?.addEventListener("error",this.handleEvent),m?.addEventListener("unhandledrejection",this.handleEvent)}destroy(){m?.removeEventListener("error",this.handleEvent),m?.removeEventListener("unhandledrejection",this.handleEvent)}buildEvent(e,t){return b({type:"exception",attributes:{error_type:e.name||"Error",error_message:e.message||"Unknown error",error_stacktrace:this.buildStackTrace(e),error_fingerprint:`${e.name}:${C({text:e.message,maxLength:400})}`,error_handled:t?.handled||!1}})}queueEvent(e){try{this.logger.log("[errors-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}enhanceError(e,t){const{filename:n,lineno:s,colno:i}=t||{};n&&!e.fileName&&Object.defineProperty(e,"fileName",{value:n}),s&&!e.lineNumber&&Object.defineProperty(e,"lineNumber",{value:s}),i&&!e.columnNumber&&Object.defineProperty(e,"columnNumber",{value:i})}createUnhandledRejectionError(e){let t;if(e.reason instanceof Error)t=e.reason;else{const n="object"==typeof e.reason?JSON.stringify(e.reason,null,2):String(e.reason);t=new Error(n),t.name="UnhandledRejection",Object.defineProperty(t,"originalReason",{value:e.reason,enumerable:!1})}return t}buildStackTrace(e){if(!e)return[];try{return i.default.parse(e).map((e=>({filename:e.fileName||"unknown",function:e.functionName||"anonymous",lineno:e.lineNumber||0,colno:e.columnNumber||0})))}catch(e){return[]}}},N=class extends T{constructor(){super(...arguments),this.currentUrl=globalThis.location.href,this.mutationObserver=null}initialize(){if(m.MutationObserver){const e=m.document.querySelector("body");e&&(this.mutationObserver=new MutationObserver((()=>{this.handleUrlChange()})),this.mutationObserver.observe(e,{childList:!0,subtree:!0,attributes:!0}))}m?.addEventListener("popstate",(()=>{this.handleUrlChange()}))}destroy(){this.mutationObserver?.disconnect(),this.mutationObserver=null}handleEvent(){try{this.logger.log("[navigation-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){l(e)}}buildEvent(){this.logger.log("[navigation-listener.buildEvent] called",globalThis.location.href);return b({type:"navigation",attributes:{page_url:globalThis.location.href}})}queueEvent(e){try{this.logger.log("[navigation-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}handleUrlChange(){this.logger.log("[navigation-listener.handleUrlChange] called");const e=new URL(globalThis.location.href),t=new URL(this.currentUrl),n=e=>e.startsWith("#/"),s=n(e.hash)||n(t.hash);(e.pathname!==t.pathname||s&&e.hash!==t.hash)&&(this.currentUrl=globalThis.location.href,this.handleEvent())}},k=class extends T{constructor(){super(),this.startTime=performance.now()}initialize(){try{this.logger.log("[page-load-listener.initialize] called"),m?.addEventListener("load",(()=>{this.handleEvent()}))}catch(e){l(e)}}destroy(){m?.removeEventListener("load",this.handleEvent)}handleEvent(){try{this.logger.log("[page-load-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){l(e)}}buildEvent(){const e=performance.now()-this.startTime,t=performance.getEntriesByType("resource"),n={count:t.length,totalSize:0,totalDuration:0,byType:{}};t.forEach((e=>{const t=e,s=t.transferSize||0,i=t.duration,r=t.initiatorType;n.totalSize+=s,n.totalDuration+=i,n.byType[r]||(n.byType[r]={count:0,size:0,duration:0}),n.byType[r].count++,n.byType[r].size+=s,n.byType[r].duration+=i}));return b({type:"pageload",attributes:{page_url:m?.location?.href||"",page_load_time:e,page_referrer:m?.document?.referrer||"",page_resources:n}})}queueEvent(e){try{this.logger.log("[page-load-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}},U=class extends T{constructor(){super(...arguments),this.handleEvent=e=>{try{if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}}}initialize(){n.onCLS(this.handleEvent),n.onLCP(this.handleEvent),n.onFCP(this.handleEvent),n.onTTFB(this.handleEvent),n.onINP(this.handleEvent)}destroy(){}buildEvent(e){return b({type:"performance",attributes:{performance_metric_name:e.name,performance_metric_value:e.value,performance_metric_id:e.id,performance_metric_navigation_type:e.navigationType||""}})}queueEvent(e){try{this.logger.log("[performance-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}},H=class{constructor(){this.logger=o.getInstance(),this.eventsPool=L.getInstance(),this.configManager=p.getInstance(),this.logEventsListener=null,this.domEventsListener=null,this.errorsEventsListener=null,this.networkEventsListener=null,this.navigationListener=null,this.performanceListener=null,this.pageLoadListener=null}instrument(){this.logger.log("[instrumentation-manager.instrument] called");const e=this.configManager.getConfig(),t=e?.options?.enabledEvents,n=!t||0===t.length,s=[];(n||t?.includes("pageload"))&&(this.pageLoadListener=new k,this.pageLoadListener.initialize(),s.push("pageload")),(n||t?.includes("dom"))&&(this.domEventsListener=new _,this.domEventsListener.initialize(),s.push("dom")),(n||t?.includes("logs"))&&(this.logEventsListener=new z,this.logEventsListener.initialize(),s.push("logs")),(n||t?.includes("exceptions"))&&(this.errorsEventsListener=new R,this.errorsEventsListener.initialize(),s.push("exceptions")),(n||t?.includes("network"))&&(this.networkEventsListener=new x,this.networkEventsListener.initialize(),s.push("network")),(n||t?.includes("navigation"))&&(this.navigationListener=new N,this.navigationListener.initialize(),s.push("navigation")),(n||t?.includes("performance"))&&(this.performanceListener=new U,this.performanceListener.initialize(),s.push("performance")),this.logger.log("[instrumentation-manager.instrument] initialized listeners based on config:",s)}sendCustomEvent(e){this.logger.log("[instrumentation-manager.sendCustomEvent] called",e);try{const t=b({type:"custom",attributes:{custom_event_name:e?.event,custom_event_attributes:e?.attributes}});this.eventsPool.addEvent(t)}catch(e){l(e)}}captureException(e){try{this.logger.log("[instrumentation-manager.captureException] called",e),this.errorsEventsListener?.handleEvent(e,{handled:!0})}catch(e){l(e)}}uninstrument(){this.domEventsListener?.destroy(),this.logEventsListener?.destroy(),this.errorsEventsListener?.destroy(),this.networkEventsListener?.destroy(),this.navigationListener?.destroy(),this.performanceListener?.destroy(),this.pageLoadListener?.destroy()}},M="gcSample",O=class{constructor(e){this.initialized=!1,this.logger=o.initialize({debug:e.options?.debug||!1,prefix:"[groundcover]"}),this.logger.log("[session-manager] initialize called"),this.instrumentationManager=new H,this.idGenerator=new d;if(!this.getSamplingDecision(e.options?.sessionSampleRate))return void this.logger.log("[session-manager] session is not sampled");if(this.initialized)return void this.logger.log("[session-manager] SDK already initialized");const t=p.getInstance();t.initialize(e);L.getInstance().initialize();t.getSessionId()||t.setSessionId(this.idGenerator.generateId()),this.instrumentationManager.instrument(),this.initialized=!0}getSamplingDecision(e){try{if(!e||1===e)return!0;const t=globalThis.sessionStorage?.getItem(M);if(t){const e="1"===t;return this.logger.log("[session-manager] using stored sampling decision:",e),e}const n=!e||Math.random()<e;return globalThis?.sessionStorage?.setItem(M,n?"1":"0"),this.logger.log("[session-manager] stored new sampling decision:",n),n}catch(t){this.logger.log("[session-manager] session storage access failed:",t);const n=!e||Math.random()<e;return this.logger.log("[session-manager] using fallback sampling decision:",n),n}}identifyUser(e){if(this.logger.log("[session-manager] identifyUser called"),!this.initialized)return void this.logger.log("[session-manager] cannot identify user: SDK not initialized");p.getInstance().updateConfig({userIdentifier:e})}sendCustomEvent(e){this.initialized?this.instrumentationManager.sendCustomEvent(e):this.logger.log("[session-manager] cannot send custom event: SDK not initialized")}captureException(e){this.initialized?this.instrumentationManager.captureException(e):this.logger.log("[session-manager] Cannot capture exception: SDK not initialized")}destroy(){this.initialized&&(this.instrumentationManager.uninstrument(),globalThis.sessionStorage?.removeItem("gcId"),this.initialized=!1)}};var j={init:function(e){try{S=new O({cluster:e?.cluster,environment:e?.environment,namespace:e?.namespace,dsn:e?.dsn,appId:e?.appId,userIdentifier:e?.userIdentifier,apiKey:e?.apiKey,options:e?.options})}catch(e){l(e)}},identifyUser:function(e){S?S.identifyUser(e):console.warn("[groundcover] identifyUser: groundcover is not initialized. please call init() first")},sendCustomEvent:function(e){S&&S.sendCustomEvent(e)},captureException:function(e){S&&S.captureException(e)}};module.exports=j;
1
+ "use strict";var e=require("fflate"),t=require("error-stack-parser"),n=require("web-vitals");function i(e){return e&&e.__esModule?e:{default:e}}var s=i(t),r=console.log.bind(console),o=class e{constructor(){this.isDebugEnabled=!1,this.prefix=""}static initialize(t){return e.instance||(e.instance=new e),t&&(e.instance.isDebugEnabled=t.debug??!1,e.instance.prefix=t.prefix??""),e.instance}static getInstance(t){return e?.instance||e.initialize(t)}formatMessage(e){return`[${(new Date).toISOString()}] ${this.prefix} ${e}`}log(e,...t){this.isDebugEnabled&&r(this.formatMessage(e),...t)}updateConfig(e){this.isDebugEnabled=e.debug??this.isDebugEnabled,this.prefix=e.prefix??this.prefix}},a=o.getInstance();function l(e){a.log("[error-handler.handleError] called",e,{groundcoverIgnore:!0})}var c={batchSize:10,batchTimeout:1e4,eventSampleRate:1,sessionSampleRate:1,environment:"development",debug:!1,enableCompression:!0,maskFields:[],enabledEvents:[],tracePropagationUrls:[]},h=class{constructor(e){this.dsn=e.dsn,this.appId=e.appId,this.cluster=e.cluster,this.apiKey=e.apiKey,this.environment=e.environment,this.namespace=e.namespace,this.userIdentifier=e.userIdentifier||null,this.options={...c,...e.options}}getEndpoint(){return this.dsn}},d=class{constructor(){this.generateTraceId=u(16),this.generateSpanId=u(8),this.generateId=u(16)}},g=Array(32);function u(e){return function(){for(let t=0;t<2*e;t++)g[t]=Math.floor(16*Math.random())+48,g[t]>=58&&(g[t]+=39);return String.fromCharCode.apply(null,g.slice(0,2*e))}}var p=class e{constructor(){this.config=null,this.logger=o.getInstance(),this.sessionId=null,this.idGenerator=new d}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(e){this.config||(this.config=new h(e))}getConfig(){return this.config?this.config:(this.logger.log("[config-manager] configuration not initialized"),null)}getSessionId(){if(this.sessionId)return this.sessionId;const e=globalThis?.sessionStorage?.getItem("gcId");return e||""}setSessionId(e){this.sessionId=e,globalThis?.sessionStorage?.setItem("gcId",e)}updateConfig(e){this.logger.log("[config-manager] updateConfig called"),this.config?(e?.options&&(this.logger.log("[config-manager] updating options"),this.config.options={...this.config.options,...e.options}),e?.userIdentifier&&(this.logger.log("[config-manager] updating user identifier"),this.config.userIdentifier={...this.config.userIdentifier,...e.userIdentifier})):this.logger.log("[config-manager] configuration not initialized")}},m="object"==typeof globalThis?globalThis:"object"==typeof self?self:"object"==typeof window?window:"object"==typeof global?global:{},f=p.getInstance(),v=new d;function y(){const e=f?.getConfig()?.options?.eventSampleRate;return!(void 0!==e&&!Number.isNaN(e))||Math.random()<=e}function E(e,t=""){return Object.entries(e).reduce(((e,[n,i])=>{const s=t?`${t}.${n}`:n;return"object"==typeof i&&null!==i?Object.assign(e,E(i,s)):e[s]=i,e}),{})}function b(e){const t=1e6*Date.now(),n=v.generateId(),i=e.spanId||v.generateSpanId(),s=e.traceId||v.generateTraceId(),r=e.parentSpanId||"",o=E(e.attributes||{}),a=function(){const e=m?.location;return e?{path:e.hash&&!e.hash.match(/^#[a-z0-9-]+$/i)&&e.hash.startsWith("#/")?e.hash:e.pathname,url:e.href,title:m?.document?.title||""}:{path:"",url:"",title:m?.document?.title||""}}(),l={type:e.type,id:n,spanId:i,parentSpanId:r,traceId:s,attributes:{...o,location:a}};return e.span_name&&(l.span_name=e.span_name),"network"===e.type?(l.start_timestamp=e.timestamp||t,l.end_timestamp=e?.end_timestamp):l.timestamp=t,l}var I=class{constructor(){this.logger=o.getInstance(),this.config=p.getInstance()}compress(t){const n=this.config.getConfig();if(!n?.options?.enableCompression)return{data:(new TextEncoder).encode(t),isCompressed:!1};try{const n=e.strToU8(t);return{data:e.gzipSync(n),isCompressed:!0}}catch(e){return{data:(new TextEncoder).encode(t),isCompressed:!1}}}async send(e){const t=this.config.getConfig();if(t)try{t?.options?.debug&&this.logger.log("Sending batch:",e,{groundcoverIgnore:!0});const n=t.apiKey,i=this.buildEndpoint();if(!n)return void this.logger.log("No API key found");const s=JSON.stringify(e),{data:r,isCompressed:o}=this.compress(s);fetch(i,{method:"POST",headers:{"Content-Type":"application/json",apikey:n,"Content-Encoding":o?"gzip":""},body:r}).catch((e=>{this.logger.log("Network error while sending batch:",e,{groundcoverIgnore:!0})}))}catch(e){t.options.debug&&this.logger.log("Failed to send batch:",e,{groundcoverIgnore:!0})}}buildEndpoint(){const e=this.config.getConfig();if(!e)return"";const{dsn:t}=e;return`${t}/json/rum`}},w=["navigation","dom.event"],L=class e{constructor(){this.events=[],this.timeoutId=null,this.config=p.getInstance(),this.initialized=!1,this.transporter=new I}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(){try{if(this.initialized)return;this.scheduleFlush(),globalThis.addEventListener("unload",(()=>{this.flush()})),this.initialized=!0}catch(e){l(e)}}addEvent(e){if(e&&this.initialized)try{const t=this.config.getConfig()?.options?.beforeSend;if(t&&!t(e))return;this.events.push(e);const n=this.config.getConfig()?.options?.batchSize||100;this.events.length>=n&&!w.includes(e.type)&&this.flush()}catch(e){l(e)}}flush(){try{if(!this.events?.length||!this.initialized)return;this.transporter.send({sessionAttributes:this.getSessionAttributes(),events:this.events}),this.events=[],this.scheduleFlush()}catch(e){l(e)}}scheduleFlush(){try{null!==this.timeoutId&&(m.clearTimeout(this.timeoutId),this.timeoutId=null);const e=this.config.getConfig()?.options?.batchTimeout;if(!e)return;this.timeoutId=m.setTimeout((()=>{this.timeoutId=null,this.flush()}),e)}catch(e){l(e)}}detectBrowser(){const e=navigator.userAgent;let t="unknown",n="unknown";const i=navigator.platform||"unknown",s=/Mobile|Android|iPhone|iPad|iPod/i.test(e);return/Edg/.test(e)?(t="Edge",n=e.match(/Edg\/([\d.]+)/)?.[1]||n):/Chrome/.test(e)&&!/Chromium/.test(e)?(t="Chrome",n=e.match(/Chrome\/([\d.]+)/)?.[1]||n):/Firefox/.test(e)?(t="Firefox",n=e.match(/Firefox\/([\d.]+)/)?.[1]||n):/Safari/.test(e)&&!/Chrome/.test(e)?(t="Safari",n=e.match(/Version\/([\d.]+)/)?.[1]||n):/Trident/.test(e)?(t="Internet Explorer",n=/rv:([^)]+)\)/i.test(e)?e.match(/rv:([^)]+)\)/i)?.[1]||n:e.match(/MSIE ([^;]+)/)?.[1]||n):/OPR/.test(e)&&(t="Opera",n=e.match(/OPR\/([\d.]+)/)?.[1]||n),{name:t,version:n,platform:i,language:navigator.language,mobile:s}}getSessionAttributes(){const e=this.detectBrowser();return{cluster:this.config.getConfig()?.cluster||"",env:this.config.getConfig()?.environment||"",namespace:this.config.getConfig()?.namespace||"",session_id:this.config.getSessionId(),user:this.config.getConfig()?.userIdentifier||{},"service.name":this.config.getConfig()?.appId,userAgent:navigator.userAgent,browser:e}}};L.instance=null;var S=L,C=class{constructor(){this.logger=o.getInstance(),this.eventsPool=S.getInstance()}};function T({text:e,maxLength:t=1e4}){return e?e.length<=t||"string"!=typeof e?e:e.substring(0,t):""}var _,z=class extends C{constructor(){super(...arguments),this.eventHandlers=[],this.capturedEvents=["click","change","keydown","select","submit"],this.getShouldMaskText=e=>["password"===e.target?.type,e.target?.id?.toLowerCase().includes("password"),e.target?.id?.toLowerCase().includes("credit-card"),e.target?.id?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.getAttribute("data-private")].some((e=>e)),this.getKeyCode=e=>{if(e instanceof KeyboardEvent&&e.code&&"Dead"!==e.key){const t=this.getShouldMaskText({target:e.target});return t||t?"*":e.key}return""},this.getText=e=>T({text:e.target.innerText||""}),this.getSelector=e=>e.target instanceof Element&&this.generateSelector(e.target)||"",this.getCoordinates=e=>{if({mouseup:!0,mousedown:!0,mousemove:!0,mouseover:!0}[e.type]){const{clientX:t,clientY:n}=e||{};return{clientX:t,clientY:n}}return null}}initialize(){try{this.logger.log("[dom-events-listener.initialize] called"),this.capturedEvents?.forEach((e=>{const t=e=>{try{this.handleEvent(e)}catch(e){l(e)}};this.eventHandlers.push({type:e,handler:t}),m?.addEventListener(e,t)}))}catch(e){l(e)}}destroy(){this.eventHandlers.forEach((({type:e,handler:t})=>{global?.removeEventListener?.(e,t)})),this.eventHandlers=[]}handleEvent(e){try{if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}}buildEvent(e){const t=this.getSelector(e),n=this.getCoordinates(e),i=e.target,s=this.getKeyCode(e),r=this.getText(e);this.logger.log("[dom-events-listener.buildEvent] called");return b({type:"dom.event",attributes:{dom_event_selector:t,dom_event_key_code:s,dom_event_type:e.type,dom_event_coordinates:n||{clientX:0,clientY:0},dom_event_target:{id:i.id,tagName:i.tagName,className:i.className,text:r}}})}queueEvent(e){try{this.logger.log("[dom-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}generateSelector(e,t={}){if(!e||!e.nodeType||e.nodeType!==Node.ELEMENT_NODE)return"";const n=t.root||document.body||document.documentElement,i=t.maxAttempts||10,s=t.priorityAttributes||["id","class","name","aria-label","type","title","alt"];if("html"===e.tagName?.toLowerCase())return"html";let r="",o=0,a=e;const l=[];for(;a&&a!==n&&a!==document.documentElement&&o<i;){let e=a.tagName?.toLowerCase()||"";try{const t=a.getAttribute("id");if(t&&/^[a-zA-Z][\w-]*$/.test(t))return`#${t}`;if(a.classList?.length){const t=Array.from(a.classList).filter((e=>e&&"string"==typeof e)).map((e=>`.${e}`));t.length&&(e+=t.join(""))}for(const t of s)if("id"!==t&&"class"!==t)try{const n=a.getAttribute(t);n&&(e+=`[${t}="${n.replace(/"/g,'\\"')}"]`)}catch(e){}}catch(t){e=a.tagName?.toLowerCase()||"*"}l.unshift(e||"*"),r=l.join(" > ");try{if(1===n.querySelectorAll(r).length)return r}catch(e){l.shift(),r=l.join(" > ")}try{a=a.parentElement}catch(e){break}o++}return r||"*"}},q=["log","info","warn","error","assert","trace"],x=class extends C{constructor(){super(...arguments),this.originalConsole=null,this.isInitialized=!1}initialize(){if(!this.isInitialized)try{this.originalConsole=this.captureConsoleMethods(),q.forEach((e=>{e in console&&(console[e]=(...t)=>{try{this.handleEvent(t,e)}catch(e){l(e)}finally{this.originalConsole?.[e]&&this.originalConsole[e](...t)}})})),this.isInitialized=!0}catch(e){l(e)}}destroy(){try{if(!this.isInitialized)return;q.forEach((e=>{this.originalConsole&&this.originalConsole[e]&&(console[e]=this.originalConsole[e])})),this.isInitialized=!1}catch(e){l(e)}}handleEvent(e,t){try{if(!y())return;const n=this.formatMessage(Array.isArray(e)?e:[e]);if(!n||n?.includes("groundcoverIgnore"))return;const i=this.buildEvent({message:n,level:t});this.queueEvent(i)}catch(e){l(e)}}buildEvent({message:e,level:t}){return b({type:"log",attributes:{message:T({text:e}),level:t}})}queueEvent(e){try{this.logger.log("[logs-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}formatMessage(e){if(!Array.isArray(e))return String(e);try{return e.map((e=>{if(void 0===e)return"undefined";if(null===e)return"null";if("object"==typeof e)try{return JSON.stringify(e)}catch{return Object.prototype.toString.call(e)}return String(e)})).join(" ")}catch(e){return l(e),"[Error formatting console message]"}}captureConsoleMethods(){const e={};try{q.forEach((t=>{console&&"function"==typeof console[t]&&(e[t]=console[t].bind(console))}))}catch(e){l(e)}return e}},R=class extends C{constructor(){super(...arguments),this.maxBodyLength=5e3,this.config=p.getInstance(),this.idGenerator=new d,this.handleEvent=e=>{try{if(this.shouldIgnoreRequest(e.url))return;if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}},this.buildEvent=e=>{let t=e.url,n=e.url;this.logger.log("[network-events-listener.buildEvent] called",{event:e});try{t=new URL(e.url).pathname}catch(t){n=new URL(e.url,globalThis.location.href).href}this.logger.log("[network-events-listener.buildEvent] fullUrl",{fullUrl:n});const i=this.formatHeaders(e.request.headers),s=this.formatHeaders(e.response.headers),r=e.method?.toUpperCase()||"UNKNOWN",o=e.request.headers.traceparent,a=o?.split("-")?.[1]||"",l=o?.split("-")?.[2]||"",c={type:"HTTP",operation:{name:r},resource_name:t,status:e.status?.toString(),subType:r,url:{full:n},http:{route:t,path:t,method:e.method,status:e.status?.toString(),request:{headers:i,method:e.method},response:{headers:s,status_code:e.status?.toString()}},error:e?.error?.type?{type:e.error?.type||"Unknown error"}:void 0,gc:{request:{body:T({text:e.request.body,maxLength:this.maxBodyLength})},response:{body:T({text:e.response.body,maxLength:this.maxBodyLength})}}};return b({type:"network",timestamp:e?.timestamp&&!Number.isNaN(e.timestamp)?1e6*e.timestamp:void 0,end_timestamp:e?.end_time&&!Number.isNaN(e.end_time)?1e6*e.end_time:void 0,span_name:`${e.method} ${t}`,attributes:c,traceId:a,spanId:l})}}initialize(){this.logger.log("[network-events-listener.initialize] called"),this.patchXHR(),this.patchFetch()}destroy(){globalThis.XMLHttpRequest.prototype.open=globalThis.XMLHttpRequest.prototype.open,globalThis.XMLHttpRequest.prototype.send=globalThis.XMLHttpRequest.prototype.send,globalThis.fetch=globalThis.fetch}shouldIgnoreRequest(e){try{const t=this.config.getConfig()?.getEndpoint();if(t&&e.includes(t))return!0;if([".tsx",".jsx",".css"].some((t=>e.toLowerCase().endsWith(t))))return!0;return(this.config.getConfig()?.options?.excludedUrls||[]).some((t=>{if(t instanceof RegExp)return t.test(e);if("string"==typeof t&&(t.includes("*")||t.includes("?"))){const n=t.replace(/[.+?^${}()|[\]\\]/g,"\\$&").replace(/\*/g,".*").replace(/\?/g,".");return new RegExp(n).test(e)}return e===t}))}catch(e){return l(e),!1}}queueEvent(e){try{this.logger.log("[network-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}patchXHR(){const e=this,t=globalThis.XMLHttpRequest.prototype.open,n=globalThis.XMLHttpRequest.prototype.send,i=globalThis.XMLHttpRequest.prototype.setRequestHeader;let s;globalThis.XMLHttpRequest.prototype.open=function(n,i,r=!0,o,a){if(s=Date.now(),e.shouldIgnoreRequest(i.toString()))return t.apply(this,[n,i,r,o,a]);const l=new URL(i.toString(),globalThis.location.href).href;return this._requestMethod=n,this._requestUrl=l,this._requestHeaders={},t.apply(this,[n,i,r,o,a])},globalThis.XMLHttpRequest.prototype.setRequestHeader=function(e,t){return this._requestHeaders&&(this._requestHeaders[e]=t),i.apply(this,[e,t])},globalThis.XMLHttpRequest.prototype.send=function(...t){const i=this._requestUrl?.toString();if(!i||e.shouldIgnoreRequest(i))return n.apply(this,t);if(e.shouldAddTraceHeader(i)){const t=e.getTraceparentHeader();t&&(this.setRequestHeader("traceparent",t.traceparent),this._requestHeaders.traceparent=t.traceparent)}return this._requestBody=t[0]||"",this.addEventListener("load",(()=>{const t=Date.now(),n={};this.getAllResponseHeaders().split(/\r?\n/).forEach((e=>{const[t,i]=e.split(": ");t&&i&&(n[t.trim()]=i.trim())}));const i={timestamp:s,end_time:t,method:this._requestMethod,url:this._requestUrl,body:this._requestBody,status:this.status,request:{headers:this._requestHeaders||{},body:this._requestBody},response:{headers:n,body:this.responseText||this.response||""}};e.handleEvent(i)})),n.apply(this,t)}}patchFetch(){const e=globalThis.fetch;globalThis.fetch=(...t)=>{const n=Date.now();let[i,s]=t;s={...s||{}};const r=s?.method||"GET",o=s?.body||"",a=i instanceof Request?i.url:i.toString();if(this.shouldIgnoreRequest(a))return e.apply(globalThis,t);const l=this.shouldAddTraceHeader(a);if(s&&!s.headers&&(s.headers={}),s||(t[1]={},s=t[1]),l){const e=this.getTraceparentHeader();e&&(s?.headers instanceof Headers?s.headers.set("traceparent",e.traceparent):s.headers={...s.headers,traceparent:e.traceparent})}const c={};return s?.headers&&(s.headers instanceof Headers?s.headers.forEach(((e,t)=>{c[t]=e})):"object"==typeof s.headers&&Object.assign(c,s.headers)),e.apply(globalThis,t).then((async e=>{const t=Date.now(),i=e.clone();let s="";const l={};i.headers.forEach(((e,t)=>{l[t]=e}));try{s="text/event-stream"===l["content-type"]?"[unreadable response body]":await i.text()}catch(e){s="[unreadable response body]"}this.logger.log("[network-events-listener.patchFetch] called",{url:a});const h={method:r,url:a,timestamp:n,body:o.toString(),status:i.status,end_time:t,request:{headers:c,body:o.toString()},response:{headers:l,body:s}};return this.handleEvent(h),e})).catch((e=>{const t=Date.now();let n="NetworkError";const i=e.message||"Unknown network error";e instanceof TypeError&&i.includes("Failed to fetch")?n="ERR_NETWORK_FAILURE":i.includes("Name not resolved")?n="ERR_NAME_NOT_RESOLVED":i.includes("Connection refused")&&(n="ERR_CONNECTION_REFUSED");const s={method:r,url:a,body:o.toString(),status:0,end_time:t,request:{headers:c,body:o.toString()},response:{headers:{},body:""},error:{type:n}};throw this.handleEvent(s),e}))}}formatHeaders(e){const t=["authorization","cookie","set-cookie"];return Object.entries(e)?.reduce(((e,[n,i])=>{const s=n.toLowerCase();return t.includes(s)||/(token|key|secret|password)/i.test(s)?e[n]="[REDACTED]":e[n]=T({text:i}),e}),{})}getTraceparentHeader(){const e=this.idGenerator.generateSpanId(),t=this.idGenerator.generateTraceId();return{traceparent:`00-${t}-${e}-01`,traceId:t,spanId:e}}shouldAddTraceHeader(e){const t=this.config.getConfig();if(this.logger.log("[network-events-listener.shouldAddTraceHeader] called",{url:e,config:t}),!t||!t.options.tracePropagationUrls||!t.options.tracePropagationUrls?.length)return!1;const n=t.options.tracePropagationUrls.some((t=>{const n=t.replace(/\*/g,".*"),i=new RegExp(`^${n}$`),s=e.startsWith("/")?new URL(e,globalThis.location.href).pathname:e;return i.test(s)}));return this.logger.log("[network-events-listener.shouldAddTraceHeader] result",{url:e,result:n}),n}},N=class extends C{constructor(){super(...arguments),this.handleEvent=(e,t)=>{this.logger.log("[errors-events-listener.handleEvent] called");try{let n;if(e instanceof Error)n=e,this.enhanceError(n);else if(e instanceof ErrorEvent){if(n=e.error||new Error(e.message||"Unknown error"),/Script error\.?/.test(n.message))return;this.enhanceError(n,e)}else{if(!(e instanceof PromiseRejectionEvent))return;n=this.createUnhandledRejectionError(e)}const i=this.buildEvent(n,t);this.queueEvent(i)}catch(e){l(e)}}}initialize(){m?.addEventListener("error",this.handleEvent),m?.addEventListener("unhandledrejection",this.handleEvent)}destroy(){m?.removeEventListener("error",this.handleEvent),m?.removeEventListener("unhandledrejection",this.handleEvent)}buildEvent(e,t){return b({type:"exception",attributes:{error_type:e.name||"Error",error_message:e.message||"Unknown error",error_stacktrace:this.buildStackTrace(e),error_fingerprint:`${e.name}:${T({text:e.message,maxLength:400})}`,error_handled:t?.handled||!1}})}queueEvent(e){try{this.logger.log("[errors-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}enhanceError(e,t){const{filename:n,lineno:i,colno:s}=t||{};n&&!e.fileName&&Object.defineProperty(e,"fileName",{value:n}),i&&!e.lineNumber&&Object.defineProperty(e,"lineNumber",{value:i}),s&&!e.columnNumber&&Object.defineProperty(e,"columnNumber",{value:s})}createUnhandledRejectionError(e){let t;if(e.reason instanceof Error)t=e.reason;else{const n="object"==typeof e.reason?JSON.stringify(e.reason,null,2):String(e.reason);t=new Error(n),t.name="UnhandledRejection",Object.defineProperty(t,"originalReason",{value:e.reason,enumerable:!1})}return t}buildStackTrace(e){if(!e)return[];try{return s.default.parse(e).map((e=>({filename:e.fileName||"unknown",function:e.functionName||"anonymous",lineno:e.lineNumber||0,colno:e.columnNumber||0})))}catch(e){return[]}}},k=class extends C{constructor(){if(super(),this.currentUrl="",this.originalPushState=null,this.originalReplaceState=null,this.isInitialized=!1,this.popStateHandler=()=>{this.handleLocationChange()},this.hashChangeHandler=()=>{this.handleLocationChange()},this.isInBrowserEnvironment())try{this.currentUrl=m.location.href,this.originalPushState=history.pushState,this.originalReplaceState=history.replaceState}catch(e){l(e)}}isInBrowserEnvironment(){try{return void 0!==m&&void 0!==m.location&&void 0!==m.history&&"function"==typeof m.addEventListener}catch(e){return l(e),!1}}initialize(){try{if(this.logger.log("[navigation-listener.initialize] called"),!this.isInBrowserEnvironment()||!this.originalPushState||!this.originalReplaceState)return void this.logger.log("[navigation-listener.initialize] Browser environment not available, skipping initialization");const e=this.originalPushState,t=this.originalReplaceState;history.pushState=(...t)=>{const n=e.apply(history,t);return this.handleLocationChange(),n},history.replaceState=(...e)=>{const n=t.apply(history,e);return this.handleLocationChange(),n},m&&"function"==typeof m.addEventListener&&(m.addEventListener("popstate",this.popStateHandler),m.addEventListener("hashchange",this.hashChangeHandler)),this.isInitialized=!0}catch(e){l(e)}}destroy(){try{this.logger.log("[navigation-listener.destroy] called"),this.isInitialized&&this.originalPushState&&this.originalReplaceState&&(history.pushState=this.originalPushState,history.replaceState=this.originalReplaceState),m&&"function"==typeof m.removeEventListener&&(m.removeEventListener("popstate",this.popStateHandler),m.removeEventListener("hashchange",this.hashChangeHandler)),this.isInitialized=!1}catch(e){l(e)}}handleEvent(){try{this.logger.log("[navigation-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){l(e)}}buildEvent(){this.logger.log("[navigation-listener.buildEvent] called",m.location.href);return b({type:"navigation",attributes:{page_url:m.location.href}})}queueEvent(e){try{this.logger.log("[navigation-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}handleLocationChange(){try{if(!this.isInitialized)return;if(this.logger.log("[navigation-listener.handleLocationChange] called"),this.currentUrl===m.location.href)return;let e,t;try{e=new URL(m.location.href),t=new URL(this.currentUrl)}catch(e){return void l(e)}const n=e=>e.startsWith("#/"),i=n(e.hash)||n(t.hash);(e.pathname!==t.pathname||i&&e.hash!==t.hash)&&(this.currentUrl=m.location.href,this.handleEvent())}catch(e){l(e)}}},H=class extends C{constructor(){super(),this.startTime=performance.now()}initialize(){try{this.logger.log("[page-load-listener.initialize] called"),m?.addEventListener("load",(()=>{this.handleEvent()}))}catch(e){l(e)}}destroy(){m?.removeEventListener("load",this.handleEvent)}handleEvent(){try{this.logger.log("[page-load-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){l(e)}}buildEvent(){const e=performance.now()-this.startTime,t=performance.getEntriesByType("resource"),n={count:t.length,totalSize:0,totalDuration:0,byType:{}};t.forEach((e=>{const t=e,i=t.transferSize||0,s=t.duration,r=t.initiatorType;n.totalSize+=i,n.totalDuration+=s,n.byType[r]||(n.byType[r]={count:0,size:0,duration:0}),n.byType[r].count++,n.byType[r].size+=i,n.byType[r].duration+=s}));return b({type:"pageload",attributes:{page_url:m?.location?.href||"",page_load_time:e,page_referrer:m?.document?.referrer||"",page_resources:n}})}queueEvent(e){try{this.logger.log("[page-load-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}},U=class extends C{constructor(){super(...arguments),this.handleEvent=e=>{try{if(!y())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){l(e)}}}initialize(){n.onCLS(this.handleEvent),n.onLCP(this.handleEvent),n.onFCP(this.handleEvent),n.onTTFB(this.handleEvent),n.onINP(this.handleEvent)}destroy(){}buildEvent(e){return b({type:"performance",attributes:{performance_metric_name:e.name,performance_metric_value:e.value,performance_metric_id:e.id,performance_metric_navigation_type:e.navigationType||""}})}queueEvent(e){try{this.logger.log("[performance-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){l(e)}}},M=class{constructor(){this.logger=o.getInstance(),this.eventsPool=S.getInstance(),this.configManager=p.getInstance(),this.logEventsListener=null,this.domEventsListener=null,this.errorsEventsListener=null,this.networkEventsListener=null,this.navigationListener=null,this.performanceListener=null,this.pageLoadListener=null}instrument(){this.logger.log("[instrumentation-manager.instrument] called");const e=this.configManager.getConfig(),t=e?.options?.enabledEvents,n=!t||0===t.length,i=[];(n||t?.includes("pageload"))&&(this.pageLoadListener=new H,this.pageLoadListener.initialize(),i.push("pageload")),(n||t?.includes("dom"))&&(this.domEventsListener=new z,this.domEventsListener.initialize(),i.push("dom")),(n||t?.includes("logs"))&&(this.logEventsListener=new x,this.logEventsListener.initialize(),i.push("logs")),(n||t?.includes("exceptions"))&&(this.errorsEventsListener=new N,this.errorsEventsListener.initialize(),i.push("exceptions")),(n||t?.includes("network"))&&(this.networkEventsListener=new R,this.networkEventsListener.initialize(),i.push("network")),(n||t?.includes("navigation"))&&(this.navigationListener=new k,this.navigationListener.initialize(),i.push("navigation")),(n||t?.includes("performance"))&&(this.performanceListener=new U,this.performanceListener.initialize(),i.push("performance")),this.logger.log("[instrumentation-manager.instrument] initialized listeners based on config:",i)}sendCustomEvent(e){this.logger.log("[instrumentation-manager.sendCustomEvent] called",e);try{const t=b({type:"custom",attributes:{custom_event_name:e?.event,custom_event_attributes:e?.attributes}});this.eventsPool.addEvent(t)}catch(e){l(e)}}captureException(e){try{this.logger.log("[instrumentation-manager.captureException] called",e),this.errorsEventsListener?.handleEvent(e,{handled:!0})}catch(e){l(e)}}uninstrument(){this.domEventsListener?.destroy(),this.logEventsListener?.destroy(),this.errorsEventsListener?.destroy(),this.networkEventsListener?.destroy(),this.navigationListener?.destroy(),this.performanceListener?.destroy(),this.pageLoadListener?.destroy()}},P="gcSample",j=class{constructor(e){this.initialized=!1,this.logger=o.initialize({debug:e.options?.debug||!1,prefix:"[groundcover]"}),this.logger.log("[session-manager] initialize called"),this.instrumentationManager=new M,this.idGenerator=new d;if(!this.getSamplingDecision(e.options?.sessionSampleRate))return void this.logger.log("[session-manager] session is not sampled");if(this.initialized)return void this.logger.log("[session-manager] SDK already initialized");const t=p.getInstance();t.initialize(e);S.getInstance().initialize();t.getSessionId()||t.setSessionId(this.idGenerator.generateId()),this.instrumentationManager.instrument(),this.initialized=!0}getSamplingDecision(e){try{if(!e||1===e)return!0;const t=globalThis.sessionStorage?.getItem(P);if(t){const e="1"===t;return this.logger.log("[session-manager] using stored sampling decision:",e),e}const n=!e||Math.random()<e;return globalThis?.sessionStorage?.setItem(P,n?"1":"0"),this.logger.log("[session-manager] stored new sampling decision:",n),n}catch(t){this.logger.log("[session-manager] session storage access failed:",t);const n=!e||Math.random()<e;return this.logger.log("[session-manager] using fallback sampling decision:",n),n}}identifyUser(e){if(this.logger.log("[session-manager] identifyUser called"),!this.initialized)return void this.logger.log("[session-manager] cannot identify user: SDK not initialized");p.getInstance().updateConfig({userIdentifier:e})}sendCustomEvent(e){this.initialized?this.instrumentationManager.sendCustomEvent(e):this.logger.log("[session-manager] cannot send custom event: SDK not initialized")}captureException(e){this.initialized?this.instrumentationManager.captureException(e):this.logger.log("[session-manager] Cannot capture exception: SDK not initialized")}destroy(){this.initialized&&(this.instrumentationManager.uninstrument(),globalThis.sessionStorage?.removeItem("gcId"),this.initialized=!1)}};var A={init:function(e){try{_=new j({cluster:e?.cluster,environment:e?.environment,namespace:e?.namespace,dsn:e?.dsn,appId:e?.appId,userIdentifier:e?.userIdentifier,apiKey:e?.apiKey,options:e?.options})}catch(e){l(e)}},identifyUser:function(e){_?_.identifyUser(e):console.warn("[groundcover] identifyUser: groundcover is not initialized. please call init() first")},sendCustomEvent:function(e){_&&_.sendCustomEvent(e)},captureException:function(e){_&&_.captureException(e)}};module.exports=A;
package/dist/index.mjs CHANGED
@@ -1 +1 @@
1
- import{strToU8 as e,gzipSync as t}from"fflate";import n from"error-stack-parser";import{onCLS as s,onLCP as i,onFCP as r,onTTFB as o,onINP as a}from"web-vitals";var l=console.log.bind(console),c=class e{constructor(){this.isDebugEnabled=!1,this.prefix=""}static initialize(t){return e.instance||(e.instance=new e),t&&(e.instance.isDebugEnabled=t.debug??!1,e.instance.prefix=t.prefix??""),e.instance}static getInstance(t){return e?.instance||e.initialize(t)}formatMessage(e){return`[${(new Date).toISOString()}] ${this.prefix} ${e}`}log(e,...t){this.isDebugEnabled&&l(this.formatMessage(e),...t)}updateConfig(e){this.isDebugEnabled=e.debug??this.isDebugEnabled,this.prefix=e.prefix??this.prefix}},h=c.getInstance();function d(e){h.log("[error-handler.handleError] called",e,{groundcoverIgnore:!0})}var u={batchSize:10,batchTimeout:1e4,eventSampleRate:1,sessionSampleRate:1,environment:"development",debug:!1,enableCompression:!0,maskFields:[],enabledEvents:[],tracePropagationUrls:[]},g=class{constructor(e){this.dsn=e.dsn,this.appId=e.appId,this.cluster=e.cluster,this.apiKey=e.apiKey,this.environment=e.environment,this.namespace=e.namespace,this.userIdentifier=e.userIdentifier||null,this.options={...u,...e.options}}getEndpoint(){return this.dsn}},p=class{constructor(){this.generateTraceId=f(16),this.generateSpanId=f(8),this.generateId=f(16)}},m=Array(32);function f(e){return function(){for(let t=0;t<2*e;t++)m[t]=Math.floor(16*Math.random())+48,m[t]>=58&&(m[t]+=39);return String.fromCharCode.apply(null,m.slice(0,2*e))}}var v=class e{constructor(){this.config=null,this.logger=c.getInstance(),this.sessionId=null,this.idGenerator=new p}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(e){this.config||(this.config=new g(e))}getConfig(){return this.config?this.config:(this.logger.log("[config-manager] configuration not initialized"),null)}getSessionId(){if(this.sessionId)return this.sessionId;const e=globalThis?.sessionStorage?.getItem("gcId");return e||""}setSessionId(e){this.sessionId=e,globalThis?.sessionStorage?.setItem("gcId",e)}updateConfig(e){this.logger.log("[config-manager] updateConfig called"),this.config?(e?.options&&(this.logger.log("[config-manager] updating options"),this.config.options={...this.config.options,...e.options}),e?.userIdentifier&&(this.logger.log("[config-manager] updating user identifier"),this.config.userIdentifier={...this.config.userIdentifier,...e.userIdentifier})):this.logger.log("[config-manager] configuration not initialized")}},y="object"==typeof globalThis?globalThis:"object"==typeof self?self:"object"==typeof window?window:"object"==typeof global?global:{},E=v.getInstance(),b=new p;function w(){const e=E?.getConfig()?.options?.eventSampleRate;return!(void 0!==e&&!Number.isNaN(e))||Math.random()<=e}function I(e,t=""){return Object.entries(e).reduce(((e,[n,s])=>{const i=t?`${t}.${n}`:n;return"object"==typeof s&&null!==s?Object.assign(e,I(s,i)):e[i]=s,e}),{})}function L(e){const t=1e6*Date.now(),n=b.generateId(),s=e.spanId||b.generateSpanId(),i=e.traceId||b.generateTraceId(),r=e.parentSpanId||"",o=I(e.attributes||{}),a=function(){const e=y?.location;return e?{path:e.hash&&!e.hash.match(/^#[a-z0-9-]+$/i)&&e.hash.startsWith("#/")?e.hash:e.pathname,url:e.href,title:y?.document?.title||""}:{path:"",url:"",title:y?.document?.title||""}}(),l={type:e.type,id:n,spanId:s,parentSpanId:r,traceId:i,attributes:{...o,location:a}};return e.span_name&&(l.span_name=e.span_name),"network"===e.type?(l.start_timestamp=e.timestamp||t,l.end_timestamp=e?.end_timestamp):l.timestamp=t,l}var T=class{constructor(){this.logger=c.getInstance(),this.config=v.getInstance()}compress(n){const s=this.config.getConfig();if(!s?.options?.enableCompression)return{data:(new TextEncoder).encode(n),isCompressed:!1};try{const s=e(n);return{data:t(s),isCompressed:!0}}catch(e){return{data:(new TextEncoder).encode(n),isCompressed:!1}}}async send(e){const t=this.config.getConfig();if(t)try{t?.options?.debug&&this.logger.log("Sending batch:",e,{groundcoverIgnore:!0});const n=t.apiKey,s=this.buildEndpoint();if(!n)return void this.logger.log("No API key found");const i=JSON.stringify(e),{data:r,isCompressed:o}=this.compress(i);fetch(s,{method:"POST",headers:{"Content-Type":"application/json",apikey:n,"Content-Encoding":o?"gzip":""},body:r}).catch((e=>{this.logger.log("Network error while sending batch:",e,{groundcoverIgnore:!0})}))}catch(e){t.options.debug&&this.logger.log("Failed to send batch:",e,{groundcoverIgnore:!0})}}buildEndpoint(){const e=this.config.getConfig();if(!e)return"";const{dsn:t}=e;return`${t}/json/rum`}},C=class e{constructor(){this.events=[],this.timeoutId=null,this.config=v.getInstance(),this.initialized=!1,this.transporter=new T}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(){try{if(this.initialized)return;this.scheduleFlush(),globalThis.addEventListener("unload",(()=>{this.flush()})),this.initialized=!0}catch(e){d(e)}}addEvent(e){if(e&&this.initialized)try{const t=this.config.getConfig()?.options?.beforeSend;if(t&&!t(e))return;this.events.push(e);const n=this.config.getConfig()?.options?.batchSize||100;this.events.length>=n&&"dom.event"!==e.type&&this.flush()}catch(e){d(e)}}flush(){try{if(0===this.events.length||!this.initialized)return;this.transporter.send({sessionAttributes:this.getSessionAttributes(),events:this.events}),this.events=[],this.scheduleFlush()}catch(e){d(e)}}scheduleFlush(){try{null!==this.timeoutId&&(y.clearTimeout(this.timeoutId),this.timeoutId=null);const e=this.config.getConfig()?.options?.batchTimeout;if(!e)return;this.timeoutId=y.setTimeout((()=>{this.timeoutId=null,this.flush()}),e)}catch(e){d(e)}}detectBrowser(){const e=navigator.userAgent;let t="unknown",n="unknown";const s=navigator.platform||"unknown",i=/Mobile|Android|iPhone|iPad|iPod/i.test(e);return/Edg/.test(e)?(t="Edge",n=e.match(/Edg\/([\d.]+)/)?.[1]||n):/Chrome/.test(e)&&!/Chromium/.test(e)?(t="Chrome",n=e.match(/Chrome\/([\d.]+)/)?.[1]||n):/Firefox/.test(e)?(t="Firefox",n=e.match(/Firefox\/([\d.]+)/)?.[1]||n):/Safari/.test(e)&&!/Chrome/.test(e)?(t="Safari",n=e.match(/Version\/([\d.]+)/)?.[1]||n):/Trident/.test(e)?(t="Internet Explorer",n=/rv:([^)]+)\)/i.test(e)?e.match(/rv:([^)]+)\)/i)?.[1]||n:e.match(/MSIE ([^;]+)/)?.[1]||n):/OPR/.test(e)&&(t="Opera",n=e.match(/OPR\/([\d.]+)/)?.[1]||n),{name:t,version:n,platform:s,language:navigator.language,mobile:i}}getSessionAttributes(){const e=this.detectBrowser();return{cluster:this.config.getConfig()?.cluster||"",env:this.config.getConfig()?.environment||"",namespace:this.config.getConfig()?.namespace||"",session_id:this.config.getSessionId(),user:this.config.getConfig()?.userIdentifier||{},"service.name":this.config.getConfig()?.appId,userAgent:navigator.userAgent,browser:e}}};C.instance=null;var S=C,_=class{constructor(){this.logger=c.getInstance(),this.eventsPool=S.getInstance()}};function q({text:e,maxLength:t=1e4}){return e?e.length<=t||"string"!=typeof e?e:e.substring(0,t):""}var x,z=class extends _{constructor(){super(...arguments),this.eventHandlers=[],this.capturedEvents=["click","change","keydown","select","submit"],this.getShouldMaskText=e=>["password"===e.target?.type,e.target?.id?.toLowerCase().includes("password"),e.target?.id?.toLowerCase().includes("credit-card"),e.target?.id?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.getAttribute("data-private")].some((e=>e)),this.getKeyCode=e=>{if(e instanceof KeyboardEvent&&e.code&&"Dead"!==e.key){const t=this.getShouldMaskText({target:e.target});return t||t?"*":e.key}return""},this.getText=e=>q({text:e.target.innerText||""}),this.getSelector=e=>e.target instanceof Element&&this.generateSelector(e.target)||"",this.getCoordinates=e=>{if({mouseup:!0,mousedown:!0,mousemove:!0,mouseover:!0}[e.type]){const{clientX:t,clientY:n}=e||{};return{clientX:t,clientY:n}}return null}}initialize(){try{this.logger.log("[dom-events-listener.initialize] called"),this.capturedEvents?.forEach((e=>{const t=e=>{try{this.handleEvent(e)}catch(e){d(e)}};this.eventHandlers.push({type:e,handler:t}),y?.addEventListener(e,t)}))}catch(e){d(e)}}destroy(){this.eventHandlers.forEach((({type:e,handler:t})=>{global?.removeEventListener?.(e,t)})),this.eventHandlers=[]}handleEvent(e){try{if(!w())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}}buildEvent(e){const t=this.getSelector(e),n=this.getCoordinates(e),s=e.target,i=this.getKeyCode(e),r=this.getText(e);this.logger.log("[dom-events-listener.buildEvent] called");return L({type:"dom.event",attributes:{dom_event_selector:t,dom_event_key_code:i,dom_event_type:e.type,dom_event_coordinates:n||{clientX:0,clientY:0},dom_event_target:{id:s.id,tagName:s.tagName,className:s.className,text:r}}})}queueEvent(e){try{this.logger.log("[dom-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}generateSelector(e,t={}){if(!e||!e.nodeType||e.nodeType!==Node.ELEMENT_NODE)return"";const n=t.root||document.body||document.documentElement,s=t.maxAttempts||10,i=t.priorityAttributes||["id","class","name","aria-label","type","title","alt"];if("html"===e.tagName?.toLowerCase())return"html";let r="",o=0,a=e;const l=[];for(;a&&a!==n&&a!==document.documentElement&&o<s;){let e=a.tagName?.toLowerCase()||"";try{const t=a.getAttribute("id");if(t&&/^[a-zA-Z][\w-]*$/.test(t))return`#${t}`;if(a.classList?.length){const t=Array.from(a.classList).filter((e=>e&&"string"==typeof e)).map((e=>`.${e}`));t.length&&(e+=t.join(""))}for(const t of i)if("id"!==t&&"class"!==t)try{const n=a.getAttribute(t);n&&(e+=`[${t}="${n.replace(/"/g,'\\"')}"]`)}catch(e){}}catch(t){e=a.tagName?.toLowerCase()||"*"}l.unshift(e||"*"),r=l.join(" > ");try{if(1===n.querySelectorAll(r).length)return r}catch(e){l.shift(),r=l.join(" > ")}try{a=a.parentElement}catch(e){break}o++}return r||"*"}},R=["log","info","warn","error","assert","trace"],N=class extends _{constructor(){super(...arguments),this.originalConsole=null,this.isInitialized=!1}initialize(){if(!this.isInitialized)try{this.originalConsole=this.captureConsoleMethods(),R.forEach((e=>{e in console&&(console[e]=(...t)=>{try{this.handleEvent(t,e)}catch(e){d(e)}finally{this.originalConsole?.[e]&&this.originalConsole[e](...t)}})})),this.isInitialized=!0}catch(e){d(e)}}destroy(){try{if(!this.isInitialized)return;R.forEach((e=>{this.originalConsole&&this.originalConsole[e]&&(console[e]=this.originalConsole[e])})),this.isInitialized=!1}catch(e){d(e)}}handleEvent(e,t){try{if(!w())return;const n=this.formatMessage(Array.isArray(e)?e:[e]);if(!n||n?.includes("groundcoverIgnore"))return;const s=this.buildEvent({message:n,level:t});this.queueEvent(s)}catch(e){d(e)}}buildEvent({message:e,level:t}){return L({type:"log",attributes:{message:q({text:e}),level:t}})}queueEvent(e){try{this.logger.log("[logs-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}formatMessage(e){if(!Array.isArray(e))return String(e);try{return e.map((e=>{if(void 0===e)return"undefined";if(null===e)return"null";if("object"==typeof e)try{return JSON.stringify(e)}catch{return Object.prototype.toString.call(e)}return String(e)})).join(" ")}catch(e){return d(e),"[Error formatting console message]"}}captureConsoleMethods(){const e={};try{R.forEach((t=>{console&&"function"==typeof console[t]&&(e[t]=console[t].bind(console))}))}catch(e){d(e)}return e}},k=class extends _{constructor(){super(...arguments),this.maxBodyLength=5e3,this.config=v.getInstance(),this.idGenerator=new p,this.handleEvent=e=>{try{if(this.shouldIgnoreRequest(e.url))return;if(!w())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}},this.buildEvent=e=>{let t=e.url,n=e.url;this.logger.log("[network-events-listener.buildEvent] called",{event:e});try{t=new URL(e.url).pathname}catch(t){n=new URL(e.url,globalThis.location.href).href}this.logger.log("[network-events-listener.buildEvent] fullUrl",{fullUrl:n});const s=this.formatHeaders(e.request.headers),i=this.formatHeaders(e.response.headers),r=e.method?.toUpperCase()||"UNKNOWN",o=e.request.headers.traceparent,a=o?.split("-")?.[1]||"",l=o?.split("-")?.[2]||"",c={type:"HTTP",operation:{name:r},resource_name:t,status:e.status?.toString(),subType:r,url:{full:n},http:{route:t,path:t,method:e.method,status:e.status?.toString(),request:{headers:s,method:e.method},response:{headers:i,status_code:e.status?.toString()}},error:e?.error?.type?{type:e.error?.type||"Unknown error"}:void 0,gc:{request:{body:q({text:e.request.body,maxLength:this.maxBodyLength})},response:{body:q({text:e.response.body,maxLength:this.maxBodyLength})}}};return L({type:"network",timestamp:e?.timestamp&&!Number.isNaN(e.timestamp)?1e6*e.timestamp:void 0,end_timestamp:e?.end_time&&!Number.isNaN(e.end_time)?1e6*e.end_time:void 0,span_name:`${e.method} ${t}`,attributes:c,traceId:a,spanId:l})}}initialize(){this.logger.log("[network-events-listener.initialize] called"),this.patchXHR(),this.patchFetch()}destroy(){globalThis.XMLHttpRequest.prototype.open=globalThis.XMLHttpRequest.prototype.open,globalThis.XMLHttpRequest.prototype.send=globalThis.XMLHttpRequest.prototype.send,globalThis.fetch=globalThis.fetch}shouldIgnoreRequest(e){try{const t=this.config.getConfig()?.getEndpoint();if(t&&e.includes(t))return!0;if([".tsx",".jsx",".css"].some((t=>e.toLowerCase().endsWith(t))))return!0;return(this.config.getConfig()?.options?.excludedUrls||[]).some((t=>{if(t instanceof RegExp)return t.test(e);if("string"==typeof t&&(t.includes("*")||t.includes("?"))){const n=t.replace(/[.+?^${}()|[\]\\]/g,"\\$&").replace(/\*/g,".*").replace(/\?/g,".");return new RegExp(n).test(e)}return e===t}))}catch(e){return d(e),!1}}queueEvent(e){try{this.logger.log("[network-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}patchXHR(){const e=this,t=globalThis.XMLHttpRequest.prototype.open,n=globalThis.XMLHttpRequest.prototype.send,s=globalThis.XMLHttpRequest.prototype.setRequestHeader;let i;globalThis.XMLHttpRequest.prototype.open=function(n,s,r=!0,o,a){if(i=Date.now(),e.shouldIgnoreRequest(s.toString()))return t.apply(this,[n,s,r,o,a]);const l=new URL(s.toString(),globalThis.location.href).href;return this._requestMethod=n,this._requestUrl=l,this._requestHeaders={},t.apply(this,[n,s,r,o,a])},globalThis.XMLHttpRequest.prototype.setRequestHeader=function(e,t){return this._requestHeaders&&(this._requestHeaders[e]=t),s.apply(this,[e,t])},globalThis.XMLHttpRequest.prototype.send=function(...t){const s=this._requestUrl?.toString();if(!s||e.shouldIgnoreRequest(s))return n.apply(this,t);if(e.shouldAddTraceHeader(s)){const t=e.getTraceparentHeader();t&&(this.setRequestHeader("traceparent",t.traceparent),this._requestHeaders.traceparent=t.traceparent)}return this._requestBody=t[0]||"",this.addEventListener("load",(()=>{const t=Date.now(),n={};this.getAllResponseHeaders().split(/\r?\n/).forEach((e=>{const[t,s]=e.split(": ");t&&s&&(n[t.trim()]=s.trim())}));const s={timestamp:i,end_time:t,method:this._requestMethod,url:this._requestUrl,body:this._requestBody,status:this.status,request:{headers:this._requestHeaders||{},body:this._requestBody},response:{headers:n,body:this.responseText||this.response||""}};e.handleEvent(s)})),n.apply(this,t)}}patchFetch(){const e=globalThis.fetch;globalThis.fetch=(...t)=>{const n=Date.now();let[s,i]=t;i={...i||{}};const r=i?.method||"GET",o=i?.body||"",a=s instanceof Request?s.url:s.toString();if(this.shouldIgnoreRequest(a))return e.apply(globalThis,t);const l=this.shouldAddTraceHeader(a);if(i&&!i.headers&&(i.headers={}),i||(t[1]={},i=t[1]),l){const e=this.getTraceparentHeader();e&&(i?.headers instanceof Headers?i.headers.set("traceparent",e.traceparent):i.headers={...i.headers,traceparent:e.traceparent})}const c={};return i?.headers&&(i.headers instanceof Headers?i.headers.forEach(((e,t)=>{c[t]=e})):"object"==typeof i.headers&&Object.assign(c,i.headers)),e.apply(globalThis,t).then((async e=>{const t=Date.now(),s=e.clone();let i="";const l={};s.headers.forEach(((e,t)=>{l[t]=e}));try{i="text/event-stream"===l["content-type"]?"[unreadable response body]":await s.text()}catch(e){i="[unreadable response body]"}this.logger.log("[network-events-listener.patchFetch] called",{url:a});const h={method:r,url:a,timestamp:n,body:o.toString(),status:s.status,end_time:t,request:{headers:c,body:o.toString()},response:{headers:l,body:i}};return this.handleEvent(h),e})).catch((e=>{const t=Date.now();let n="NetworkError";const s=e.message||"Unknown network error";e instanceof TypeError&&s.includes("Failed to fetch")?n="ERR_NETWORK_FAILURE":s.includes("Name not resolved")?n="ERR_NAME_NOT_RESOLVED":s.includes("Connection refused")&&(n="ERR_CONNECTION_REFUSED");const i={method:r,url:a,body:o.toString(),status:0,end_time:t,request:{headers:c,body:o.toString()},response:{headers:{},body:""},error:{type:n}};throw this.handleEvent(i),e}))}}formatHeaders(e){const t=["authorization","cookie","set-cookie"];return Object.entries(e)?.reduce(((e,[n,s])=>{const i=n.toLowerCase();return t.includes(i)||/(token|key|secret|password)/i.test(i)?e[n]="[REDACTED]":e[n]=q({text:s}),e}),{})}getTraceparentHeader(){const e=this.idGenerator.generateSpanId(),t=this.idGenerator.generateTraceId();return{traceparent:`00-${t}-${e}-01`,traceId:t,spanId:e}}shouldAddTraceHeader(e){const t=this.config.getConfig();if(this.logger.log("[network-events-listener.shouldAddTraceHeader] called",{url:e,config:t}),!t||!t.options.tracePropagationUrls||!t.options.tracePropagationUrls?.length)return!1;const n=t.options.tracePropagationUrls.some((t=>{const n=t.replace(/\*/g,".*"),s=new RegExp(`^${n}$`),i=e.startsWith("/")?new URL(e,globalThis.location.href).pathname:e;return s.test(i)}));return this.logger.log("[network-events-listener.shouldAddTraceHeader] result",{url:e,result:n}),n}},H=class extends _{constructor(){super(...arguments),this.handleEvent=(e,t)=>{this.logger.log("[errors-events-listener.handleEvent] called");try{let n;if(e instanceof Error)n=e,this.enhanceError(n);else if(e instanceof ErrorEvent){if(n=e.error||new Error(e.message||"Unknown error"),/Script error\.?/.test(n.message))return;this.enhanceError(n,e)}else{if(!(e instanceof PromiseRejectionEvent))return;n=this.createUnhandledRejectionError(e)}const s=this.buildEvent(n,t);this.queueEvent(s)}catch(e){d(e)}}}initialize(){y?.addEventListener("error",this.handleEvent),y?.addEventListener("unhandledrejection",this.handleEvent)}destroy(){y?.removeEventListener("error",this.handleEvent),y?.removeEventListener("unhandledrejection",this.handleEvent)}buildEvent(e,t){return L({type:"exception",attributes:{error_type:e.name||"Error",error_message:e.message||"Unknown error",error_stacktrace:this.buildStackTrace(e),error_fingerprint:`${e.name}:${q({text:e.message,maxLength:400})}`,error_handled:t?.handled||!1}})}queueEvent(e){try{this.logger.log("[errors-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}enhanceError(e,t){const{filename:n,lineno:s,colno:i}=t||{};n&&!e.fileName&&Object.defineProperty(e,"fileName",{value:n}),s&&!e.lineNumber&&Object.defineProperty(e,"lineNumber",{value:s}),i&&!e.columnNumber&&Object.defineProperty(e,"columnNumber",{value:i})}createUnhandledRejectionError(e){let t;if(e.reason instanceof Error)t=e.reason;else{const n="object"==typeof e.reason?JSON.stringify(e.reason,null,2):String(e.reason);t=new Error(n),t.name="UnhandledRejection",Object.defineProperty(t,"originalReason",{value:e.reason,enumerable:!1})}return t}buildStackTrace(e){if(!e)return[];try{return n.parse(e).map((e=>({filename:e.fileName||"unknown",function:e.functionName||"anonymous",lineno:e.lineNumber||0,colno:e.columnNumber||0})))}catch(e){return[]}}},U=class extends _{constructor(){super(...arguments),this.currentUrl=globalThis.location.href,this.mutationObserver=null}initialize(){if(y.MutationObserver){const e=y.document.querySelector("body");e&&(this.mutationObserver=new MutationObserver((()=>{this.handleUrlChange()})),this.mutationObserver.observe(e,{childList:!0,subtree:!0,attributes:!0}))}y?.addEventListener("popstate",(()=>{this.handleUrlChange()}))}destroy(){this.mutationObserver?.disconnect(),this.mutationObserver=null}handleEvent(){try{this.logger.log("[navigation-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){d(e)}}buildEvent(){this.logger.log("[navigation-listener.buildEvent] called",globalThis.location.href);return L({type:"navigation",attributes:{page_url:globalThis.location.href}})}queueEvent(e){try{this.logger.log("[navigation-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}handleUrlChange(){this.logger.log("[navigation-listener.handleUrlChange] called");const e=new URL(globalThis.location.href),t=new URL(this.currentUrl),n=e=>e.startsWith("#/"),s=n(e.hash)||n(t.hash);(e.pathname!==t.pathname||s&&e.hash!==t.hash)&&(this.currentUrl=globalThis.location.href,this.handleEvent())}},M=class extends _{constructor(){super(),this.startTime=performance.now()}initialize(){try{this.logger.log("[page-load-listener.initialize] called"),y?.addEventListener("load",(()=>{this.handleEvent()}))}catch(e){d(e)}}destroy(){y?.removeEventListener("load",this.handleEvent)}handleEvent(){try{this.logger.log("[page-load-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){d(e)}}buildEvent(){const e=performance.now()-this.startTime,t=performance.getEntriesByType("resource"),n={count:t.length,totalSize:0,totalDuration:0,byType:{}};t.forEach((e=>{const t=e,s=t.transferSize||0,i=t.duration,r=t.initiatorType;n.totalSize+=s,n.totalDuration+=i,n.byType[r]||(n.byType[r]={count:0,size:0,duration:0}),n.byType[r].count++,n.byType[r].size+=s,n.byType[r].duration+=i}));return L({type:"pageload",attributes:{page_url:y?.location?.href||"",page_load_time:e,page_referrer:y?.document?.referrer||"",page_resources:n}})}queueEvent(e){try{this.logger.log("[page-load-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}},O=class extends _{constructor(){super(...arguments),this.handleEvent=e=>{try{if(!w())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}}}initialize(){s(this.handleEvent),i(this.handleEvent),r(this.handleEvent),o(this.handleEvent),a(this.handleEvent)}destroy(){}buildEvent(e){return L({type:"performance",attributes:{performance_metric_name:e.name,performance_metric_value:e.value,performance_metric_id:e.id,performance_metric_navigation_type:e.navigationType||""}})}queueEvent(e){try{this.logger.log("[performance-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}},j=class{constructor(){this.logger=c.getInstance(),this.eventsPool=S.getInstance(),this.configManager=v.getInstance(),this.logEventsListener=null,this.domEventsListener=null,this.errorsEventsListener=null,this.networkEventsListener=null,this.navigationListener=null,this.performanceListener=null,this.pageLoadListener=null}instrument(){this.logger.log("[instrumentation-manager.instrument] called");const e=this.configManager.getConfig(),t=e?.options?.enabledEvents,n=!t||0===t.length,s=[];(n||t?.includes("pageload"))&&(this.pageLoadListener=new M,this.pageLoadListener.initialize(),s.push("pageload")),(n||t?.includes("dom"))&&(this.domEventsListener=new z,this.domEventsListener.initialize(),s.push("dom")),(n||t?.includes("logs"))&&(this.logEventsListener=new N,this.logEventsListener.initialize(),s.push("logs")),(n||t?.includes("exceptions"))&&(this.errorsEventsListener=new H,this.errorsEventsListener.initialize(),s.push("exceptions")),(n||t?.includes("network"))&&(this.networkEventsListener=new k,this.networkEventsListener.initialize(),s.push("network")),(n||t?.includes("navigation"))&&(this.navigationListener=new U,this.navigationListener.initialize(),s.push("navigation")),(n||t?.includes("performance"))&&(this.performanceListener=new O,this.performanceListener.initialize(),s.push("performance")),this.logger.log("[instrumentation-manager.instrument] initialized listeners based on config:",s)}sendCustomEvent(e){this.logger.log("[instrumentation-manager.sendCustomEvent] called",e);try{const t=L({type:"custom",attributes:{custom_event_name:e?.event,custom_event_attributes:e?.attributes}});this.eventsPool.addEvent(t)}catch(e){d(e)}}captureException(e){try{this.logger.log("[instrumentation-manager.captureException] called",e),this.errorsEventsListener?.handleEvent(e,{handled:!0})}catch(e){d(e)}}uninstrument(){this.domEventsListener?.destroy(),this.logEventsListener?.destroy(),this.errorsEventsListener?.destroy(),this.networkEventsListener?.destroy(),this.navigationListener?.destroy(),this.performanceListener?.destroy(),this.pageLoadListener?.destroy()}},A="gcSample",P=class{constructor(e){this.initialized=!1,this.logger=c.initialize({debug:e.options?.debug||!1,prefix:"[groundcover]"}),this.logger.log("[session-manager] initialize called"),this.instrumentationManager=new j,this.idGenerator=new p;if(!this.getSamplingDecision(e.options?.sessionSampleRate))return void this.logger.log("[session-manager] session is not sampled");if(this.initialized)return void this.logger.log("[session-manager] SDK already initialized");const t=v.getInstance();t.initialize(e);S.getInstance().initialize();t.getSessionId()||t.setSessionId(this.idGenerator.generateId()),this.instrumentationManager.instrument(),this.initialized=!0}getSamplingDecision(e){try{if(!e||1===e)return!0;const t=globalThis.sessionStorage?.getItem(A);if(t){const e="1"===t;return this.logger.log("[session-manager] using stored sampling decision:",e),e}const n=!e||Math.random()<e;return globalThis?.sessionStorage?.setItem(A,n?"1":"0"),this.logger.log("[session-manager] stored new sampling decision:",n),n}catch(t){this.logger.log("[session-manager] session storage access failed:",t);const n=!e||Math.random()<e;return this.logger.log("[session-manager] using fallback sampling decision:",n),n}}identifyUser(e){if(this.logger.log("[session-manager] identifyUser called"),!this.initialized)return void this.logger.log("[session-manager] cannot identify user: SDK not initialized");v.getInstance().updateConfig({userIdentifier:e})}sendCustomEvent(e){this.initialized?this.instrumentationManager.sendCustomEvent(e):this.logger.log("[session-manager] cannot send custom event: SDK not initialized")}captureException(e){this.initialized?this.instrumentationManager.captureException(e):this.logger.log("[session-manager] Cannot capture exception: SDK not initialized")}destroy(){this.initialized&&(this.instrumentationManager.uninstrument(),globalThis.sessionStorage?.removeItem("gcId"),this.initialized=!1)}};var D={init:function(e){try{x=new P({cluster:e?.cluster,environment:e?.environment,namespace:e?.namespace,dsn:e?.dsn,appId:e?.appId,userIdentifier:e?.userIdentifier,apiKey:e?.apiKey,options:e?.options})}catch(e){d(e)}},identifyUser:function(e){x?x.identifyUser(e):console.warn("[groundcover] identifyUser: groundcover is not initialized. please call init() first")},sendCustomEvent:function(e){x&&x.sendCustomEvent(e)},captureException:function(e){x&&x.captureException(e)}};export{D as default};
1
+ import{strToU8 as e,gzipSync as t}from"fflate";import n from"error-stack-parser";import{onCLS as i,onLCP as s,onFCP as r,onTTFB as o,onINP as a}from"web-vitals";var l=console.log.bind(console),c=class e{constructor(){this.isDebugEnabled=!1,this.prefix=""}static initialize(t){return e.instance||(e.instance=new e),t&&(e.instance.isDebugEnabled=t.debug??!1,e.instance.prefix=t.prefix??""),e.instance}static getInstance(t){return e?.instance||e.initialize(t)}formatMessage(e){return`[${(new Date).toISOString()}] ${this.prefix} ${e}`}log(e,...t){this.isDebugEnabled&&l(this.formatMessage(e),...t)}updateConfig(e){this.isDebugEnabled=e.debug??this.isDebugEnabled,this.prefix=e.prefix??this.prefix}},h=c.getInstance();function d(e){h.log("[error-handler.handleError] called",e,{groundcoverIgnore:!0})}var g={batchSize:10,batchTimeout:1e4,eventSampleRate:1,sessionSampleRate:1,environment:"development",debug:!1,enableCompression:!0,maskFields:[],enabledEvents:[],tracePropagationUrls:[]},u=class{constructor(e){this.dsn=e.dsn,this.appId=e.appId,this.cluster=e.cluster,this.apiKey=e.apiKey,this.environment=e.environment,this.namespace=e.namespace,this.userIdentifier=e.userIdentifier||null,this.options={...g,...e.options}}getEndpoint(){return this.dsn}},p=class{constructor(){this.generateTraceId=f(16),this.generateSpanId=f(8),this.generateId=f(16)}},m=Array(32);function f(e){return function(){for(let t=0;t<2*e;t++)m[t]=Math.floor(16*Math.random())+48,m[t]>=58&&(m[t]+=39);return String.fromCharCode.apply(null,m.slice(0,2*e))}}var v=class e{constructor(){this.config=null,this.logger=c.getInstance(),this.sessionId=null,this.idGenerator=new p}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(e){this.config||(this.config=new u(e))}getConfig(){return this.config?this.config:(this.logger.log("[config-manager] configuration not initialized"),null)}getSessionId(){if(this.sessionId)return this.sessionId;const e=globalThis?.sessionStorage?.getItem("gcId");return e||""}setSessionId(e){this.sessionId=e,globalThis?.sessionStorage?.setItem("gcId",e)}updateConfig(e){this.logger.log("[config-manager] updateConfig called"),this.config?(e?.options&&(this.logger.log("[config-manager] updating options"),this.config.options={...this.config.options,...e.options}),e?.userIdentifier&&(this.logger.log("[config-manager] updating user identifier"),this.config.userIdentifier={...this.config.userIdentifier,...e.userIdentifier})):this.logger.log("[config-manager] configuration not initialized")}},y="object"==typeof globalThis?globalThis:"object"==typeof self?self:"object"==typeof window?window:"object"==typeof global?global:{},E=v.getInstance(),b=new p;function I(){const e=E?.getConfig()?.options?.eventSampleRate;return!(void 0!==e&&!Number.isNaN(e))||Math.random()<=e}function w(e,t=""){return Object.entries(e).reduce(((e,[n,i])=>{const s=t?`${t}.${n}`:n;return"object"==typeof i&&null!==i?Object.assign(e,w(i,s)):e[s]=i,e}),{})}function L(e){const t=1e6*Date.now(),n=b.generateId(),i=e.spanId||b.generateSpanId(),s=e.traceId||b.generateTraceId(),r=e.parentSpanId||"",o=w(e.attributes||{}),a=function(){const e=y?.location;return e?{path:e.hash&&!e.hash.match(/^#[a-z0-9-]+$/i)&&e.hash.startsWith("#/")?e.hash:e.pathname,url:e.href,title:y?.document?.title||""}:{path:"",url:"",title:y?.document?.title||""}}(),l={type:e.type,id:n,spanId:i,parentSpanId:r,traceId:s,attributes:{...o,location:a}};return e.span_name&&(l.span_name=e.span_name),"network"===e.type?(l.start_timestamp=e.timestamp||t,l.end_timestamp=e?.end_timestamp):l.timestamp=t,l}var S=class{constructor(){this.logger=c.getInstance(),this.config=v.getInstance()}compress(n){const i=this.config.getConfig();if(!i?.options?.enableCompression)return{data:(new TextEncoder).encode(n),isCompressed:!1};try{const i=e(n);return{data:t(i),isCompressed:!0}}catch(e){return{data:(new TextEncoder).encode(n),isCompressed:!1}}}async send(e){const t=this.config.getConfig();if(t)try{t?.options?.debug&&this.logger.log("Sending batch:",e,{groundcoverIgnore:!0});const n=t.apiKey,i=this.buildEndpoint();if(!n)return void this.logger.log("No API key found");const s=JSON.stringify(e),{data:r,isCompressed:o}=this.compress(s);fetch(i,{method:"POST",headers:{"Content-Type":"application/json",apikey:n,"Content-Encoding":o?"gzip":""},body:r}).catch((e=>{this.logger.log("Network error while sending batch:",e,{groundcoverIgnore:!0})}))}catch(e){t.options.debug&&this.logger.log("Failed to send batch:",e,{groundcoverIgnore:!0})}}buildEndpoint(){const e=this.config.getConfig();if(!e)return"";const{dsn:t}=e;return`${t}/json/rum`}},C=["navigation","dom.event"],T=class e{constructor(){this.events=[],this.timeoutId=null,this.config=v.getInstance(),this.initialized=!1,this.transporter=new S}static getInstance(){return e.instance||(e.instance=new e),e.instance}initialize(){try{if(this.initialized)return;this.scheduleFlush(),globalThis.addEventListener("unload",(()=>{this.flush()})),this.initialized=!0}catch(e){d(e)}}addEvent(e){if(e&&this.initialized)try{const t=this.config.getConfig()?.options?.beforeSend;if(t&&!t(e))return;this.events.push(e);const n=this.config.getConfig()?.options?.batchSize||100;this.events.length>=n&&!C.includes(e.type)&&this.flush()}catch(e){d(e)}}flush(){try{if(!this.events?.length||!this.initialized)return;this.transporter.send({sessionAttributes:this.getSessionAttributes(),events:this.events}),this.events=[],this.scheduleFlush()}catch(e){d(e)}}scheduleFlush(){try{null!==this.timeoutId&&(y.clearTimeout(this.timeoutId),this.timeoutId=null);const e=this.config.getConfig()?.options?.batchTimeout;if(!e)return;this.timeoutId=y.setTimeout((()=>{this.timeoutId=null,this.flush()}),e)}catch(e){d(e)}}detectBrowser(){const e=navigator.userAgent;let t="unknown",n="unknown";const i=navigator.platform||"unknown",s=/Mobile|Android|iPhone|iPad|iPod/i.test(e);return/Edg/.test(e)?(t="Edge",n=e.match(/Edg\/([\d.]+)/)?.[1]||n):/Chrome/.test(e)&&!/Chromium/.test(e)?(t="Chrome",n=e.match(/Chrome\/([\d.]+)/)?.[1]||n):/Firefox/.test(e)?(t="Firefox",n=e.match(/Firefox\/([\d.]+)/)?.[1]||n):/Safari/.test(e)&&!/Chrome/.test(e)?(t="Safari",n=e.match(/Version\/([\d.]+)/)?.[1]||n):/Trident/.test(e)?(t="Internet Explorer",n=/rv:([^)]+)\)/i.test(e)?e.match(/rv:([^)]+)\)/i)?.[1]||n:e.match(/MSIE ([^;]+)/)?.[1]||n):/OPR/.test(e)&&(t="Opera",n=e.match(/OPR\/([\d.]+)/)?.[1]||n),{name:t,version:n,platform:i,language:navigator.language,mobile:s}}getSessionAttributes(){const e=this.detectBrowser();return{cluster:this.config.getConfig()?.cluster||"",env:this.config.getConfig()?.environment||"",namespace:this.config.getConfig()?.namespace||"",session_id:this.config.getSessionId(),user:this.config.getConfig()?.userIdentifier||{},"service.name":this.config.getConfig()?.appId,userAgent:navigator.userAgent,browser:e}}};T.instance=null;var _=T,z=class{constructor(){this.logger=c.getInstance(),this.eventsPool=_.getInstance()}};function q({text:e,maxLength:t=1e4}){return e?e.length<=t||"string"!=typeof e?e:e.substring(0,t):""}var x,R=class extends z{constructor(){super(...arguments),this.eventHandlers=[],this.capturedEvents=["click","change","keydown","select","submit"],this.getShouldMaskText=e=>["password"===e.target?.type,e.target?.id?.toLowerCase().includes("password"),e.target?.id?.toLowerCase().includes("credit-card"),e.target?.id?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("cc"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.className?.toLowerCase().includes("credit-card"),e.target?.getAttribute("data-private")].some((e=>e)),this.getKeyCode=e=>{if(e instanceof KeyboardEvent&&e.code&&"Dead"!==e.key){const t=this.getShouldMaskText({target:e.target});return t||t?"*":e.key}return""},this.getText=e=>q({text:e.target.innerText||""}),this.getSelector=e=>e.target instanceof Element&&this.generateSelector(e.target)||"",this.getCoordinates=e=>{if({mouseup:!0,mousedown:!0,mousemove:!0,mouseover:!0}[e.type]){const{clientX:t,clientY:n}=e||{};return{clientX:t,clientY:n}}return null}}initialize(){try{this.logger.log("[dom-events-listener.initialize] called"),this.capturedEvents?.forEach((e=>{const t=e=>{try{this.handleEvent(e)}catch(e){d(e)}};this.eventHandlers.push({type:e,handler:t}),y?.addEventListener(e,t)}))}catch(e){d(e)}}destroy(){this.eventHandlers.forEach((({type:e,handler:t})=>{global?.removeEventListener?.(e,t)})),this.eventHandlers=[]}handleEvent(e){try{if(!I())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}}buildEvent(e){const t=this.getSelector(e),n=this.getCoordinates(e),i=e.target,s=this.getKeyCode(e),r=this.getText(e);this.logger.log("[dom-events-listener.buildEvent] called");return L({type:"dom.event",attributes:{dom_event_selector:t,dom_event_key_code:s,dom_event_type:e.type,dom_event_coordinates:n||{clientX:0,clientY:0},dom_event_target:{id:i.id,tagName:i.tagName,className:i.className,text:r}}})}queueEvent(e){try{this.logger.log("[dom-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}generateSelector(e,t={}){if(!e||!e.nodeType||e.nodeType!==Node.ELEMENT_NODE)return"";const n=t.root||document.body||document.documentElement,i=t.maxAttempts||10,s=t.priorityAttributes||["id","class","name","aria-label","type","title","alt"];if("html"===e.tagName?.toLowerCase())return"html";let r="",o=0,a=e;const l=[];for(;a&&a!==n&&a!==document.documentElement&&o<i;){let e=a.tagName?.toLowerCase()||"";try{const t=a.getAttribute("id");if(t&&/^[a-zA-Z][\w-]*$/.test(t))return`#${t}`;if(a.classList?.length){const t=Array.from(a.classList).filter((e=>e&&"string"==typeof e)).map((e=>`.${e}`));t.length&&(e+=t.join(""))}for(const t of s)if("id"!==t&&"class"!==t)try{const n=a.getAttribute(t);n&&(e+=`[${t}="${n.replace(/"/g,'\\"')}"]`)}catch(e){}}catch(t){e=a.tagName?.toLowerCase()||"*"}l.unshift(e||"*"),r=l.join(" > ");try{if(1===n.querySelectorAll(r).length)return r}catch(e){l.shift(),r=l.join(" > ")}try{a=a.parentElement}catch(e){break}o++}return r||"*"}},N=["log","info","warn","error","assert","trace"],k=class extends z{constructor(){super(...arguments),this.originalConsole=null,this.isInitialized=!1}initialize(){if(!this.isInitialized)try{this.originalConsole=this.captureConsoleMethods(),N.forEach((e=>{e in console&&(console[e]=(...t)=>{try{this.handleEvent(t,e)}catch(e){d(e)}finally{this.originalConsole?.[e]&&this.originalConsole[e](...t)}})})),this.isInitialized=!0}catch(e){d(e)}}destroy(){try{if(!this.isInitialized)return;N.forEach((e=>{this.originalConsole&&this.originalConsole[e]&&(console[e]=this.originalConsole[e])})),this.isInitialized=!1}catch(e){d(e)}}handleEvent(e,t){try{if(!I())return;const n=this.formatMessage(Array.isArray(e)?e:[e]);if(!n||n?.includes("groundcoverIgnore"))return;const i=this.buildEvent({message:n,level:t});this.queueEvent(i)}catch(e){d(e)}}buildEvent({message:e,level:t}){return L({type:"log",attributes:{message:q({text:e}),level:t}})}queueEvent(e){try{this.logger.log("[logs-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}formatMessage(e){if(!Array.isArray(e))return String(e);try{return e.map((e=>{if(void 0===e)return"undefined";if(null===e)return"null";if("object"==typeof e)try{return JSON.stringify(e)}catch{return Object.prototype.toString.call(e)}return String(e)})).join(" ")}catch(e){return d(e),"[Error formatting console message]"}}captureConsoleMethods(){const e={};try{N.forEach((t=>{console&&"function"==typeof console[t]&&(e[t]=console[t].bind(console))}))}catch(e){d(e)}return e}},H=class extends z{constructor(){super(...arguments),this.maxBodyLength=5e3,this.config=v.getInstance(),this.idGenerator=new p,this.handleEvent=e=>{try{if(this.shouldIgnoreRequest(e.url))return;if(!I())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}},this.buildEvent=e=>{let t=e.url,n=e.url;this.logger.log("[network-events-listener.buildEvent] called",{event:e});try{t=new URL(e.url).pathname}catch(t){n=new URL(e.url,globalThis.location.href).href}this.logger.log("[network-events-listener.buildEvent] fullUrl",{fullUrl:n});const i=this.formatHeaders(e.request.headers),s=this.formatHeaders(e.response.headers),r=e.method?.toUpperCase()||"UNKNOWN",o=e.request.headers.traceparent,a=o?.split("-")?.[1]||"",l=o?.split("-")?.[2]||"",c={type:"HTTP",operation:{name:r},resource_name:t,status:e.status?.toString(),subType:r,url:{full:n},http:{route:t,path:t,method:e.method,status:e.status?.toString(),request:{headers:i,method:e.method},response:{headers:s,status_code:e.status?.toString()}},error:e?.error?.type?{type:e.error?.type||"Unknown error"}:void 0,gc:{request:{body:q({text:e.request.body,maxLength:this.maxBodyLength})},response:{body:q({text:e.response.body,maxLength:this.maxBodyLength})}}};return L({type:"network",timestamp:e?.timestamp&&!Number.isNaN(e.timestamp)?1e6*e.timestamp:void 0,end_timestamp:e?.end_time&&!Number.isNaN(e.end_time)?1e6*e.end_time:void 0,span_name:`${e.method} ${t}`,attributes:c,traceId:a,spanId:l})}}initialize(){this.logger.log("[network-events-listener.initialize] called"),this.patchXHR(),this.patchFetch()}destroy(){globalThis.XMLHttpRequest.prototype.open=globalThis.XMLHttpRequest.prototype.open,globalThis.XMLHttpRequest.prototype.send=globalThis.XMLHttpRequest.prototype.send,globalThis.fetch=globalThis.fetch}shouldIgnoreRequest(e){try{const t=this.config.getConfig()?.getEndpoint();if(t&&e.includes(t))return!0;if([".tsx",".jsx",".css"].some((t=>e.toLowerCase().endsWith(t))))return!0;return(this.config.getConfig()?.options?.excludedUrls||[]).some((t=>{if(t instanceof RegExp)return t.test(e);if("string"==typeof t&&(t.includes("*")||t.includes("?"))){const n=t.replace(/[.+?^${}()|[\]\\]/g,"\\$&").replace(/\*/g,".*").replace(/\?/g,".");return new RegExp(n).test(e)}return e===t}))}catch(e){return d(e),!1}}queueEvent(e){try{this.logger.log("[network-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}patchXHR(){const e=this,t=globalThis.XMLHttpRequest.prototype.open,n=globalThis.XMLHttpRequest.prototype.send,i=globalThis.XMLHttpRequest.prototype.setRequestHeader;let s;globalThis.XMLHttpRequest.prototype.open=function(n,i,r=!0,o,a){if(s=Date.now(),e.shouldIgnoreRequest(i.toString()))return t.apply(this,[n,i,r,o,a]);const l=new URL(i.toString(),globalThis.location.href).href;return this._requestMethod=n,this._requestUrl=l,this._requestHeaders={},t.apply(this,[n,i,r,o,a])},globalThis.XMLHttpRequest.prototype.setRequestHeader=function(e,t){return this._requestHeaders&&(this._requestHeaders[e]=t),i.apply(this,[e,t])},globalThis.XMLHttpRequest.prototype.send=function(...t){const i=this._requestUrl?.toString();if(!i||e.shouldIgnoreRequest(i))return n.apply(this,t);if(e.shouldAddTraceHeader(i)){const t=e.getTraceparentHeader();t&&(this.setRequestHeader("traceparent",t.traceparent),this._requestHeaders.traceparent=t.traceparent)}return this._requestBody=t[0]||"",this.addEventListener("load",(()=>{const t=Date.now(),n={};this.getAllResponseHeaders().split(/\r?\n/).forEach((e=>{const[t,i]=e.split(": ");t&&i&&(n[t.trim()]=i.trim())}));const i={timestamp:s,end_time:t,method:this._requestMethod,url:this._requestUrl,body:this._requestBody,status:this.status,request:{headers:this._requestHeaders||{},body:this._requestBody},response:{headers:n,body:this.responseText||this.response||""}};e.handleEvent(i)})),n.apply(this,t)}}patchFetch(){const e=globalThis.fetch;globalThis.fetch=(...t)=>{const n=Date.now();let[i,s]=t;s={...s||{}};const r=s?.method||"GET",o=s?.body||"",a=i instanceof Request?i.url:i.toString();if(this.shouldIgnoreRequest(a))return e.apply(globalThis,t);const l=this.shouldAddTraceHeader(a);if(s&&!s.headers&&(s.headers={}),s||(t[1]={},s=t[1]),l){const e=this.getTraceparentHeader();e&&(s?.headers instanceof Headers?s.headers.set("traceparent",e.traceparent):s.headers={...s.headers,traceparent:e.traceparent})}const c={};return s?.headers&&(s.headers instanceof Headers?s.headers.forEach(((e,t)=>{c[t]=e})):"object"==typeof s.headers&&Object.assign(c,s.headers)),e.apply(globalThis,t).then((async e=>{const t=Date.now(),i=e.clone();let s="";const l={};i.headers.forEach(((e,t)=>{l[t]=e}));try{s="text/event-stream"===l["content-type"]?"[unreadable response body]":await i.text()}catch(e){s="[unreadable response body]"}this.logger.log("[network-events-listener.patchFetch] called",{url:a});const h={method:r,url:a,timestamp:n,body:o.toString(),status:i.status,end_time:t,request:{headers:c,body:o.toString()},response:{headers:l,body:s}};return this.handleEvent(h),e})).catch((e=>{const t=Date.now();let n="NetworkError";const i=e.message||"Unknown network error";e instanceof TypeError&&i.includes("Failed to fetch")?n="ERR_NETWORK_FAILURE":i.includes("Name not resolved")?n="ERR_NAME_NOT_RESOLVED":i.includes("Connection refused")&&(n="ERR_CONNECTION_REFUSED");const s={method:r,url:a,body:o.toString(),status:0,end_time:t,request:{headers:c,body:o.toString()},response:{headers:{},body:""},error:{type:n}};throw this.handleEvent(s),e}))}}formatHeaders(e){const t=["authorization","cookie","set-cookie"];return Object.entries(e)?.reduce(((e,[n,i])=>{const s=n.toLowerCase();return t.includes(s)||/(token|key|secret|password)/i.test(s)?e[n]="[REDACTED]":e[n]=q({text:i}),e}),{})}getTraceparentHeader(){const e=this.idGenerator.generateSpanId(),t=this.idGenerator.generateTraceId();return{traceparent:`00-${t}-${e}-01`,traceId:t,spanId:e}}shouldAddTraceHeader(e){const t=this.config.getConfig();if(this.logger.log("[network-events-listener.shouldAddTraceHeader] called",{url:e,config:t}),!t||!t.options.tracePropagationUrls||!t.options.tracePropagationUrls?.length)return!1;const n=t.options.tracePropagationUrls.some((t=>{const n=t.replace(/\*/g,".*"),i=new RegExp(`^${n}$`),s=e.startsWith("/")?new URL(e,globalThis.location.href).pathname:e;return i.test(s)}));return this.logger.log("[network-events-listener.shouldAddTraceHeader] result",{url:e,result:n}),n}},U=class extends z{constructor(){super(...arguments),this.handleEvent=(e,t)=>{this.logger.log("[errors-events-listener.handleEvent] called");try{let n;if(e instanceof Error)n=e,this.enhanceError(n);else if(e instanceof ErrorEvent){if(n=e.error||new Error(e.message||"Unknown error"),/Script error\.?/.test(n.message))return;this.enhanceError(n,e)}else{if(!(e instanceof PromiseRejectionEvent))return;n=this.createUnhandledRejectionError(e)}const i=this.buildEvent(n,t);this.queueEvent(i)}catch(e){d(e)}}}initialize(){y?.addEventListener("error",this.handleEvent),y?.addEventListener("unhandledrejection",this.handleEvent)}destroy(){y?.removeEventListener("error",this.handleEvent),y?.removeEventListener("unhandledrejection",this.handleEvent)}buildEvent(e,t){return L({type:"exception",attributes:{error_type:e.name||"Error",error_message:e.message||"Unknown error",error_stacktrace:this.buildStackTrace(e),error_fingerprint:`${e.name}:${q({text:e.message,maxLength:400})}`,error_handled:t?.handled||!1}})}queueEvent(e){try{this.logger.log("[errors-events-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}enhanceError(e,t){const{filename:n,lineno:i,colno:s}=t||{};n&&!e.fileName&&Object.defineProperty(e,"fileName",{value:n}),i&&!e.lineNumber&&Object.defineProperty(e,"lineNumber",{value:i}),s&&!e.columnNumber&&Object.defineProperty(e,"columnNumber",{value:s})}createUnhandledRejectionError(e){let t;if(e.reason instanceof Error)t=e.reason;else{const n="object"==typeof e.reason?JSON.stringify(e.reason,null,2):String(e.reason);t=new Error(n),t.name="UnhandledRejection",Object.defineProperty(t,"originalReason",{value:e.reason,enumerable:!1})}return t}buildStackTrace(e){if(!e)return[];try{return n.parse(e).map((e=>({filename:e.fileName||"unknown",function:e.functionName||"anonymous",lineno:e.lineNumber||0,colno:e.columnNumber||0})))}catch(e){return[]}}},M=class extends z{constructor(){if(super(),this.currentUrl="",this.originalPushState=null,this.originalReplaceState=null,this.isInitialized=!1,this.popStateHandler=()=>{this.handleLocationChange()},this.hashChangeHandler=()=>{this.handleLocationChange()},this.isInBrowserEnvironment())try{this.currentUrl=y.location.href,this.originalPushState=history.pushState,this.originalReplaceState=history.replaceState}catch(e){d(e)}}isInBrowserEnvironment(){try{return void 0!==y&&void 0!==y.location&&void 0!==y.history&&"function"==typeof y.addEventListener}catch(e){return d(e),!1}}initialize(){try{if(this.logger.log("[navigation-listener.initialize] called"),!this.isInBrowserEnvironment()||!this.originalPushState||!this.originalReplaceState)return void this.logger.log("[navigation-listener.initialize] Browser environment not available, skipping initialization");const e=this.originalPushState,t=this.originalReplaceState;history.pushState=(...t)=>{const n=e.apply(history,t);return this.handleLocationChange(),n},history.replaceState=(...e)=>{const n=t.apply(history,e);return this.handleLocationChange(),n},y&&"function"==typeof y.addEventListener&&(y.addEventListener("popstate",this.popStateHandler),y.addEventListener("hashchange",this.hashChangeHandler)),this.isInitialized=!0}catch(e){d(e)}}destroy(){try{this.logger.log("[navigation-listener.destroy] called"),this.isInitialized&&this.originalPushState&&this.originalReplaceState&&(history.pushState=this.originalPushState,history.replaceState=this.originalReplaceState),y&&"function"==typeof y.removeEventListener&&(y.removeEventListener("popstate",this.popStateHandler),y.removeEventListener("hashchange",this.hashChangeHandler)),this.isInitialized=!1}catch(e){d(e)}}handleEvent(){try{this.logger.log("[navigation-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){d(e)}}buildEvent(){this.logger.log("[navigation-listener.buildEvent] called",y.location.href);return L({type:"navigation",attributes:{page_url:y.location.href}})}queueEvent(e){try{this.logger.log("[navigation-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}handleLocationChange(){try{if(!this.isInitialized)return;if(this.logger.log("[navigation-listener.handleLocationChange] called"),this.currentUrl===y.location.href)return;let e,t;try{e=new URL(y.location.href),t=new URL(this.currentUrl)}catch(e){return void d(e)}const n=e=>e.startsWith("#/"),i=n(e.hash)||n(t.hash);(e.pathname!==t.pathname||i&&e.hash!==t.hash)&&(this.currentUrl=y.location.href,this.handleEvent())}catch(e){d(e)}}},P=class extends z{constructor(){super(),this.startTime=performance.now()}initialize(){try{this.logger.log("[page-load-listener.initialize] called"),y?.addEventListener("load",(()=>{this.handleEvent()}))}catch(e){d(e)}}destroy(){y?.removeEventListener("load",this.handleEvent)}handleEvent(){try{this.logger.log("[page-load-listener.handleEvent] called");const e=this.buildEvent();this.queueEvent(e)}catch(e){d(e)}}buildEvent(){const e=performance.now()-this.startTime,t=performance.getEntriesByType("resource"),n={count:t.length,totalSize:0,totalDuration:0,byType:{}};t.forEach((e=>{const t=e,i=t.transferSize||0,s=t.duration,r=t.initiatorType;n.totalSize+=i,n.totalDuration+=s,n.byType[r]||(n.byType[r]={count:0,size:0,duration:0}),n.byType[r].count++,n.byType[r].size+=i,n.byType[r].duration+=s}));return L({type:"pageload",attributes:{page_url:y?.location?.href||"",page_load_time:e,page_referrer:y?.document?.referrer||"",page_resources:n}})}queueEvent(e){try{this.logger.log("[page-load-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}},j=class extends z{constructor(){super(...arguments),this.handleEvent=e=>{try{if(!I())return;const t=this.buildEvent(e);this.queueEvent(t)}catch(e){d(e)}}}initialize(){i(this.handleEvent),s(this.handleEvent),r(this.handleEvent),o(this.handleEvent),a(this.handleEvent)}destroy(){}buildEvent(e){return L({type:"performance",attributes:{performance_metric_name:e.name,performance_metric_value:e.value,performance_metric_id:e.id,performance_metric_navigation_type:e.navigationType||""}})}queueEvent(e){try{this.logger.log("[performance-listener.queueEvent] called"),e&&this.eventsPool.addEvent(e)}catch(e){d(e)}}},A=class{constructor(){this.logger=c.getInstance(),this.eventsPool=_.getInstance(),this.configManager=v.getInstance(),this.logEventsListener=null,this.domEventsListener=null,this.errorsEventsListener=null,this.networkEventsListener=null,this.navigationListener=null,this.performanceListener=null,this.pageLoadListener=null}instrument(){this.logger.log("[instrumentation-manager.instrument] called");const e=this.configManager.getConfig(),t=e?.options?.enabledEvents,n=!t||0===t.length,i=[];(n||t?.includes("pageload"))&&(this.pageLoadListener=new P,this.pageLoadListener.initialize(),i.push("pageload")),(n||t?.includes("dom"))&&(this.domEventsListener=new R,this.domEventsListener.initialize(),i.push("dom")),(n||t?.includes("logs"))&&(this.logEventsListener=new k,this.logEventsListener.initialize(),i.push("logs")),(n||t?.includes("exceptions"))&&(this.errorsEventsListener=new U,this.errorsEventsListener.initialize(),i.push("exceptions")),(n||t?.includes("network"))&&(this.networkEventsListener=new H,this.networkEventsListener.initialize(),i.push("network")),(n||t?.includes("navigation"))&&(this.navigationListener=new M,this.navigationListener.initialize(),i.push("navigation")),(n||t?.includes("performance"))&&(this.performanceListener=new j,this.performanceListener.initialize(),i.push("performance")),this.logger.log("[instrumentation-manager.instrument] initialized listeners based on config:",i)}sendCustomEvent(e){this.logger.log("[instrumentation-manager.sendCustomEvent] called",e);try{const t=L({type:"custom",attributes:{custom_event_name:e?.event,custom_event_attributes:e?.attributes}});this.eventsPool.addEvent(t)}catch(e){d(e)}}captureException(e){try{this.logger.log("[instrumentation-manager.captureException] called",e),this.errorsEventsListener?.handleEvent(e,{handled:!0})}catch(e){d(e)}}uninstrument(){this.domEventsListener?.destroy(),this.logEventsListener?.destroy(),this.errorsEventsListener?.destroy(),this.networkEventsListener?.destroy(),this.navigationListener?.destroy(),this.performanceListener?.destroy(),this.pageLoadListener?.destroy()}},D="gcSample",O=class{constructor(e){this.initialized=!1,this.logger=c.initialize({debug:e.options?.debug||!1,prefix:"[groundcover]"}),this.logger.log("[session-manager] initialize called"),this.instrumentationManager=new A,this.idGenerator=new p;if(!this.getSamplingDecision(e.options?.sessionSampleRate))return void this.logger.log("[session-manager] session is not sampled");if(this.initialized)return void this.logger.log("[session-manager] SDK already initialized");const t=v.getInstance();t.initialize(e);_.getInstance().initialize();t.getSessionId()||t.setSessionId(this.idGenerator.generateId()),this.instrumentationManager.instrument(),this.initialized=!0}getSamplingDecision(e){try{if(!e||1===e)return!0;const t=globalThis.sessionStorage?.getItem(D);if(t){const e="1"===t;return this.logger.log("[session-manager] using stored sampling decision:",e),e}const n=!e||Math.random()<e;return globalThis?.sessionStorage?.setItem(D,n?"1":"0"),this.logger.log("[session-manager] stored new sampling decision:",n),n}catch(t){this.logger.log("[session-manager] session storage access failed:",t);const n=!e||Math.random()<e;return this.logger.log("[session-manager] using fallback sampling decision:",n),n}}identifyUser(e){if(this.logger.log("[session-manager] identifyUser called"),!this.initialized)return void this.logger.log("[session-manager] cannot identify user: SDK not initialized");v.getInstance().updateConfig({userIdentifier:e})}sendCustomEvent(e){this.initialized?this.instrumentationManager.sendCustomEvent(e):this.logger.log("[session-manager] cannot send custom event: SDK not initialized")}captureException(e){this.initialized?this.instrumentationManager.captureException(e):this.logger.log("[session-manager] Cannot capture exception: SDK not initialized")}destroy(){this.initialized&&(this.instrumentationManager.uninstrument(),globalThis.sessionStorage?.removeItem("gcId"),this.initialized=!1)}};var $={init:function(e){try{x=new O({cluster:e?.cluster,environment:e?.environment,namespace:e?.namespace,dsn:e?.dsn,appId:e?.appId,userIdentifier:e?.userIdentifier,apiKey:e?.apiKey,options:e?.options})}catch(e){d(e)}},identifyUser:function(e){x?x.identifyUser(e):console.warn("[groundcover] identifyUser: groundcover is not initialized. please call init() first")},sendCustomEvent:function(e){x&&x.sendCustomEvent(e)},captureException:function(e){x&&x.captureException(e)}};export{$ as default};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@groundcover/browser",
3
- "version": "0.0.35",
3
+ "version": "0.0.36",
4
4
  "description": "groundcover browser SDK",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",