@aicore/core-analytics-client-lib 1.0.3 → 1.0.4

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/README.md CHANGED
@@ -40,14 +40,18 @@ initSession(): Initialize the analytics session. It takes the following paramete
40
40
  * `granularitySec` (_Optional_): The smallest time period under which the events can be distinguished. Multiple
41
41
  events happening during this time period is aggregated to a count. The default granularity is 3 Seconds, which means
42
42
  that any events that happen within 3 seconds cannot be distinguished in ordering.
43
- * `postBaseURLInit` Optional: Provide your own analytics server address if you self-hosted the server
43
+ * `analyticsURL` (_Optional_): Provide your own analytics server address if you self-hosted the server
44
+ * `debug` (_Optional_): set to true if you want to see detailed debug logs.
44
45
 
45
46
  ```javascript
46
47
  // Example for custom initSession where the analytics aggregated data
47
48
  // is posted to custom server https://localhost:3000 every 600 secs
48
49
  // with a granularity(resolution) of 5 seconds.
49
50
 
50
- initSession("accountID", "appName", 600, 5, "https://localhost:3000");
51
+ initSession("accountID", "appName", "https://localhost:3000", 600, 5);
52
+
53
+ // To initSession in debug mode set debug arg in init to true:
54
+ initSession("accountID", "appName", "https://localhost:3000", 600, 5, true);
51
55
  ```
52
56
 
53
57
  ## Raising analytics events
