/**
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 * @preserved
 */
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).userale={})}(this,(function(e){"use strict";function t(e){return t="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(e){return typeof e}:function(e){return e&&"function"==typeof Symbol&&e.constructor===Symbol&&e!==Symbol.prototype?"symbol":typeof e},t(e)}var n="2.4.0",r=null;function o(e,t){var n=e.autostart,r=t.autostart;Object.keys(t).forEach((function(n){if("userFromParams"===n){var r=(o=t[n],i=new RegExp("[?&]"+o+"(=([^&#]*)|&|#|$)"),(a=window.location.href.match(i))&&a[2]?decodeURIComponent(a[2].replace(/\+/g," ")):null);r&&(e.userId=r)}var o,i,a;e[n]=t[n]})),!1!==n&&!1!==r||(e.autostart=!1)}var i=function(e,t,n){if(n||2===arguments.length)for(var r,o=0,i=t.length;o<i;o++)!r&&o in t||(r||(r=Array.prototype.slice.call(t,0,o)),r[o]=t[o]);return e.concat(r||Array.prototype.slice.call(t))},a=function(e,t,n){this.name=e,this.version=t,this.os=n,this.type="browser"},l=function(e){this.version=e,this.type="node",this.name="node",this.os=process.platform},u=function(e,t,n,r){this.name=e,this.version=t,this.os=n,this.bot=r,this.type="bot-device"},s=function(){this.type="bot",this.bot=!0,this.name="bot",this.version=null,this.os=null},c=function(){this.type="react-native",this.name="react-native",this.version=null,this.os=null},d=/(nuhk|curl|Googlebot|Yammybot|Openbot|Slurp|MSNBot|Ask\ Jeeves\/Teoma|ia_archiver)/,f=3,m=[["aol",/AOLShield\/([0-9\._]+)/],["edge",/Edge\/([0-9\._]+)/],["edge-ios",/EdgiOS\/([0-9\._]+)/],["yandexbrowser",/YaBrowser\/([0-9\._]+)/],["kakaotalk",/KAKAOTALK\s([0-9\.]+)/],["samsung",/SamsungBrowser\/([0-9\.]+)/],["silk",/\bSilk\/([0-9._-]+)\b/],["miui",/MiuiBrowser\/([0-9\.]+)$/],["beaker",/BeakerBrowser\/([0-9\.]+)/],["edge-chromium",/EdgA?\/([0-9\.]+)/],["chromium-webview",/(?!Chrom.*OPR)wv\).*Chrom(?:e|ium)\/([0-9\.]+)(:?\s|$)/],["chrome",/(?!Chrom.*OPR)Chrom(?:e|ium)\/([0-9\.]+)(:?\s|$)/],["phantomjs",/PhantomJS\/([0-9\.]+)(:?\s|$)/],["crios",/CriOS\/([0-9\.]+)(:?\s|$)/],["firefox",/Firefox\/([0-9\.]+)(?:\s|$)/],["fxios",/FxiOS\/([0-9\.]+)/],["opera-mini",/Opera Mini.*Version\/([0-9\.]+)/],["opera",/Opera\/([0-9\.]+)(?:\s|$)/],["opera",/OPR\/([0-9\.]+)(:?\s|$)/],["pie",/^Microsoft Pocket Internet Explorer\/(\d+\.\d+)$/],["pie",/^Mozilla\/\d\.\d+\s\(compatible;\s(?:MSP?IE|MSInternet Explorer) (\d+\.\d+);.*Windows CE.*\)$/],["netfront",/^Mozilla\/\d\.\d+.*NetFront\/(\d.\d)/],["ie",/Trident\/7\.0.*rv\:([0-9\.]+).*\).*Gecko$/],["ie",/MSIE\s([0-9\.]+);.*Trident\/[4-7].0/],["ie",/MSIE\s(7\.0)/],["bb10",/BB10;\sTouch.*Version\/([0-9\.]+)/],["android",/Android\s([0-9\.]+)/],["ios",/Version\/([0-9\._]+).*Mobile.*Safari.*/],["safari",/Version\/([0-9\._]+).*Safari/],["facebook",/FB[AS]V\/([0-9\.]+)/],["instagram",/Instagram\s([0-9\.]+)/],["ios-webview",/AppleWebKit\/([0-9\.]+).*Mobile/],["ios-webview",/AppleWebKit\/([0-9\.]+).*Gecko\)$/],["curl",/^curl\/([0-9\.]+)$/],["searchbot",/alexa|bot|crawl(er|ing)|facebookexternalhit|feedburner|google web preview|nagios|postrank|pingdom|slurp|spider|yahoo!|yandex/]],h=[["iOS",/iP(hone|od|ad)/],["Android OS",/Android/],["BlackBerry OS",/BlackBerry|BB10/],["Windows Mobile",/IEMobile/],["Amazon OS",/Kindle/],["Windows 3.11",/Win16/],["Windows 95",/(Windows 95)|(Win95)|(Windows_95)/],["Windows 98",/(Windows 98)|(Win98)/],["Windows 2000",/(Windows NT 5.0)|(Windows 2000)/],["Windows XP",/(Windows NT 5.1)|(Windows XP)/],["Windows Server 2003",/(Windows NT 5.2)/],["Windows Vista",/(Windows NT 6.0)/],["Windows 7",/(Windows NT 6.1)/],["Windows 8",/(Windows NT 6.2)/],["Windows 8.1",/(Windows NT 6.3)/],["Windows 10",/(Windows NT 10.0)/],["Windows ME",/Windows ME/],["Windows CE",/Windows CE|WinCE|Microsoft Pocket Internet Explorer/],["Open BSD",/OpenBSD/],["Sun OS",/SunOS/],["Chrome OS",/CrOS/],["Linux",/(Linux)|(X11)/],["Mac OS",/(Mac_PowerPC)|(Macintosh)/],["QNX",/QNX/],["BeOS",/BeOS/],["OS/2",/OS\/2/]];function p(e){var t=function(e){return""!==e&&m.reduce((function(t,n){var r=n[0],o=n[1];if(t)return t;var i=o.exec(e);return!!i&&[r,i]}),!1)}(e);if(!t)return null;var n=t[0],r=t[1];if("searchbot"===n)return new s;var o=r[1]&&r[1].split(".").join("_").split("_").slice(0,3);o?o.length<f&&(o=i(i([],o,!0),function(e){for(var t=[],n=0;n<e;n++)t.push("0");return t}(f-o.length),!0)):o=[];var l=o.join("."),c=function(e){for(var t=0,n=h.length;t<n;t++){var r=h[t],o=r[0];if(r[1].exec(e))return o}return null}(e),p=d.exec(e);return p&&p[1]?new u(n,l,c,p[1]):new a(n,l,c)}var w,g,v,y,b,S,O,k,E,W,I,T,N=w?p(w):"undefined"==typeof document&&"undefined"!=typeof navigator&&"ReactNative"===navigator.product?new c:"undefined"!=typeof navigator?p(navigator.userAgent):"undefined"!=typeof process&&process.version?new l(process.version.slice(1)):null,x={};function A(e,t){if(!v.on)return!1;var n=null;t&&(n=t(e));for(var r,o=(r=e.timeStamp&&e.timeStamp>0?v.time(e.timeStamp):Date.now(),{milli:Math.floor(r),micro:Number((r%1).toFixed(3))}),i={target:M(e.target),path:B(e),pageUrl:window.location.href,pageTitle:document.title,pageReferrer:document.referrer,browser:P(),clientTime:o.milli,microTime:o.micro,location:C(e),scrnRes:D(),type:e.type,logType:"raw",userAction:!0,details:n,userId:v.userId,toolVersion:v.version,toolName:v.toolName,useraleVersion:v.useraleVersion,sessionID:v.sessionID},a=0,l=Object.values(x);a<l.length;a++){var u=l[a];if("function"==typeof u&&!(i=u(i,e)))return!1}return g.push(i),!0}function j(e,t,n){if(!v.on)return!1;var r=null;t&&(r=t());for(var o={pageUrl:window.location.href,pageTitle:document.title,pageReferrer:document.referrer,browser:P(),clientTime:Date.now(),scrnRes:D(),logType:"custom",userAction:n,details:r,userId:v.userId,toolVersion:v.version,toolName:v.toolName,useraleVersion:v.useraleVersion,sessionID:v.sessionID},i=Object.assign(o,e),a=0,l=Object.values(x);a<l.length;a++){var u=l[a];if("function"==typeof u&&!(i=u(i,null)))return!1}return g.push(i),!0}function C(e){return null!=e.pageX?{x:e.pageX,y:e.pageY}:null!=e.clientX?{x:document.documentElement.scrollLeft+e.clientX,y:document.documentElement.scrollTop+e.clientY}:{x:null,y:null}}function D(){return{width:window.innerWidth,height:window.innerHeight}}function M(e){return e.localName?e.localName+(e.id?"#"+e.id:"")+(e.className?"."+e.className:""):e.nodeName?e.nodeName+(e.id?"#"+e.id:"")+(e.className?"."+e.className:""):e&&e.document&&e.location&&e.alert&&e.setInterval?"Window":"Unknown"}function B(e){if(e instanceof window.Event)return function(e){var t,n=0,r=[];for(;t=e[n];)r.push(M(t)),++n;return r}(e.composedPath())}function P(){return{browser:N?N.name:"",version:N?N.version:""}}var K,V=["click","focus","blur","input","change","mouseover","submit"],L=["load","blur","focus"];function R(e){return{clicks:e.detail,ctrl:e.ctrlKey,alt:e.altKey,shift:e.shiftKey,meta:e.metaKey}}function $(e){return function(e){W={click:R,dblclick:R,mousedown:R,mouseup:R,focus:null,blur:null,input:e.logDetails?function(e){return{value:e.target.value}}:null,change:e.logDetails?function(e){return{value:e.target.value}}:null,dragstart:null,dragend:null,drag:null,drop:null,keydown:e.logDetails?function(e){return{key:e.keyCode,ctrl:e.ctrlKey,alt:e.altKey,shift:e.shiftKey,meta:e.metaKey}}:null,mouseover:null},I={},T={wheel:function(e){return{x:e.deltaX,y:e.deltaY,z:e.deltaZ}},scroll:function(){return{x:window.scrollX,y:window.scrollY}},resize:function(){return{width:window.outerWidth,height:window.outerHeight}}},K={submit:null}}(e),Object.keys(W).forEach((function(e){document.addEventListener(e,(function(t){A(t,W[e])}),!0)})),V.forEach((function(e){document.addEventListener(e,(function(e){!function(e){var t=M(e.target),n=B(e),r=e.type,o=Math.floor(e.timeStamp&&e.timeStamp>0?v.time(e.timeStamp):Date.now());if(null==y&&(y=t,b=r,S=n,O=o,k=0),y!==t||b!==r){E={target:y,path:S,pageUrl:window.location.href,pageTitle:document.title,pageReferrer:document.referrer,browser:P(),count:k,duration:o-O,startTime:O,endTime:o,type:b,logType:"interval",targetChange:y!==t,typeChange:b!==r,userAction:!1,userId:v.userId,toolVersion:v.version,toolName:v.toolName,useraleVersion:v.useraleVersion,sessionID:v.sessionID};for(var i=0,a=Object.values(x);i<a.length;i++){var l=a[i];if("function"==typeof l&&!(E=l(E,null)))return!1}g.push(E),y=t,b=r,S=n,O=o,k=0}y==t&&b==r&&(k+=1)}(e)}),!0)})),Object.keys(T).forEach((function(t){I[t]=!0,window.addEventListener(t,(function(n){I[t]&&(I[t]=!1,A(n,T[t]),setTimeout((function(){I[t]=!0}),e.resolution))}),!0)})),Object.keys(K).forEach((function(e){document.addEventListener(e,(function(t){A(t,W[e])}),!0)})),L.forEach((function(e){window.addEventListener(e,(function(e){A(e,(function(){return{window:!0}}))}),!0)})),!0}function X(e,t){(null==t||t>e.length)&&(t=e.length);for(var n=0,r=new Array(t);n<t;n++)r[n]=e[n];return r}function _(e,t){return function(e){if(Array.isArray(e))return e}(e)||function(e,t){var n=null==e?null:"undefined"!=typeof Symbol&&e[Symbol.iterator]||e["@@iterator"];if(null!=n){var r,o,i,a,l=[],u=!0,s=!1;try{if(i=(n=n.call(e)).next,0===t){if(Object(n)!==n)return;u=!1}else for(;!(u=(r=i.call(n)).done)&&(l.push(r.value),l.length!==t);u=!0);}catch(e){s=!0,o=e}finally{try{if(!u&&null!=n.return&&(a=n.return(),Object(a)!==a))return}finally{if(s)throw o}}return l}}(e,t)||function(e,t){if(e){if("string"==typeof e)return X(e,t);var n=Object.prototype.toString.call(e).slice(8,-1);return"Object"===n&&e.constructor&&(n=e.constructor.name),"Map"===n||"Set"===n?Array.from(e):"Arguments"===n||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?X(e,t):void 0}}(e,t)||function(){throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}()}var H=null;var U=null;function z(e,t){null!==U&&clearInterval(U),U=function(e,t){return setInterval((function(){t.on&&e.length>=t.logCountThreshold&&(F(e.slice(0),t,0),e.splice(0))}),t.transmitInterval)}(e,t),function(e,t){window.addEventListener("pagehide",(function(){t.on&&e.length>0&&(navigator.sendBeacon(t.url,JSON.stringify(e)),e.splice(0))}))}(e,t)}function F(e,t,n){var r=new XMLHttpRequest,o=JSON.stringify(e);r.open("POST",t.url),function(e){if(H)try{e.authHeader=H()}catch(e){console.error("Error encountered while setting the auth header: ".concat(e))}}(t),t.authHeader&&r.setRequestHeader("Authorization",t.authHeader),r.setRequestHeader("Content-type","application/json;charset=UTF-8"),t.headers&&Object.entries(t.headers).forEach((function(e){var t=_(e,2),n=t[0],o=t[1];r.setRequestHeader(n,o)})),r.onreadystatechange=function(){4===r.readyState&&200!==r.status&&n>0&&F(e,t,n--)},r.send(o)}var Y,J={},q=[],G=Date.now();window.onload=function(){Y=Date.now()},e.started=!1,J.on=!1,J.useraleVersion=n,o(J,function(){var e={};null===r&&(r=function(e,t){if(null===window.sessionStorage.getItem(e))return window.sessionStorage.setItem(e,JSON.stringify(t)),t;return JSON.parse(window.sessionStorage.getItem(e))}("userAleSessionId","session_"+String(Date.now())));var t,n=document.currentScript||(t=document.getElementsByTagName("script"))[t.length-1],o=n?n.getAttribute.bind(n):function(){return null};return e.autostart="false"!==o("data-autostart"),e.url=o("data-url")||"http://localhost:8000",e.transmitInterval=+o("data-interval")||5e3,e.logCountThreshold=+o("data-threshold")||5,e.userId=o("data-user")||null,e.version=o("data-version")||null,e.logDetails="true"===o("data-log-details"),e.resolution=+o("data-resolution")||500,e.toolName=o("data-tool")||null,e.userFromParams=o("data-user-from-params")||null,e.time=function(e){var t;if(e.timeStamp&&e.timeStamp>0){var n=Date.now()-e.timeStamp;if(n<0)t=function(){return e.timeStamp/1e3};else if(n>e.timeStamp){var r=performance.timing.navigationStart;t=function(e){return e+r}}else t=function(e){return e}}else t=function(){return Date.now()};return t}(document.createEvent("CustomEvent")),e.sessionID=o("data-session")||r,e.authHeader=o("data-auth")||null,e.custIndex=o("data-index")||null,e.headers=o("data-headers")||null,e}()),g=q,v=J,x=[],y=null,b=null,S=null,O=null,k=0,E=null,J.autostart&&function t(n){e.started||setTimeout((function(){var r=document.readyState;!n.autostart||"interactive"!==r&&"complete"!==r?t(n):($(n),z(q,n),e.started=n.on=!0,j({type:"load",details:{pageLoadTime:Y-G}},(function(){}),!1))}),100)}(J);var Q=n;e.addCallbacks=function(){for(var e=arguments.length,t=new Array(e),n=0;n<e;n++)t[n]=arguments[n];return t.forEach((function(e){var t=Object.keys(e).reduce((function(t,n){return t[n]=Object.getOwnPropertyDescriptor(e,n),t}),{});Object.getOwnPropertySymbols(e).forEach((function(n){var r=Object.getOwnPropertyDescriptor(e,n);r.enumerable&&(t[n]=r)})),Object.defineProperties(x,t)})),x},e.buildPath=B,e.details=function(e,t){return{click:R,dblclick:R,mousedown:R,mouseup:R,focus:null,blur:null,input:e.logDetails?function(e){return{value:e.target.value}}:null,change:e.logDetails?function(e){return{value:e.target.value}}:null,dragstart:null,dragend:null,drag:null,drop:null,keydown:e.logDetails?function(e){return{key:e.keyCode,ctrl:e.ctrlKey,alt:e.altKey,shift:e.shiftKey,meta:e.metaKey}}:null,mouseover:null,wheel:function(e){return{x:e.deltaX,y:e.deltaY,z:e.deltaZ}},scroll:function(){return{x:window.scrollX,y:window.scrollY}},resize:function(){return{width:window.outerWidth,height:window.outerHeight}},submit:null}[t]},e.getSelector=M,e.log=function(e){return null!==e&&"object"===t(e)&&(q.push(e),!0)},e.options=function(e){return void 0!==e&&o(J,e),J},e.packageCustomLog=j,e.packageLog=A,e.registerAuthCallback=function(e){try{return function(e){if("function"!=typeof e)throw new Error("Userale auth callback must be a function");var t=e();if("string"!=typeof t)throw new Error("Userale auth callback must return a string")}(e),H=e,!0}catch(e){return!1}},e.removeCallbacks=function(e){e.forEach((function(e){Object.hasOwn(x,e)&&delete x[e]}))},e.start=function(){e.started&&!1!==J.autostart||(e.started=J.on=!0,J.autostart=!0)},e.stop=function(){e.started=J.on=!1,J.autostart=!1},e.version=Q}));
