1 import { describe
, it
} from
'node:test'
3 import { hoursToMilliseconds
, hoursToSeconds
} from
'date-fns'
4 import { expect
} from
'expect'
6 import { Constants
} from
'../../src/utils/Constants.js'
13 extractTimeSeriesValues
,
14 formatDurationMilliSeconds
,
15 formatDurationSeconds
,
37 } from
'../../src/utils/Utils.js'
39 await describe('Utils test suite', async () => {
40 await it('Verify generateUUID()/validateUUID()', () => {
41 const uuid
= generateUUID()
42 expect(uuid
).toBeDefined()
43 expect(uuid
.length
).toEqual(36)
44 expect(validateUUID(uuid
)).toBe(true)
45 expect(validateUUID('abcdef00-0000-4000-0000-000000000000')).toBe(true)
46 expect(validateUUID('')).toBe(false)
47 // Shall invalidate Nil UUID
48 expect(validateUUID('00000000-0000-0000-0000-000000000000')).toBe(false)
49 expect(validateUUID('987FBC9-4BED-3078-CF07A-9141BA07C9F3')).toBe(false)
52 await it('Verify sleep()', async () => {
53 const start
= performance
.now()
55 const stop
= performance
.now()
56 expect(stop
- start
).toBeGreaterThanOrEqual(1000)
59 await it('Verify formatDurationMilliSeconds()', () => {
60 expect(formatDurationMilliSeconds(0)).toBe('0 seconds')
61 expect(formatDurationMilliSeconds(900)).toBe('0 seconds')
62 expect(formatDurationMilliSeconds(1000)).toBe('1 second')
63 expect(formatDurationMilliSeconds(hoursToMilliseconds(4380))).toBe('182 days 12 hours')
66 await it('Verify formatDurationSeconds()', () => {
67 expect(formatDurationSeconds(0)).toBe('0 seconds')
68 expect(formatDurationSeconds(0.9)).toBe('0 seconds')
69 expect(formatDurationSeconds(1)).toBe('1 second')
70 expect(formatDurationSeconds(hoursToSeconds(4380))).toBe('182 days 12 hours')
73 await it('Verify isValidTime()', () => {
74 expect(isValidTime(undefined)).toBe(false)
75 expect(isValidTime(null)).toBe(false)
76 expect(isValidTime('')).toBe(false)
77 expect(isValidTime({})).toBe(false)
78 expect(isValidTime([])).toBe(false)
79 expect(isValidTime(new Map())).toBe(false)
80 expect(isValidTime(new Set())).toBe(false)
81 expect(isValidTime(new WeakMap())).toBe(false)
82 expect(isValidTime(new WeakSet())).toBe(false)
83 expect(isValidTime(-1)).toBe(true)
84 expect(isValidTime(0)).toBe(true)
85 expect(isValidTime(1)).toBe(true)
86 expect(isValidTime(-0.5)).toBe(true)
87 expect(isValidTime(0.5)).toBe(true)
88 expect(isValidTime(new Date())).toBe(true)
91 await it('Verify convertToDate()', () => {
92 expect(convertToDate(undefined)).toBe(undefined)
93 expect(convertToDate(null)).toBe(null)
94 expect(() => convertToDate('')).toThrow(new Error("Cannot convert to date: ''"))
95 expect(() => convertToDate('00:70:61')).toThrow(new Error("Cannot convert to date: '00:70:61'"))
96 expect(convertToDate(0)).toStrictEqual(new Date('1970-01-01T00:00:00.000Z'))
97 expect(convertToDate(-1)).toStrictEqual(new Date('1969-12-31T23:59:59.999Z'))
98 const dateStr
= '2020-01-01T00:00:00.000Z'
99 let date
= convertToDate(dateStr
)
100 expect(date
).toBeInstanceOf(Date)
101 expect(date
).toStrictEqual(new Date(dateStr
))
102 date
= convertToDate(new Date(dateStr
))
103 expect(date
).toBeInstanceOf(Date)
104 expect(date
).toStrictEqual(new Date(dateStr
))
107 await it('Verify convertToInt()', () => {
108 expect(convertToInt(undefined)).toBe(0)
109 expect(convertToInt(null)).toBe(0)
110 expect(convertToInt(0)).toBe(0)
111 const randomInteger
= getRandomInteger()
112 expect(convertToInt(randomInteger
)).toEqual(randomInteger
)
113 expect(convertToInt('-1')).toBe(-1)
114 expect(convertToInt('1')).toBe(1)
115 expect(convertToInt('1.1')).toBe(1)
116 expect(convertToInt('1.9')).toBe(1)
117 expect(convertToInt('1.999')).toBe(1)
118 expect(convertToInt(-1)).toBe(-1)
119 expect(convertToInt(1)).toBe(1)
120 expect(convertToInt(1.1)).toBe(1)
121 expect(convertToInt(1.9)).toBe(1)
122 expect(convertToInt(1.999)).toBe(1)
125 }).toThrow("Cannot convert to integer: 'NaN'")
128 await it('Verify convertToFloat()', () => {
129 expect(convertToFloat(undefined)).toBe(0)
130 expect(convertToFloat(null)).toBe(0)
131 expect(convertToFloat(0)).toBe(0)
132 const randomFloat
= getRandomFloat()
133 expect(convertToFloat(randomFloat
)).toEqual(randomFloat
)
134 expect(convertToFloat('-1')).toBe(-1)
135 expect(convertToFloat('1')).toBe(1)
136 expect(convertToFloat('1.1')).toBe(1.1)
137 expect(convertToFloat('1.9')).toBe(1.9)
138 expect(convertToFloat('1.999')).toBe(1.999)
139 expect(convertToFloat(-1)).toBe(-1)
140 expect(convertToFloat(1)).toBe(1)
141 expect(convertToFloat(1.1)).toBe(1.1)
142 expect(convertToFloat(1.9)).toBe(1.9)
143 expect(convertToFloat(1.999)).toBe(1.999)
145 convertToFloat('NaN')
146 }).toThrow("Cannot convert to float: 'NaN'")
149 await it('Verify convertToBoolean()', () => {
150 expect(convertToBoolean(undefined)).toBe(false)
151 expect(convertToBoolean(null)).toBe(false)
152 expect(convertToBoolean('true')).toBe(true)
153 expect(convertToBoolean('false')).toBe(false)
154 expect(convertToBoolean('TRUE')).toBe(true)
155 expect(convertToBoolean('FALSE')).toBe(false)
156 expect(convertToBoolean('1')).toBe(true)
157 expect(convertToBoolean('0')).toBe(false)
158 expect(convertToBoolean(1)).toBe(true)
159 expect(convertToBoolean(0)).toBe(false)
160 expect(convertToBoolean(true)).toBe(true)
161 expect(convertToBoolean(false)).toBe(false)
162 expect(convertToBoolean('')).toBe(false)
163 expect(convertToBoolean('NoNBoolean')).toBe(false)
166 await it('Verify secureRandom()', () => {
167 const random
= secureRandom()
168 expect(typeof random
=== 'number').toBe(true)
169 expect(random
).toBeGreaterThanOrEqual(0)
170 expect(random
).toBeLessThan(1)
173 await it('Verify getRandomInteger()', () => {
174 let randomInteger
= getRandomInteger()
175 expect(Number.isSafeInteger(randomInteger
)).toBe(true)
176 expect(randomInteger
).toBeGreaterThanOrEqual(0)
177 expect(randomInteger
).toBeLessThanOrEqual(Constants
.MAX_RANDOM_INTEGER
)
178 expect(randomInteger
).not
.toEqual(getRandomInteger())
179 randomInteger
= getRandomInteger(0, -Constants
.MAX_RANDOM_INTEGER
)
180 expect(randomInteger
).toBeGreaterThanOrEqual(-Constants
.MAX_RANDOM_INTEGER
)
181 expect(randomInteger
).toBeLessThanOrEqual(0)
182 expect(() => getRandomInteger(0, 1)).toThrow(
183 'The value of "max" is out of range. It must be greater than the value of "min" (1). Received 1'
185 expect(() => getRandomInteger(-1)).toThrow(
186 'The value of "max" is out of range. It must be greater than the value of "min" (0). Received 0'
188 expect(() => getRandomInteger(Constants
.MAX_RANDOM_INTEGER
+ 1)).toThrow(
189 `The value of "max" is out of range. It must be <= ${
190 Constants.MAX_RANDOM_INTEGER + 1
191 }. Received 281_474_976_710_656`
193 randomInteger
= getRandomInteger(2, 1)
194 expect(randomInteger
).toBeGreaterThanOrEqual(1)
195 expect(randomInteger
).toBeLessThanOrEqual(2)
198 randomInteger
= getRandomInteger(maximum
, minimum
)
199 expect(randomInteger
).toBeLessThanOrEqual(Math.floor(maximum
))
200 expect(randomInteger
).toBeGreaterThanOrEqual(Math.ceil(minimum
))
203 await it('Verify roundTo()', () => {
204 expect(roundTo(0, 2)).toBe(0)
205 expect(roundTo(0.5, 0)).toBe(1)
206 expect(roundTo(0.5, 2)).toBe(0.5)
207 expect(roundTo(-0.5, 0)).toBe(-1)
208 expect(roundTo(-0.5, 2)).toBe(-0.5)
209 expect(roundTo(1.005, 0)).toBe(1)
210 expect(roundTo(1.005, 2)).toBe(1.01)
211 expect(roundTo(2.175, 2)).toBe(2.18)
212 expect(roundTo(5.015, 2)).toBe(5.02)
213 expect(roundTo(-1.005, 2)).toBe(-1.01)
214 expect(roundTo(-2.175, 2)).toBe(-2.18)
215 expect(roundTo(-5.015, 2)).toBe(-5.02)
218 await it('Verify getRandomFloat()', () => {
219 let randomFloat
= getRandomFloat()
220 expect(typeof randomFloat
=== 'number').toBe(true)
221 expect(randomFloat
).toBeGreaterThanOrEqual(0)
222 expect(randomFloat
).toBeLessThanOrEqual(Number.MAX_VALUE
)
223 expect(randomFloat
).not
.toEqual(getRandomFloat())
224 expect(() => getRandomFloat(0, 1)).toThrow(new RangeError('Invalid interval'))
225 expect(() => getRandomFloat(Number.MAX_VALUE
, -Number.MAX_VALUE
)).toThrow(
226 new RangeError('Invalid interval')
228 randomFloat
= getRandomFloat(0, -Number.MAX_VALUE
)
229 expect(randomFloat
).toBeGreaterThanOrEqual(-Number.MAX_VALUE
)
230 expect(randomFloat
).toBeLessThanOrEqual(0)
233 await it('Verify extractTimeSeriesValues()', () => {
234 expect(extractTimeSeriesValues([])).toEqual([])
235 expect(extractTimeSeriesValues([{ timestamp
: Date.now(), value
: 1.1 }])).toEqual([1.1])
237 extractTimeSeriesValues([
238 { timestamp
: Date.now(), value
: 1.1 },
239 { timestamp
: Date.now(), value
: 2.2 }
241 ).toEqual([1.1, 2.2])
244 await it('Verify isObject()', () => {
245 expect(isObject('test')).toBe(false)
246 expect(isObject(undefined)).toBe(false)
247 expect(isObject(null)).toBe(false)
248 expect(isObject(0)).toBe(false)
249 expect(isObject([])).toBe(false)
250 expect(isObject([0, 1])).toBe(false)
251 expect(isObject(['0', '1'])).toBe(false)
252 expect(isObject({})).toBe(true)
253 expect(isObject({ 1: 1 })).toBe(true)
254 expect(isObject({ 1: '1' })).toBe(true)
255 expect(isObject(new Map())).toBe(true)
256 expect(isObject(new Set())).toBe(true)
257 expect(isObject(new WeakMap())).toBe(true)
258 expect(isObject(new WeakSet())).toBe(true)
261 await it('Verify cloneObject()', () => {
263 expect(cloneObject(obj
)).toStrictEqual(obj
)
264 expect(cloneObject(obj
) === obj
).toBe(false)
265 const nestedObj
= { 1: obj
, 2: obj
}
266 expect(cloneObject(nestedObj
)).toStrictEqual(nestedObj
)
267 expect(cloneObject(nestedObj
) === nestedObj
).toBe(false)
269 expect(cloneObject(array
)).toStrictEqual(array
)
270 expect(cloneObject(array
) === array
).toBe(false)
271 const objArray
= [obj
, obj
]
272 expect(cloneObject(objArray
)).toStrictEqual(objArray
)
273 expect(cloneObject(objArray
) === objArray
).toBe(false)
274 const date
= new Date()
275 expect(cloneObject(date
)).toStrictEqual(date
)
276 expect(cloneObject(date
) === date
).toBe(false)
277 const map
= new Map([['1', '2']])
278 expect(cloneObject(map
)).toStrictEqual({})
279 const set
= new Set(['1'])
280 expect(cloneObject(set
)).toStrictEqual({})
281 // The URL object seems to have not enumerable properties
282 const url
= new URL('https://domain.tld')
283 expect(cloneObject(url
)).toStrictEqual({})
284 const weakMap
= new WeakMap([[{ 1: 1 }, { 2: 2 }]])
285 expect(cloneObject(weakMap
)).toStrictEqual({})
286 const weakSet
= new WeakSet([{ 1: 1 }, { 2: 2 }])
287 expect(cloneObject(weakSet
)).toStrictEqual({})
290 await it('Verify hasOwnProp()', () => {
291 expect(hasOwnProp('test', '')).toBe(false)
292 expect(hasOwnProp(undefined, '')).toBe(false)
293 expect(hasOwnProp(null, '')).toBe(false)
294 expect(hasOwnProp([], '')).toBe(false)
295 expect(hasOwnProp({}, '')).toBe(false)
296 expect(hasOwnProp({ 1: 1 }, 1)).toBe(true)
297 expect(hasOwnProp({ 1: 1 }, '1')).toBe(true)
298 expect(hasOwnProp({ 1: 1 }, 2)).toBe(false)
299 expect(hasOwnProp({ 1: 1 }, '2')).toBe(false)
300 expect(hasOwnProp({ 1: '1' }, '1')).toBe(true)
301 expect(hasOwnProp({ 1: '1' }, 1)).toBe(true)
302 expect(hasOwnProp({ 1: '1' }, '2')).toBe(false)
303 expect(hasOwnProp({ 1: '1' }, 2)).toBe(false)
306 await it('Verify isIterable()', () => {
307 expect(isIterable('')).toBe(true)
308 expect(isIterable(' ')).toBe(true)
309 expect(isIterable('test')).toBe(true)
310 expect(isIterable(undefined)).toBe(false)
311 expect(isIterable(null)).toBe(false)
312 expect(isIterable(0)).toBe(false)
313 expect(isIterable([0, 1])).toBe(true)
314 expect(isIterable({ 1: 1 })).toBe(false)
315 expect(isIterable(new Map())).toBe(true)
316 expect(isIterable(new Set())).toBe(true)
317 expect(isIterable(new WeakMap())).toBe(false)
318 expect(isIterable(new WeakSet())).toBe(false)
321 await it('Verify isEmptyString()', () => {
322 expect(isEmptyString('')).toBe(true)
323 expect(isEmptyString(' ')).toBe(true)
324 expect(isEmptyString(' ')).toBe(true)
325 expect(isEmptyString('test')).toBe(false)
326 expect(isEmptyString(' test')).toBe(false)
327 expect(isEmptyString('test ')).toBe(false)
328 expect(isEmptyString(undefined)).toBe(true)
329 expect(isEmptyString(null)).toBe(true)
330 expect(isEmptyString(0)).toBe(false)
331 expect(isEmptyString({})).toBe(false)
332 expect(isEmptyString([])).toBe(false)
333 expect(isEmptyString(new Map())).toBe(false)
334 expect(isEmptyString(new Set())).toBe(false)
335 expect(isEmptyString(new WeakMap())).toBe(false)
336 expect(isEmptyString(new WeakSet())).toBe(false)
339 await it('Verify isNotEmptyString()', () => {
340 expect(isNotEmptyString('')).toBe(false)
341 expect(isNotEmptyString(' ')).toBe(false)
342 expect(isNotEmptyString(' ')).toBe(false)
343 expect(isNotEmptyString('test')).toBe(true)
344 expect(isNotEmptyString(' test')).toBe(true)
345 expect(isNotEmptyString('test ')).toBe(true)
346 expect(isNotEmptyString(undefined)).toBe(false)
347 expect(isNotEmptyString(null)).toBe(false)
348 expect(isNotEmptyString(0)).toBe(false)
349 expect(isNotEmptyString({})).toBe(false)
350 expect(isNotEmptyString([])).toBe(false)
351 expect(isNotEmptyString(new Map())).toBe(false)
352 expect(isNotEmptyString(new Set())).toBe(false)
353 expect(isNotEmptyString(new WeakMap())).toBe(false)
354 expect(isNotEmptyString(new WeakSet())).toBe(false)
357 await it('Verify isUndefined()', () => {
358 expect(isUndefined(undefined)).toBe(true)
359 expect(isUndefined(null)).toBe(false)
360 expect(isUndefined('')).toBe(false)
361 expect(isUndefined(0)).toBe(false)
362 expect(isUndefined({})).toBe(false)
363 expect(isUndefined([])).toBe(false)
364 expect(isUndefined(new Map())).toBe(false)
365 expect(isUndefined(new Set())).toBe(false)
366 expect(isUndefined(new WeakMap())).toBe(false)
367 expect(isUndefined(new WeakSet())).toBe(false)
370 await it('Verify isEmptyArray()', () => {
371 expect(isEmptyArray([])).toBe(true)
372 expect(isEmptyArray([1, 2])).toBe(false)
373 expect(isEmptyArray(['1', '2'])).toBe(false)
374 expect(isEmptyArray(undefined)).toBe(false)
375 expect(isEmptyArray(null)).toBe(false)
376 expect(isEmptyArray('')).toBe(false)
377 expect(isEmptyArray('test')).toBe(false)
378 expect(isEmptyArray(0)).toBe(false)
379 expect(isEmptyArray({})).toBe(false)
380 expect(isEmptyArray(new Map())).toBe(false)
381 expect(isEmptyArray(new Set())).toBe(false)
382 expect(isEmptyArray(new WeakMap())).toBe(false)
383 expect(isEmptyArray(new WeakSet())).toBe(false)
386 await it('Verify isNotEmptyArray()', () => {
387 expect(isNotEmptyArray([])).toBe(false)
388 expect(isNotEmptyArray([1, 2])).toBe(true)
389 expect(isNotEmptyArray(['1', '2'])).toBe(true)
390 expect(isNotEmptyArray(undefined)).toBe(false)
391 expect(isNotEmptyArray(null)).toBe(false)
392 expect(isNotEmptyArray('')).toBe(false)
393 expect(isNotEmptyArray('test')).toBe(false)
394 expect(isNotEmptyArray(0)).toBe(false)
395 expect(isNotEmptyArray({})).toBe(false)
396 expect(isNotEmptyArray(new Map())).toBe(false)
397 expect(isNotEmptyArray(new Set())).toBe(false)
398 expect(isNotEmptyArray(new WeakMap())).toBe(false)
399 expect(isNotEmptyArray(new WeakSet())).toBe(false)
402 await it('Verify isEmptyObject()', () => {
403 expect(isEmptyObject({})).toBe(true)
404 expect(isEmptyObject({ 1: 1, 2: 2 })).toBe(false)
405 expect(isEmptyObject(new Map())).toBe(false)
406 expect(isEmptyObject(new Set())).toBe(false)
407 expect(isEmptyObject(new WeakMap())).toBe(false)
408 expect(isEmptyObject(new WeakSet())).toBe(false)
411 await it('Verify isArraySorted()', () => {
413 isArraySorted([], (a
, b
) => {
418 isArraySorted([1], (a
, b
) => {
422 expect(isArraySorted
<number>([1, 2, 3, 4, 5], (a
, b
) => a
- b
)).toBe(true)
423 expect(isArraySorted
<number>([1, 2, 3, 5, 4], (a
, b
) => a
- b
)).toBe(false)
424 expect(isArraySorted
<number>([2, 1, 3, 4, 5], (a
, b
) => a
- b
)).toBe(false)
427 await it('Verify once()', () => {
429 const fn
= (): number => ++called
430 const onceFn
= once(fn
, this)
431 const result1
= onceFn()
432 expect(called
).toBe(1)
433 expect(result1
).toBe(1)
434 const result2
= onceFn()
435 expect(called
).toBe(1)
436 expect(result2
).toBe(1)
437 const result3
= onceFn()
438 expect(called
).toBe(1)
439 expect(result3
).toBe(1)
442 await it('Verify min()', () => {
443 expect(min()).toBe(Infinity)
444 expect(min(0, 1)).toBe(0)
445 expect(min(1, 0)).toBe(0)
446 expect(min(0, -1)).toBe(-1)
447 expect(min(-1, 0)).toBe(-1)
450 await it('Verify max()', () => {
451 expect(max()).toBe(-Infinity)
452 expect(max(0, 1)).toBe(1)
453 expect(max(1, 0)).toBe(1)
454 expect(max(0, -1)).toBe(0)
455 expect(max(-1, 0)).toBe(0)