@@ -1,3 +1,4 @@
1
- let accountID,appName,userID,sessionID,postIntervalSeconds,granularitySec,postURL;const DEFAULT_GRANULARITY_IN_SECONDS=3,DEFAULT_RETRY_TIME_IN_SECONDS=30,DEFAULT_POST_INTERVAL_SECONDS=600,USERID_LOCAL_STORAGE_KEY="aicore.analytics.userID",POST_LARGE_DATA_THRESHOLD_BYTES=1e4;let currentAnalyticsEvent=null;const IS_NODE_ENV="undefined"==typeof window;let DEFAULT_BASE_URL="https://analytics.core.ai",granularityTimer,postTimer,currentQuantisedTime=0;if(IS_NODE_ENV)throw new Error("Node environment is not currently supported");function _createAnalyticsEvent(){return{schemaVersion:1,accountID:accountID,appName:appName,uuid:userID,sessionID:sessionID,granularitySec:granularitySec,unixTimestampUTC:+new Date,numEventsTotal:0,events:{}}}function _validateCurrentState(){if(!currentAnalyticsEvent)throw new Error("Please call initSession before using any analytics event")}function getCurrentAnalyticsEvent(){return _validateCurrentState(),JSON.parse(JSON.stringify(currentAnalyticsEvent))}function _getOrCreateUserID(){let t=localStorage.getItem(USERID_LOCAL_STORAGE_KEY);return t||(t=crypto.randomUUID(),localStorage.setItem(USERID_LOCAL_STORAGE_KEY,t)),t}function _getOrCreateSessionID(){let t=sessionStorage.getItem(USERID_LOCAL_STORAGE_KEY);return t||(t=Math.random().toString(36).substr(2,10),sessionStorage.setItem(USERID_LOCAL_STORAGE_KEY,t)),t}function _setupIDs(){userID=_getOrCreateUserID(),sessionID=_getOrCreateSessionID()}function _retryPost(t){t.backoffCount=(t.backoffCount||0)+1,console.log(`Failed to call core analytics server. Will retry in ${DEFAULT_RETRY_TIME_IN_SECONDS*t.backoffCount}s: `),setTimeout(()=>{_postCurrentAnalyticsEvent(t)},1e3*DEFAULT_RETRY_TIME_IN_SECONDS*t.backoffCount)}function _postCurrentAnalyticsEvent(e){var t;e||(e=currentAnalyticsEvent,currentAnalyticsEvent=_createAnalyticsEvent()),0!==e.numEventsTotal&&((t=JSON.stringify(e)).length>POST_LARGE_DATA_THRESHOLD_BYTES&&console.warn(`Analytics event generated is very large at greater than ${t.length}B. This
2
- typically means that you may be sending too many value events? .`),window.fetch(postURL,{method:"POST",headers:{"Content-Type":"application/json"},body:t}).then(t=>{200!==t.status&&(400!==t.status?_retryPost(e):console.error("Bad Request, this is most likely a problem with the library, update to latest version."))}).catch(t=>{console.error(t),_retryPost(e)}))}function _setupTimers(){granularityTimer&&(clearInterval(granularityTimer),granularityTimer=null),granularityTimer=setInterval(()=>{currentQuantisedTime+=granularitySec},1e3*granularitySec),postTimer&&(clearInterval(postTimer),postTimer=null),postTimer=setInterval(_postCurrentAnalyticsEvent,1e3*postIntervalSeconds)}function initSession(t,e,n,r,a){if(!t||!e)throw new Error("accountID and appName must exist for init");accountID=t,appName=e,postIntervalSeconds=n||DEFAULT_POST_INTERVAL_SECONDS,granularitySec=r||DEFAULT_GRANULARITY_IN_SECONDS,postURL=(a||DEFAULT_BASE_URL)+"/ingest",_setupIDs(),currentAnalyticsEvent=_createAnalyticsEvent(),_setupTimers()}function _ensureAnalyticsEventExists(t,e,n){let r=currentAnalyticsEvent.events;r[t]=r[t]||{},r[t][e]=r[t][e]||{},r[t][e][n]=r[t][e][n]||{time:[],valueCount:[]}}function _validateEvent(t,e,n,r,a){if(_validateCurrentState(),!t||!e||!n)throw new Error("missing eventType or category or subCategory");if("number"!=typeof r||r<0)throw new Error("invalid count");if("number"!=typeof a)throw new Error("invalid value")}function _updateExistingAnalyticsEvent(e,n,r,a,s,i){let o=currentAnalyticsEvent.events;var t="number"==typeof o[n][r][a].valueCount[e];if(t&&0===i)o[n][r][a].valueCount[e]+=s;else if(t&&0!==i){let t={};t[i]=s,t[0]=o[n][r][a].valueCount[e],o[n][r][a].valueCount[e]=t}else if(!t){let t=o[n][r][a].valueCount[e];t[i]=(t[i]||0)+s}currentAnalyticsEvent.numEventsTotal+=1}function analyticsEvent(e,n,r,a=1,s=0){_validateEvent(e,n,r,a,s),_ensureAnalyticsEventExists(e,n,r);let i=currentAnalyticsEvent.events;var t=i[e][n][r].time;if((0<t.length?t[t.length-1]:null)===currentQuantisedTime)_updateExistingAnalyticsEvent(i[e][n][r].valueCount.length-1,e,n,r,a,s);else{if(i[e][n][r].time.push(currentQuantisedTime),0===s)i[e][n][r].valueCount.push(a);else{let t={};t[s]=a,i[e][n][r].valueCount.push(t)}currentAnalyticsEvent.numEventsTotal+=1}}export{initSession,getCurrentAnalyticsEvent,analyticsEvent};
1
+ let accountID,appName,userID,sessionID,postIntervalSeconds,granularitySec,analyticsURL,postURL,serverConfig;const DEFAULT_GRANULARITY_IN_SECONDS=3,DEFAULT_RETRY_TIME_IN_SECONDS=30,DEFAULT_POST_INTERVAL_SECONDS=600,USERID_LOCAL_STORAGE_KEY="aicore.analytics.userID",POST_LARGE_DATA_THRESHOLD_BYTES=1e4;let currentAnalyticsEvent=null;const IS_NODE_ENV="undefined"==typeof window;let DEFAULT_BASE_URL="https://analytics.core.ai",granularityTimer,postTimer,currentQuantisedTime=0,disabled=!1,debugMode=!1;function debugLog(...e){debugMode&&console.log(...e)}function debugError(...e){debugMode&&console.error(...e)}if(IS_NODE_ENV)throw new Error("Node environment is not currently supported");function _createAnalyticsEvent(){return{schemaVersion:1,accountID:accountID,appName:appName,uuid:userID,sessionID:sessionID,unixTimestampUTC:+new Date,numEventsTotal:0,events:{}}}function _validateCurrentState(){if(!currentAnalyticsEvent)throw new Error("Please call initSession before using any analytics event")}function getCurrentAnalyticsEvent(){return _validateCurrentState(),JSON.parse(JSON.stringify(currentAnalyticsEvent))}function _getOrCreateUserID(){let e=localStorage.getItem(USERID_LOCAL_STORAGE_KEY);return e||(e=crypto.randomUUID(),localStorage.setItem(USERID_LOCAL_STORAGE_KEY,e)),e}function _getOrCreateSessionID(){let e=sessionStorage.getItem(USERID_LOCAL_STORAGE_KEY);return e||(e=Math.random().toString(36).substr(2,10),sessionStorage.setItem(USERID_LOCAL_STORAGE_KEY,e)),e}function _setupIDs(){userID=_getOrCreateUserID(),sessionID=_getOrCreateSessionID()}function _retryPost(e){e.backoffCount=(e.backoffCount||0)+1,debugLog(`Failed to call core analytics server. Will retry in ${DEFAULT_RETRY_TIME_IN_SECONDS*e.backoffCount}s: `),setTimeout(()=>{_postCurrentAnalyticsEvent(e)},1e3*DEFAULT_RETRY_TIME_IN_SECONDS*e.backoffCount)}function _postCurrentAnalyticsEvent(t){var e;disabled||(t||(t=currentAnalyticsEvent,currentQuantisedTime=0,_resetGranularityTimer(),currentAnalyticsEvent=_createAnalyticsEvent()),0!==t.numEventsTotal&&((e=JSON.stringify(t)).length>POST_LARGE_DATA_THRESHOLD_BYTES&&console.warn(`Analytics event generated is very large at greater than ${e.length}B. This
2
+ typically means that you may be sending too many value events? .`),debugLog("Sending Analytics data of length: ",e.length,"B"),window.fetch(postURL,{method:"POST",headers:{"Content-Type":"application/json"},body:e}).then(e=>{200!==e.status&&(400!==e.status?_retryPost(t):console.error("Analytics client: Bad Request, this is most likely a problem with the library, update to latest version."))}).catch(e=>{debugError(e),_retryPost(t)})))}function _resetGranularityTimer(e){granularityTimer&&(clearInterval(granularityTimer),granularityTimer=null),e||(granularityTimer=setInterval(()=>{currentQuantisedTime+=granularitySec},1e3*granularitySec))}function _setupTimers(e){_resetGranularityTimer(e),postTimer&&(clearInterval(postTimer),postTimer=null),e||(postTimer=setInterval(_postCurrentAnalyticsEvent,1e3*postIntervalSeconds))}async function _getServerConfig(){return new Promise((n,r)=>{var e=analyticsURL+(`/getAppConfig?accountID=${accountID}&appName=`+appName);window.fetch(e).then(async e=>{switch(e.status){case 200:var t=await e.json();return void n(t);case 400:r("Bad Request, check library version compatible?",e);break;default:r("analytics client: Could not update from remote config. Continuing with defaults.",e)}}).catch(e=>{r("analytics client: Could not update from remote config. Continuing with defaults.",e)})})}function getAppConfig(){return{accountID:accountID,appName:appName,disabled:disabled,uuid:userID,sessionID:sessionID,postIntervalSeconds:postIntervalSeconds,granularitySec:granularitySec,analyticsURL:analyticsURL,serverConfig:serverConfig}}async function _initFromRemoteConfig(e,t){(serverConfig=await _getServerConfig())!=={}&&(postIntervalSeconds=e||serverConfig.postIntervalSecondsInit||DEFAULT_POST_INTERVAL_SECONDS,granularitySec=t||serverConfig.granularitySecInit||DEFAULT_GRANULARITY_IN_SECONDS,analyticsURL=serverConfig.analyticsURLInit||analyticsURL||DEFAULT_BASE_URL,_setupTimers(disabled=!0===serverConfig.disabled),debugLog(`Init analytics Config from remote. disabled: ${disabled}
3
+ postIntervalSeconds:${postIntervalSeconds}, granularitySec: ${granularitySec} ,URL: `+analyticsURL),disabled&&console.warn(`Core Analytics is disabled from the server for app: ${accountID}:`+appName))}function _stripTrailingSlash(e){return e.replace(/\/$/,"")}function initSession(e,t,n,r,a,i){if(!e||!t)throw new Error("accountID and appName must exist for init");analyticsURL=n?_stripTrailingSlash(n):DEFAULT_BASE_URL,accountID=e,appName=t,debugMode=i||!1,postIntervalSeconds=r||DEFAULT_POST_INTERVAL_SECONDS,granularitySec=a||DEFAULT_GRANULARITY_IN_SECONDS,postURL=analyticsURL+"/ingest",_setupIDs(),currentAnalyticsEvent=_createAnalyticsEvent(),_setupTimers(),_initFromRemoteConfig(r,a)}function _ensureAnalyticsEventExists(e,t,n){let r=currentAnalyticsEvent.events;r[e]=r[e]||{},r[e][t]=r[e][t]||{},r[e][t][n]=r[e][t][n]||{time:[],valueCount:[]}}function _validateEvent(e,t,n,r,a){if(_validateCurrentState(),!e||!t||!n)throw new Error("missing eventType or category or subCategory");if("number"!=typeof r||r<0)throw new Error("invalid count");if("number"!=typeof a)throw new Error("invalid value")}function _updateExistingAnalyticsEvent(t,n,r,a,i,s){let o=currentAnalyticsEvent.events;var e="number"==typeof o[n][r][a].valueCount[t];if(e&&0===s)o[n][r][a].valueCount[t]+=i;else if(e&&0!==s){let e={};e[s]=i,e[0]=o[n][r][a].valueCount[t],o[n][r][a].valueCount[t]=e}else if(!e){let e=o[n][r][a].valueCount[t];e[s]=(e[s]||0)+i}currentAnalyticsEvent.numEventsTotal+=1}function analyticsEvent(n,r,a,i=1,s=0){if(!disabled){_validateEvent(n,r,a,i,s),_ensureAnalyticsEventExists(n,r,a);let t=currentAnalyticsEvent.events;var e=t[n][r][a].time;if((0<e.length?e[e.length-1]:null)!==currentQuantisedTime){if(t[n][r][a].time.push(currentQuantisedTime),0===s)t[n][r][a].valueCount.push(i);else{let e={};e[s]=i,t[n][r][a].valueCount.push(e)}currentAnalyticsEvent.numEventsTotal+=1}else _updateExistingAnalyticsEvent(t[n][r][a].valueCount.length-1,n,r,a,i,s)}}export{initSession,getCurrentAnalyticsEvent,analyticsEvent,getAppConfig};
3
4
  //# sourceMappingURL=analytics.min.js.map
