make-mp-data 1.4.1 → 1.4.2
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/defaults.js +799 -11487
- package/index.js +184 -78
- package/package.json +3 -3
- package/schemas/simple.js +10 -0
- package/scratch.mjs +3 -2
- package/tests/unit.test.js +5 -4
- package/types.d.ts +15 -2
- package/utils.js +72 -13
package/utils.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const fs = require('fs');
|
|
2
2
|
const Chance = require('chance');
|
|
3
3
|
const readline = require('readline');
|
|
4
|
-
const { comma, uid } = require('ak-tools');
|
|
4
|
+
const { comma, uid, clone } = require('ak-tools');
|
|
5
5
|
const { spawn } = require('child_process');
|
|
6
6
|
const dayjs = require('dayjs');
|
|
7
7
|
const utc = require('dayjs/plugin/utc');
|
|
@@ -225,6 +225,7 @@ function integer(min = 1, max = 100) {
|
|
|
225
225
|
|
|
226
226
|
function pickAWinner(items, mostChosenIndex) {
|
|
227
227
|
const chance = getChance();
|
|
228
|
+
if (!mostChosenIndex) mostChosenIndex = integer(0, items.length);
|
|
228
229
|
if (mostChosenIndex > items.length) mostChosenIndex = items.length;
|
|
229
230
|
return function () {
|
|
230
231
|
const weighted = [];
|
|
@@ -252,6 +253,48 @@ function pickAWinner(items, mostChosenIndex) {
|
|
|
252
253
|
}
|
|
253
254
|
|
|
254
255
|
|
|
256
|
+
function inferFunnels(events) {
|
|
257
|
+
const createdFunnels = [];
|
|
258
|
+
const firstEvents = events.filter((e) => e.isFirstEvent).map((e) => e.event);
|
|
259
|
+
const usageEvents = events.filter((e) => !e.isFirstEvent).map((e) => e.event);
|
|
260
|
+
const numFunnelsToCreate = Math.ceil(usageEvents.length);
|
|
261
|
+
/** @type {Funnel} */
|
|
262
|
+
const funnelTemplate = {
|
|
263
|
+
sequence: [],
|
|
264
|
+
conversionRate: 50,
|
|
265
|
+
order: 'sequential',
|
|
266
|
+
requireRepeats: false,
|
|
267
|
+
props: {},
|
|
268
|
+
timeToConvert: 1,
|
|
269
|
+
isFirstFunnel: false,
|
|
270
|
+
weight: 1
|
|
271
|
+
};
|
|
272
|
+
if (firstEvents.length) {
|
|
273
|
+
for (const event of firstEvents) {
|
|
274
|
+
createdFunnels.push({ ...clone(funnelTemplate), sequence: [event], isFirstFunnel: true, conversionRate: 100 });
|
|
275
|
+
}
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
//at least one funnel with all usage events
|
|
279
|
+
createdFunnels.push({ ...clone(funnelTemplate), sequence: usageEvents });
|
|
280
|
+
|
|
281
|
+
//for the rest, make random funnels
|
|
282
|
+
followUpFunnels: for (let i = 1; i < numFunnelsToCreate; i++) {
|
|
283
|
+
/** @type {Funnel} */
|
|
284
|
+
const funnel = { ...clone(funnelTemplate) };
|
|
285
|
+
funnel.conversionRate = integer(25, 75);
|
|
286
|
+
funnel.timeToConvert = integer(1, 10);
|
|
287
|
+
funnel.weight = integer(1, 10);
|
|
288
|
+
const sequence = shuffleArray(usageEvents).slice(0, integer(2, usageEvents.length));
|
|
289
|
+
funnel.sequence = sequence;
|
|
290
|
+
funnel.order = 'random';
|
|
291
|
+
createdFunnels.push(funnel);
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
return createdFunnels;
|
|
295
|
+
|
|
296
|
+
}
|
|
297
|
+
|
|
255
298
|
/*
|
|
256
299
|
----
|
|
257
300
|
GENERATORS
|
|
@@ -274,7 +317,10 @@ function optimizedBoxMuller() {
|
|
|
274
317
|
const chance = getChance();
|
|
275
318
|
const u = Math.max(Math.min(chance.normal({ mean: .5, dev: .25 }), 1), 0);
|
|
276
319
|
const v = Math.max(Math.min(chance.normal({ mean: .5, dev: .25 }), 1), 0);
|
|
277
|
-
|
|
320
|
+
const result = Math.sqrt(-2.0 * Math.log(u)) * Math.cos(2.0 * Math.PI * v);
|
|
321
|
+
//ensure we didn't get infinity
|
|
322
|
+
if (result === Infinity || result === -Infinity) return chance.floating({ min: 0, max: 1 });
|
|
323
|
+
return result;
|
|
278
324
|
|
|
279
325
|
}
|
|
280
326
|
|
|
@@ -769,31 +815,36 @@ function TimeSoup(earliestTime, latestTime, peaks = 5, deviation = 2, mean = 0)
|
|
|
769
815
|
|
|
770
816
|
|
|
771
817
|
/**
|
|
818
|
+
* @param {string} userId
|
|
772
819
|
* @param {number} bornDaysAgo=30
|
|
820
|
+
* @param {boolean} isAnonymous
|
|
773
821
|
* @return {Person}
|
|
774
822
|
*/
|
|
775
|
-
function person(bornDaysAgo = 30) {
|
|
823
|
+
function person(userId, bornDaysAgo = 30, isAnonymous = false) {
|
|
776
824
|
const chance = getChance();
|
|
777
825
|
//names and photos
|
|
826
|
+
const l = chance.letter;
|
|
778
827
|
let gender = chance.pickone(['male', 'female']);
|
|
779
828
|
if (!gender) gender = "female";
|
|
780
829
|
// @ts-ignore
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
830
|
+
let first = chance.first({ gender });
|
|
831
|
+
let last = chance.last();
|
|
832
|
+
let name = `${first} ${last}`;
|
|
833
|
+
let email = `${first[0]}.${last}@${chance.domain()}.com`;
|
|
834
|
+
let avatarPrefix = `https://randomuser.me/api/portraits`;
|
|
835
|
+
let randomAvatarNumber = chance.integer({
|
|
787
836
|
min: 1,
|
|
788
837
|
max: 99
|
|
789
838
|
});
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
839
|
+
let avPath = gender === 'male' ? `/men/${randomAvatarNumber}.jpg` : `/women/${randomAvatarNumber}.jpg`;
|
|
840
|
+
let avatar = avatarPrefix + avPath;
|
|
841
|
+
let created = dayjs.unix(global.NOW).subtract(bornDaysAgo, 'day').format('YYYY-MM-DD');
|
|
793
842
|
// const created = date(bornDaysAgo, true)();
|
|
794
843
|
|
|
844
|
+
|
|
795
845
|
/** @type {Person} */
|
|
796
846
|
const user = {
|
|
847
|
+
distinct_id: userId,
|
|
797
848
|
name,
|
|
798
849
|
email,
|
|
799
850
|
avatar,
|
|
@@ -802,6 +853,13 @@ function person(bornDaysAgo = 30) {
|
|
|
802
853
|
sessionIds: []
|
|
803
854
|
};
|
|
804
855
|
|
|
856
|
+
if (isAnonymous) {
|
|
857
|
+
user.name = "Anonymous User";
|
|
858
|
+
user.email = `${l()}${l()}****${l()}${l()}@${l()}**${l()}*.com`;
|
|
859
|
+
delete user.avatar;
|
|
860
|
+
|
|
861
|
+
}
|
|
862
|
+
|
|
805
863
|
//anon Ids
|
|
806
864
|
if (global.MP_SIMULATION_CONFIG?.anonIds) {
|
|
807
865
|
const clusterSize = integer(2, 10);
|
|
@@ -921,5 +979,6 @@ module.exports = {
|
|
|
921
979
|
optimizedBoxMuller,
|
|
922
980
|
buildFileNames,
|
|
923
981
|
streamJSON,
|
|
924
|
-
streamCSV
|
|
982
|
+
streamCSV,
|
|
983
|
+
inferFunnels
|
|
925
984
|
};
|