UNPKG

2.85 kBJavaScriptView Raw
1// the `unique` module
2var unique = {};
3
4// global results store
5// currently uniqueness is global to entire faker instance
6// this means that faker should currently *never* return duplicate values across all API methods when using `Faker.unique`
7// it's possible in the future that some users may want to scope found per function call instead of faker instance
8var found = {};
9
10// global exclude list of results
11// defaults to nothing excluded
12var exclude = [];
13
14// current iteration or retries of unique.exec ( current loop depth )
15var currentIterations = 0;
16
17// uniqueness compare function
18// default behavior is to check value as key against object hash
19var defaultCompare = function(obj, key) {
20 if (typeof obj[key] === 'undefined') {
21 return -1;
22 }
23 return 0;
24};
25
26// common error handler for messages
27unique.errorMessage = function (now, code, opts) {
28 console.error('error', code);
29 console.log('found', Object.keys(found).length, 'unique entries before throwing error. \nretried:', currentIterations, '\ntotal time:', now - opts.startTime, 'ms');
30 throw new Error(code + ' for uniqueness check \n\nMay not be able to generate any more unique values with current settings. \nTry adjusting maxTime or maxRetries parameters for faker.unique()')
31};
32
33unique.exec = function (method, args, opts) {
34 //console.log(currentIterations)
35
36 var now = new Date().getTime();
37
38 opts = opts || {};
39 opts.maxTime = opts.maxTime || 3;
40 opts.maxRetries = opts.maxRetries || 50;
41 opts.exclude = opts.exclude || exclude;
42 opts.compare = opts.compare || defaultCompare;
43
44 if (typeof opts.currentIterations !== 'number') {
45 opts.currentIterations = 0;
46 }
47
48 if (typeof opts.startTime === 'undefined') {
49 opts.startTime = new Date().getTime();
50 }
51
52 var startTime = opts.startTime;
53
54 // support single exclude argument as string
55 if (typeof opts.exclude === 'string') {
56 opts.exclude = [opts.exclude];
57 }
58
59 if (opts.currentIterations > 0) {
60 // console.log('iterating', currentIterations)
61 }
62
63 // console.log(now - startTime)
64 if (now - startTime >= opts.maxTime) {
65 return unique.errorMessage(now, 'Exceeded maxTime:' + opts.maxTime, opts);
66 }
67
68 if (opts.currentIterations >= opts.maxRetries) {
69 return unique.errorMessage(now, 'Exceeded maxRetries:' + opts.maxRetries, opts);
70 }
71
72 // execute the provided method to find a potential satifised value
73 var result = method.apply(this, args);
74
75 // if the result has not been previously found, add it to the found array and return the value as it's unique
76 if (opts.compare(found, result) === -1 && opts.exclude.indexOf(result) === -1) {
77 found[result] = result;
78 opts.currentIterations = 0;
79 return result;
80 } else {
81 // console.log('conflict', result);
82 opts.currentIterations++;
83 return unique.exec(method, args, opts);
84 }
85};
86
87module.exports = unique;