@@ -1 +1 @@
1
- {"version":3,"sourceRoot":"src/analytics.js","sources":["src/analytics.js"],"names":["let","accountID","appName","userID","sessionID","postIntervalSeconds","granularitySec","postURL","DEFAULT_GRANULARITY_IN_SECONDS","DEFAULT_RETRY_TIME_IN_SECONDS","DEFAULT_POST_INTERVAL_SECONDS","USERID_LOCAL_STORAGE_KEY","POST_LARGE_DATA_THRESHOLD_BYTES","currentAnalyticsEvent","IS_NODE_ENV","window","DEFAULT_BASE_URL","granularityTimer","postTimer","currentQuantisedTime","Error","_createAnalyticsEvent","schemaVersion","uuid","unixTimestampUTC","Date","numEventsTotal","events","_validateCurrentState","getCurrentAnalyticsEvent","JSON","parse","stringify","_getOrCreateUserID","localUserID","localStorage","getItem","crypto","randomUUID","setItem","_getOrCreateSessionID","localSessionID","sessionStorage","Math","random","toString","substr","_setupIDs","_retryPost","eventToSend","backoffCount","console","log","setTimeout","_postCurrentAnalyticsEvent","textToSend","length","warn","fetch","method","headers","Content-Type","body","then","res","status","error","catch","_setupTimers","clearInterval","setInterval","initSession","accountIDInit","appNameInit","postIntervalSecondsInit","granularitySecInit","postBaseURLInit","_ensureAnalyticsEventExists","eventType","category","subCategory","time","valueCount","_validateEvent","count","value","_updateExistingAnalyticsEvent","index","newValue","storedValueIsCount","newValueCount","storedValueObject","analyticsEvent","eventCategory","eventCount","eventValue","timeArray","push"],"mappings":"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"}
1
+ {"version":3,"sourceRoot":"src/analytics.js","sources":["src/analytics.js"],"names":["let","accountID","appName","userID","sessionID","postIntervalSeconds","granularitySec","analyticsURL","postURL","serverConfig","DEFAULT_GRANULARITY_IN_SECONDS","DEFAULT_RETRY_TIME_IN_SECONDS","DEFAULT_POST_INTERVAL_SECONDS","USERID_LOCAL_STORAGE_KEY","POST_LARGE_DATA_THRESHOLD_BYTES","currentAnalyticsEvent","IS_NODE_ENV","window","DEFAULT_BASE_URL","granularityTimer","postTimer","currentQuantisedTime","disabled","debugMode","debugLog","args","console","log","debugError","error","Error","_createAnalyticsEvent","schemaVersion","uuid","unixTimestampUTC","Date","numEventsTotal","events","_validateCurrentState","getCurrentAnalyticsEvent","JSON","parse","stringify","_getOrCreateUserID","localUserID","localStorage","getItem","crypto","randomUUID","setItem","_getOrCreateSessionID","localSessionID","sessionStorage","Math","random","toString","substr","_setupIDs","_retryPost","eventToSend","backoffCount","setTimeout","_postCurrentAnalyticsEvent","textToSend","_resetGranularityTimer","length","warn","fetch","method","headers","Content-Type","body","then","res","status","catch","disable","clearInterval","setInterval","_setupTimers","async","_getServerConfig","Promise","resolve","reject","configURL","serverResponse","json","err","getAppConfig","_initFromRemoteConfig","postIntervalSecondsInit","granularitySecInit","_stripTrailingSlash","url","replace","initSession","accountIDInit","appNameInit","analyticsURLInit","debug","_ensureAnalyticsEventExists","eventType","category","subCategory","time","valueCount","_validateEvent","count","value","_updateExistingAnalyticsEvent","index","newValue","storedValueIsCount","newValueCount","storedValueObject","analyticsEvent","eventCategory","eventCount","eventValue","timeArray","push"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aicore/core-analytics-client-lib",
3
- "version": "1.0.3",
3
+ "version": "1.0.4",
4
4
  "description": "Analytics client library for https://github.com/aicore/Core-Analytics-Server",
5
5
  "main": "dist/analytics.min.js",
6
6
  "type": "module",
@@ -26,9 +26,10 @@
26
26
  "cover:unit": "echo please open test/index.html in browser to run tests",
27
27
  "cover:integ": "echo please open test/index.html in browser to run tests",
28
28
  "build": "",
29
- "patchVersion": "npm --no-git-tag-version version patch",
30
29
  "minify": "echo creating minified package dist/analytics.min.js && mkdir -p dist && uglifyjs src/analytics.js --compress --mangle -o dist/analytics.min.js -c -m --source-map \"root='src/analytics.js',url='analytics.min.js.map'\"",
31
- "release": "npm run patchVersion && npm run minify"
30
+ "bumpPatchVersion": "npm --no-git-tag-version version patch",
31
+ "bumpPatchVersionWithGitTag": "npm version patch",
32
+ "release": "npm run minify && npm run bumpPatchVersionWithGitTag"
32
33
  },
33
34
  "files": [
34
35
  "src",
@@ -45,13 +46,13 @@
45
46
  },
46
47
  "homepage": "https://github.com/aicore/core-analytics-client-lib#readme",
47
48
  "devDependencies": {
48
- "@commitlint/cli": "16.1.0",
49
- "@commitlint/config-conventional": "16.0.0",
50
- "c8": "7.11.0",
49
+ "@commitlint/cli": "16.3.0",
50
+ "@commitlint/config-conventional": "16.2.4",
51
+ "c8": "7.11.2",
51
52
  "chai": "4.3.6",
52
- "eslint": "8.8.0",
53
+ "eslint": "8.15.0",
53
54
  "husky": "7.0.4",
54
- "mocha": "9.2.0",
55
- "uglify-js": "3.15.1"
55
+ "mocha": "9.2.2",
56
+ "uglify-js": "3.15.5"
56
57
  }
57
58
  }
package/src/analytics.js CHANGED
@@ -3,7 +3,7 @@
3
3
  // jshint ignore: start
4
4
  /*global localStorage, sessionStorage, crypto*/
5
5
 
6
- let accountID, appName, userID, sessionID, postIntervalSeconds, granularitySec, postURL;
6
+ let accountID, appName, userID, sessionID, postIntervalSeconds, granularitySec, analyticsURL, postURL, serverConfig;
7
7
  const DEFAULT_GRANULARITY_IN_SECONDS = 3;
8
8
  const DEFAULT_RETRY_TIME_IN_SECONDS = 30;
9
9
  const DEFAULT_POST_INTERVAL_SECONDS = 600; // 10 minutes
@@ -16,6 +16,23 @@ let DEFAULT_BASE_URL = "https://analytics.core.ai";
16
16
  let granularityTimer;
17
17
  let postTimer;
18
18
  let currentQuantisedTime = 0;
19
+ let disabled = false;
20
+ let debugMode = false;
21
+
22
+ function debugLog(...args) {
23
+ if(!debugMode){
24
+ return;
25
+ }
26
+ console.log(...args);
27
+ }
28
+
29
+ function debugError(...args) {
30
+ if(!debugMode){
31
+ return;
32
+ }
33
+ console.error(...args);
34
+ }
35
+
19
36
 
20
37
  if(IS_NODE_ENV){
21
38
  throw new Error("Node environment is not currently supported");
@@ -28,7 +45,6 @@ function _createAnalyticsEvent() {
28
45
  appName: appName,
29
46
  uuid: userID,
30
47
  sessionID: sessionID,
31
- granularitySec: granularitySec,
32
48
  unixTimestampUTC: +new Date(),
33
49
  numEventsTotal: 0,
34
50
  events: {}
@@ -72,7 +88,7 @@ function _setupIDs() {
72
88
 
73
89
  function _retryPost(eventToSend) {
74
90
  eventToSend.backoffCount = (eventToSend.backoffCount || 0) + 1;
75
- console.log(`Failed to call core analytics server. Will retry in ${
91
+ debugLog(`Failed to call core analytics server. Will retry in ${
76
92
  DEFAULT_RETRY_TIME_IN_SECONDS * eventToSend.backoffCount}s: `);
77
93
  setTimeout(()=>{
78
94
  _postCurrentAnalyticsEvent(eventToSend);
@@ -80,8 +96,13 @@ function _retryPost(eventToSend) {
80
96
  }
81
97
 
82
98
  function _postCurrentAnalyticsEvent(eventToSend) {
99
+ if(disabled){
100
+ return;
101
+ }
83
102
  if(!eventToSend){
84
103
  eventToSend = currentAnalyticsEvent;
104
+ currentQuantisedTime = 0;
105
+ _resetGranularityTimer();
85
106
  currentAnalyticsEvent = _createAnalyticsEvent();
86
107
  }
87
108
  if(eventToSend.numEventsTotal === 0 ){
@@ -92,6 +113,7 @@ function _postCurrentAnalyticsEvent(eventToSend) {
92
113
  console.warn(`Analytics event generated is very large at greater than ${textToSend.length}B. This
93
114
  typically means that you may be sending too many value events? .`);
94
115
  }
116
+ debugLog("Sending Analytics data of length: ", textToSend.length, "B");
95
117
  window.fetch(postURL, {
96
118
  method: "POST",
97
119
  headers: {'Content-Type': 'application/json'},
@@ -103,53 +125,123 @@ function _postCurrentAnalyticsEvent(eventToSend) {
103
125
  if(res.status !== 400){ // we don't retry bad requests
104
126
  _retryPost(eventToSend);
105
127
  } else {
106
- console.error("Bad Request, this is most likely a problem with the library, update to latest version.");
128
+ console.error("Analytics client: " +
129
+ "Bad Request, this is most likely a problem with the library, update to latest version.");
107
130
  }
108
131
  }).catch(res => {
109
- console.error(res);
132
+ debugError(res);
110
133
  _retryPost(eventToSend);
111
134
  });
112
135
  }
113
136
 
114
- function _setupTimers() {
137
+ function _resetGranularityTimer(disable) {
115
138
  if(granularityTimer){
116
139
  clearInterval(granularityTimer);
117
140
  granularityTimer = null;
118
141
  }
142
+ if(disable){
143
+ return;
144
+ }
119
145
  granularityTimer = setInterval(()=>{
120
146
  currentQuantisedTime = currentQuantisedTime + granularitySec;
121
147
  }, granularitySec*1000);
148
+ }
122
149
 
150
+ function _setupTimers(disable) {
151
+ _resetGranularityTimer(disable);
123
152
  if(postTimer){
124
153
  clearInterval(postTimer);
125
154
  postTimer = null;
126
155
  }
156
+ if(disable){
157
+ return;
158
+ }
127
159
  postTimer = setInterval(_postCurrentAnalyticsEvent, postIntervalSeconds*1000);
128
160
  }
129
161
 
162
+ async function _getServerConfig() {
163
+ return new Promise((resolve, reject)=>{
164
+ let configURL = analyticsURL + `/getAppConfig?accountID=${accountID}&appName=${appName}`;
165
+ window.fetch(configURL).then(async res=>{
166
+ switch (res.status) {
167
+ case 200:
168
+ let serverResponse = await res.json();
169
+ resolve(serverResponse);
170
+ return;
171
+ case 400:
172
+ reject("Bad Request, check library version compatible?", res);
173
+ break;
174
+ default:
175
+ reject("analytics client: Could not update from remote config. Continuing with defaults.", res);
176
+ }
177
+ }).catch(err => {
178
+ reject("analytics client: Could not update from remote config. Continuing with defaults.", err);
179
+ });
180
+ });
181
+ }
182
+
183
+ /**
184
+ * Returns the analytics config for the app
185
+ * @returns {Object}
186
+ */
187
+ function getAppConfig() {
188
+ return {
189
+ accountID, appName, disabled,
190
+ uuid: userID, sessionID,
191
+ postIntervalSeconds, granularitySec, analyticsURL, serverConfig
192
+ };
193
+ }
194
+
195
+ async function _initFromRemoteConfig(postIntervalSecondsInit, granularitySecInit) {
196
+ serverConfig = await _getServerConfig();
197
+ if(serverConfig !== {}){
198
+ // User init overrides takes precedence over server overrides
199
+ postIntervalSeconds = postIntervalSecondsInit ||
200
+ serverConfig["postIntervalSecondsInit"] || DEFAULT_POST_INTERVAL_SECONDS;
201
+ granularitySec = granularitySecInit || serverConfig["granularitySecInit"] || DEFAULT_GRANULARITY_IN_SECONDS;
202
+ // For URLs, the server suggested URL takes precedence over user init values
203
+ analyticsURL = serverConfig["analyticsURLInit"] || analyticsURL || DEFAULT_BASE_URL;
204
+ disabled = serverConfig["disabled"] === true;
205
+ _setupTimers(disabled);
206
+ debugLog(`Init analytics Config from remote. disabled: ${disabled}
207
+ postIntervalSeconds:${postIntervalSeconds}, granularitySec: ${granularitySec} ,URL: ${analyticsURL}`);
208
+ if(disabled){
209
+ console.warn(`Core Analytics is disabled from the server for app: ${accountID}:${appName}`);
210
+ }
211
+ }
212
+ }
213
+
214
+ function _stripTrailingSlash(url) {
215
+ return url.replace(/\/$/, "");
216
+ }
217
+
130
218
  /**
131
219
  * Initialize the analytics session
132
220
  * @param accountIDInit Your analytics account id as configured in the server or core.ai analytics
133
221
  * @param appNameInit The app name to log the events against.
222
+ * @param analyticsURLInit Optional: Provide your own analytics server address if you self-hosted the server
134
223
  * @param postIntervalSecondsInit Optional: This defines the interval between sending analytics events to the server.
135
224
  * Default is 10 minutes
136
225
  * @param granularitySecInit Optional: The smallest time period under which the events can be distinguished. Multiple
137
226
  * events happening during this time period is aggregated to a count. The default granularity is 3 Seconds, which means
138
227
  * that any events that happen within 3 seconds cannot be distinguished in ordering.
139
- * @param postBaseURLInit Optional: Provide your own analytics server address if you self-hosted the server
228
+ * @param debug set to true if you want to see detailed debug logs.
140
229
  */
141
- function initSession(accountIDInit, appNameInit, postIntervalSecondsInit, granularitySecInit, postBaseURLInit) {
230
+ function initSession(accountIDInit, appNameInit, analyticsURLInit, postIntervalSecondsInit, granularitySecInit, debug) {
142
231
  if(!accountIDInit || !appNameInit){
143
232
  throw new Error("accountID and appName must exist for init");
144
233
  }
234
+ analyticsURL = analyticsURLInit? _stripTrailingSlash(analyticsURLInit) : DEFAULT_BASE_URL;
145
235
  accountID = accountIDInit;
146
236
  appName = appNameInit;
237
+ debugMode = debug || false;
147
238
  postIntervalSeconds = postIntervalSecondsInit || DEFAULT_POST_INTERVAL_SECONDS;
148
239
  granularitySec = granularitySecInit || DEFAULT_GRANULARITY_IN_SECONDS;
149
- postURL = (postBaseURLInit || DEFAULT_BASE_URL) + "/ingest";
240
+ postURL = analyticsURL + "/ingest";
150
241
  _setupIDs();
151
242
  currentAnalyticsEvent = _createAnalyticsEvent();
152
243
  _setupTimers();
244
+ _initFromRemoteConfig(postIntervalSecondsInit, granularitySecInit);
153
245
  }
154
246
 
155
247
  function _ensureAnalyticsEventExists(eventType, category, subCategory) {
@@ -202,6 +294,9 @@ function _updateExistingAnalyticsEvent(index, eventType, category, subCategory,
202
294
  * @param eventValue (Optional) : A number value associated with the event. defaults to 0
203
295
  */
204
296
  function analyticsEvent(eventType, eventCategory, subCategory, eventCount=1, eventValue=0) {
297
+ if(disabled){
298
+ return;
299
+ }
205
300
  _validateEvent(eventType, eventCategory, subCategory, eventCount, eventValue);
206
301
  _ensureAnalyticsEventExists(eventType, eventCategory, subCategory);
207
302
  let events = currentAnalyticsEvent.events;
@@ -226,5 +321,6 @@ function analyticsEvent(eventType, eventCategory, subCategory, eventCount=1, eve
226
321
  export {
227
322
  initSession,
228
323
  getCurrentAnalyticsEvent,
229
- analyticsEvent
324
+ analyticsEvent,
325
+ getAppConfig
230
326
  };
@@ -8,16 +8,20 @@ schema:
8
8
  "appName" : "app1",
9
9
  "uuid": "u1",
10
10
  "sessionID": "s1",
11
- "granularitySec" : 3,
12
11
  "unixTimestampUTC" : 1643043376,
13
- "numEventsTotal": 25,
12
+ "numEventsTotal": 8,
14
13
  "events":{
15
14
  "eventType":{
16
15
  "category":{
17
16
  "subCategory": {
18
- "t": [0,3],
19
- "v": [1,[1,3]],
20
- "c": [23,2]
17
+ "time": [0,2],
18
+ "valueCount": [
19
+ 1,
20
+ [{
21
+ "1": 5,
22
+ "3": 2
23
+ }]
24
+ ]
21
25
  }
22
26
  }
23
27
  }
@@ -30,49 +34,58 @@ schema:
30
34
  1. `appName`: The application name for which the event is being raised.
31
35
  2. `uuid`: The unique id for the user. or the string `default` if there is no UUID/anonymous analytics is used from client.
32
36
  3. `sessionID`: The unique session-id autogenerated by the client lib for each session. Will be reset for every session.
33
- 4. `granularitySec`: The minimum granularity for event recording in seconds. Repeating events within the same granularity window will be aggregated and only the count will be increased.
34
37
  5. `unixTimestampUTC`: The start Unix time from which the client time is being recorded.
35
38
  5. `numEventsTotal`: The sum total of all events raised from the client. This aggregates all count values `c`
36
- 6. `events` : A map of events that took place from `unixTimestamp`. The keys are nested in order `eventType` > `category` > `subCategory`
37
- * Within a subcategory, `t` array specifies the `time window` in seconds from the `unixTimestamp` for which the current event is raised.
38
- * `v` array specifies the `values` if any that are logged as part of the event. If no value is specified, the default value `1` is used. If multiple values are logged within the same window, it is logged as an array.
39
- * `c` array specifies the `count` of events that happened within the time window. For Eg. in the above schema, the event that started in window 0 repeated 23 counts within the window with the default value(1).
39
+ 6. `events` : A map of events that took place from `unixTimestampUTC`. The keys are nested in order `eventType` > `category` > `subCategory`
40
+ * Within a subcategory, `time` array specifies the `time drift` in seconds from the `unixTimestampUTC` for which the current event is raised.
41
+ * `valueCount` array specifies the `values` and/or related counts. If the array
42
+ item is a number, then it signifies count. If it is an object, then
43
+ it indicates values and the corresponding counts.
40
44
 
41
45
  ## sample analytics event
42
46
  Schema
43
47
  ```json
44
48
  {
45
- "schemaVersion" : 1,
46
- "appName" : "brackets",
47
- "uuid": "u1",
48
- "sessionID": "s1",
49
- "granularitySec" : 3,
50
- "unixTimestampUTC" : 1643043376,
51
- "numEventsTotal" : 5,
52
- "events":{
53
- "platform":{
54
- "os":{
55
- "win": {
56
- "t": [0],
57
- "v": [1],
58
- "c": [1]
59
- }
60
- }, "performance":{
61
- "fileOpenTimeMs": {
62
- "t": [0,3,6],
63
- "v": [102, [50,34], 200],
64
- "c": [1,2,1]
49
+ "schemaVersion": 1,
50
+ "appName": "brackets",
51
+ "uuid": "u1",
52
+ "sessionID": "s1",
53
+ "unixTimestampUTC": 1643043376,
54
+ "numEventsTotal": 5,
55
+ "events": {
56
+ "platform": {
57
+ "os": {
58
+ "win": {
59
+ "time": [0],
60
+ "valueCount": [1]
61
+ }
62
+ },
63
+ "performance": {
64
+ "fileOpenTimeMs": {
65
+ "time": [0, 2, 5],
66
+ "valueCount": [
67
+ [{
68
+ "121": 1
69
+ }],
70
+ [{
71
+ "100": 1,
72
+ "300": 1
73
+ }],
74
+ [{
75
+ "100": 5
76
+ }]
77
+ ]
78
+ }
79
+ }
65
80
  }
66
- }
67
81
  }
68
- }
69
82
  }
70
83
 
71
84
  ```
72
85
  The above event raises two event types :
73
86
  1. (platform, os, win)
74
87
  2. (platform, performance, fileOpenTimeMs)
75
- * at time `1643043376 + 0`, a value of `102` is registered.
76
- * at time `1643043376 + 3000`, two values `[50,34]` are registered.
77
- * at time `1643043376 + 6000`, a value of 200 is registered.
88
+ * at time `1643043376 + 0`, a value of `121` is registered and count is 1.
89
+ * at time `1643043376 + 3000`, two values `[100,300]` are registered with a count each of 1.
90
+ * at time `1643043376 + 6000`, a value of `500` is registered with a count of 5.
78
91