@adaptivestone/framework 4.6.0 → 4.8.0

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.
Files changed (90) hide show
  1. package/CHANGELOG.md +14 -1
  2. package/Cli.js +1 -0
  3. package/cluster.js +1 -2
  4. package/commands/GetOpenApiJson.js +1 -2
  5. package/commands/SyncIndexes.js +1 -1
  6. package/commands/migration/Migrate.js +2 -2
  7. package/controllers/Auth.js +3 -5
  8. package/controllers/index.js +0 -3
  9. package/coverage/clover.xml +2035 -1926
  10. package/coverage/coverage-final.json +43 -40
  11. package/coverage/framework/config/auth.js.html +6 -6
  12. package/coverage/framework/config/http.js.html +10 -10
  13. package/coverage/framework/config/i18n.js.html +13 -13
  14. package/coverage/framework/config/index.html +1 -1
  15. package/coverage/framework/config/log.js.html +23 -23
  16. package/coverage/framework/config/mail.js.html +30 -30
  17. package/coverage/framework/config/mongo.js.html +4 -4
  18. package/coverage/framework/config/rateLimiter.js.html +17 -17
  19. package/coverage/framework/config/redis.js.html +5 -5
  20. package/coverage/framework/config/validate.js.html +4 -4
  21. package/coverage/framework/controllers/Auth.js.html +97 -103
  22. package/coverage/framework/controllers/Home.js.html +27 -27
  23. package/coverage/framework/controllers/index.html +15 -15
  24. package/coverage/framework/controllers/index.js.html +58 -67
  25. package/coverage/framework/controllers/test/SomeController.js.html +44 -89
  26. package/coverage/framework/controllers/test/index.html +17 -17
  27. package/coverage/framework/helpers/files.js.html +310 -0
  28. package/coverage/framework/helpers/index.html +131 -0
  29. package/coverage/framework/helpers/logger.js.html +142 -0
  30. package/coverage/framework/helpers/redis/clearNamespace.js.html +10 -10
  31. package/coverage/framework/helpers/redis/index.html +1 -1
  32. package/coverage/framework/index.html +19 -19
  33. package/coverage/framework/models/Migration.js.html +130 -0
  34. package/coverage/framework/models/Sequence.js.html +11 -11
  35. package/coverage/framework/models/User.js.html +130 -130
  36. package/coverage/framework/models/index.html +20 -5
  37. package/coverage/framework/modules/AbstractController.js.html +100 -106
  38. package/coverage/framework/modules/AbstractModel.js.html +58 -58
  39. package/coverage/framework/modules/Base.js.html +70 -403
  40. package/coverage/framework/modules/index.html +24 -24
  41. package/coverage/framework/server.js.html +704 -338
  42. package/coverage/framework/services/cache/Cache.js.html +96 -81
  43. package/coverage/framework/services/cache/index.html +19 -19
  44. package/coverage/framework/services/documentation/DocumentationGenerator.js.html +39 -45
  45. package/coverage/framework/services/documentation/index.html +11 -11
  46. package/coverage/framework/services/http/HttpServer.js.html +90 -90
  47. package/coverage/framework/services/http/index.html +1 -1
  48. package/coverage/framework/services/http/middleware/AbstractMiddleware.js.html +45 -45
  49. package/coverage/framework/services/http/middleware/Auth.js.html +19 -19
  50. package/coverage/framework/services/http/middleware/GetUserByToken.js.html +36 -36
  51. package/coverage/framework/services/http/middleware/I18n.js.html +67 -67
  52. package/coverage/framework/services/http/middleware/Pagination.js.html +21 -21
  53. package/coverage/framework/services/http/middleware/PrepareAppInfo.js.html +5 -5
  54. package/coverage/framework/services/http/middleware/RateLimiter.js.html +19 -19
  55. package/coverage/framework/services/http/middleware/RequestLogger.js.html +21 -21
  56. package/coverage/framework/services/http/middleware/RequestParser.js.html +7 -7
  57. package/coverage/framework/services/http/middleware/Role.js.html +43 -43
  58. package/coverage/framework/services/http/middleware/index.html +33 -33
  59. package/coverage/framework/services/http/middleware/test/CheckFlag.js.html +9 -9
  60. package/coverage/framework/services/http/middleware/test/index.html +1 -1
  61. package/coverage/framework/services/messaging/email/index.html +1 -1
  62. package/coverage/framework/services/messaging/email/index.js.html +67 -67
  63. package/coverage/framework/services/messaging/index.html +1 -1
  64. package/coverage/framework/services/messaging/index.js.html +6 -6
  65. package/coverage/framework/services/validate/ValidateService.js.html +155 -167
  66. package/coverage/framework/services/validate/drivers/AbstractValidator.js.html +24 -24
  67. package/coverage/framework/services/validate/drivers/CustomValidator.js.html +14 -14
  68. package/coverage/framework/services/validate/drivers/YupValidator.js.html +41 -41
  69. package/coverage/framework/services/validate/drivers/index.html +1 -1
  70. package/coverage/framework/services/validate/index.html +5 -5
  71. package/coverage/index.html +91 -76
  72. package/helpers/files.js +75 -0
  73. package/helpers/logger.js +19 -0
  74. package/models/Migration.test.js +19 -0
  75. package/modules/AbstractController.js +2 -4
  76. package/modules/Base.js +8 -119
  77. package/modules/BaseCli.js +0 -4
  78. package/package.json +2 -2
  79. package/server.d.ts +14 -1
  80. package/server.js +208 -86
  81. package/services/cache/Cache.js +10 -5
  82. package/services/cache/Cache.test.js +81 -0
  83. package/services/documentation/DocumentationGenerator.js +18 -20
  84. package/services/http/middleware/Auth.test.js +57 -0
  85. package/services/http/middleware/I18n.test.js +15 -3
  86. package/services/http/middleware/PrepareAppInfo.test.js +1 -1
  87. package/services/http/middleware/Role.test.js +93 -0
  88. package/services/validate/ValidateService.js +3 -7
  89. package/tests/setup.js +1 -0
  90. package/tests/setupVitest.js +1 -0
@@ -23,30 +23,30 @@
23
23
  <div class='clearfix'>
24
24
 
25
25
  <div class='fl pad1y space-right2'>
26
- <span class="strong">87.34% </span>
26
+ <span class="strong">86.64% </span>
27
27
  <span class="quiet">Statements</span>
28
- <span class='fraction'>214/245</span>
28
+ <span class='fraction'>318/367</span>
29
29
  </div>
30
30
 
31
31
 
32
32
  <div class='fl pad1y space-right2'>
33
- <span class="strong">80% </span>
33
+ <span class="strong">78.72% </span>
34
34
  <span class="quiet">Branches</span>
35
- <span class='fraction'>16/20</span>
35
+ <span class='fraction'>37/47</span>
36
36
  </div>
37
37
 
38
38
 
39
39
  <div class='fl pad1y space-right2'>
40
- <span class="strong">91.66% </span>
40
+ <span class="strong">90.9% </span>
41
41
  <span class="quiet">Functions</span>
42
- <span class='fraction'>11/12</span>
42
+ <span class='fraction'>20/22</span>
43
43
  </div>
44
44
 
45
45
 
46
46
  <div class='fl pad1y space-right2'>
47
- <span class="strong">87.34% </span>
47
+ <span class="strong">86.64% </span>
48
48
  <span class="quiet">Lines</span>
49
- <span class='fraction'>214/245</span>
49
+ <span class='fraction'>318/367</span>
50
50
  </div>
51
51
 
52
52
 
@@ -308,261 +308,515 @@
308
308
  <a name='L243'></a><a href='#L243'>243</a>
309
309
  <a name='L244'></a><a href='#L244'>244</a>
310
310
  <a name='L245'></a><a href='#L245'>245</a>
311
- <a name='L246'></a><a href='#L246'>246</a></td><td class="line-coverage quiet"><span class="cline-any cline-yes">11x</span>
312
- <span class="cline-any cline-yes">11x</span>
313
- <span class="cline-any cline-yes">11x</span>
314
- <span class="cline-any cline-yes">11x</span>
315
- <span class="cline-any cline-yes">11x</span>
316
- <span class="cline-any cline-yes">11x</span>
317
- <span class="cline-any cline-yes">11x</span>
318
- <span class="cline-any cline-yes">11x</span>
319
- <span class="cline-any cline-yes">11x</span>
320
- <span class="cline-any cline-yes">11x</span>
321
- <span class="cline-any cline-yes">11x</span>
322
- <span class="cline-any cline-yes">11x</span>
323
- <span class="cline-any cline-yes">11x</span>
324
- <span class="cline-any cline-yes">11x</span>
325
- <span class="cline-any cline-yes">11x</span>
326
- <span class="cline-any cline-yes">11x</span>
327
- <span class="cline-any cline-yes">11x</span>
328
- <span class="cline-any cline-yes">11x</span>
329
- <span class="cline-any cline-yes">11x</span>
330
- <span class="cline-any cline-yes">11x</span>
331
- <span class="cline-any cline-yes">11x</span>
332
- <span class="cline-any cline-yes">11x</span>
333
- <span class="cline-any cline-yes">11x</span>
334
- <span class="cline-any cline-yes">11x</span>
335
- <span class="cline-any cline-yes">11x</span>
336
- <span class="cline-any cline-yes">11x</span>
337
- <span class="cline-any cline-yes">11x</span>
338
- <span class="cline-any cline-yes">11x</span>
339
- <span class="cline-any cline-yes">11x</span>
340
- <span class="cline-any cline-yes">11x</span>
341
- <span class="cline-any cline-yes">11x</span>
342
- <span class="cline-any cline-yes">11x</span>
343
- <span class="cline-any cline-yes">11x</span>
344
- <span class="cline-any cline-yes">4x</span>
345
- <span class="cline-any cline-yes">11x</span>
346
- <span class="cline-any cline-yes">11x</span>
347
- <span class="cline-any cline-yes">11x</span>
348
- <span class="cline-any cline-yes">11x</span>
349
- <span class="cline-any cline-yes">11x</span>
350
- <span class="cline-any cline-yes">11x</span>
351
- <span class="cline-any cline-yes">11x</span>
352
- <span class="cline-any cline-yes">11x</span>
353
- <span class="cline-any cline-yes">11x</span>
354
- <span class="cline-any cline-yes">11x</span>
355
- <span class="cline-any cline-yes">11x</span>
356
- <span class="cline-any cline-yes">11x</span>
357
- <span class="cline-any cline-yes">11x</span>
358
- <span class="cline-any cline-yes">11x</span>
359
- <span class="cline-any cline-yes">11x</span>
360
- <span class="cline-any cline-yes">11x</span>
361
- <span class="cline-any cline-yes">11x</span>
362
- <span class="cline-any cline-yes">11x</span>
363
- <span class="cline-any cline-yes">11x</span>
364
- <span class="cline-any cline-yes">11x</span>
365
- <span class="cline-any cline-yes">11x</span>
366
- <span class="cline-any cline-yes">11x</span>
367
- <span class="cline-any cline-yes">11x</span>
368
- <span class="cline-any cline-yes">11x</span>
369
- <span class="cline-any cline-yes">11x</span>
370
- <span class="cline-any cline-yes">11x</span>
371
- <span class="cline-any cline-yes">11x</span>
372
- <span class="cline-any cline-yes">11x</span>
373
- <span class="cline-any cline-yes">11x</span>
374
- <span class="cline-any cline-yes">11x</span>
375
- <span class="cline-any cline-yes">11x</span>
376
- <span class="cline-any cline-yes">11x</span>
377
- <span class="cline-any cline-yes">11x</span>
378
- <span class="cline-any cline-yes">11x</span>
379
- <span class="cline-any cline-yes">11x</span>
380
- <span class="cline-any cline-yes">11x</span>
381
- <span class="cline-any cline-yes">11x</span>
382
- <span class="cline-any cline-yes">11x</span>
383
- <span class="cline-any cline-yes">11x</span>
384
- <span class="cline-any cline-yes">11x</span>
385
- <span class="cline-any cline-yes">11x</span>
386
- <span class="cline-any cline-yes">11x</span>
387
- <span class="cline-any cline-yes">11x</span>
388
- <span class="cline-any cline-yes">11x</span>
389
- <span class="cline-any cline-yes">11x</span>
390
- <span class="cline-any cline-yes">11x</span>
391
- <span class="cline-any cline-yes">11x</span>
392
- <span class="cline-any cline-yes">11x</span>
393
- <span class="cline-any cline-yes">11x</span>
394
- <span class="cline-any cline-yes">11x</span>
395
- <span class="cline-any cline-yes">11x</span>
396
- <span class="cline-any cline-no">&nbsp;</span>
397
- <span class="cline-any cline-no">&nbsp;</span>
398
- <span class="cline-any cline-no">&nbsp;</span>
399
- <span class="cline-any cline-no">&nbsp;</span>
400
- <span class="cline-any cline-no">&nbsp;</span>
401
- <span class="cline-any cline-no">&nbsp;</span>
402
- <span class="cline-any cline-no">&nbsp;</span>
403
- <span class="cline-any cline-yes">11x</span>
404
- <span class="cline-any cline-yes">11x</span>
405
- <span class="cline-any cline-yes">11x</span>
406
- <span class="cline-any cline-yes">11x</span>
407
- <span class="cline-any cline-yes">11x</span>
408
- <span class="cline-any cline-yes">11x</span>
409
- <span class="cline-any cline-yes">11x</span>
410
- <span class="cline-any cline-yes">11x</span>
411
- <span class="cline-any cline-yes">11x</span>
412
- <span class="cline-any cline-yes">11x</span>
413
- <span class="cline-any cline-yes">11x</span>
414
- <span class="cline-any cline-yes">11x</span>
415
- <span class="cline-any cline-yes">11x</span>
416
- <span class="cline-any cline-yes">11x</span>
417
- <span class="cline-any cline-yes">725x</span>
418
- <span class="cline-any cline-yes">725x</span>
419
- <span class="cline-any cline-yes">91x</span>
420
- <span class="cline-any cline-yes">91x</span>
421
- <span class="cline-any cline-yes">91x</span>
422
- <span class="cline-any cline-yes">91x</span>
423
- <span class="cline-any cline-yes">91x</span>
424
- <span class="cline-any cline-yes">91x</span>
425
- <span class="cline-any cline-yes">91x</span>
426
- <span class="cline-any cline-yes">91x</span>
427
- <span class="cline-any cline-yes">91x</span>
428
- <span class="cline-any cline-yes">91x</span>
429
- <span class="cline-any cline-yes">91x</span>
430
- <span class="cline-any cline-yes">91x</span>
431
- <span class="cline-any cline-yes">91x</span>
432
- <span class="cline-any cline-yes">91x</span>
433
- <span class="cline-any cline-yes">91x</span>
434
- <span class="cline-any cline-yes">91x</span>
435
- <span class="cline-any cline-yes">91x</span>
436
- <span class="cline-any cline-yes">725x</span>
437
- <span class="cline-any cline-yes">725x</span>
438
- <span class="cline-any cline-yes">11x</span>
439
- <span class="cline-any cline-yes">11x</span>
440
- <span class="cline-any cline-yes">11x</span>
441
- <span class="cline-any cline-yes">11x</span>
442
- <span class="cline-any cline-yes">11x</span>
443
- <span class="cline-any cline-yes">11x</span>
444
- <span class="cline-any cline-yes">11x</span>
445
- <span class="cline-any cline-yes">11x</span>
446
- <span class="cline-any cline-yes">11x</span>
447
- <span class="cline-any cline-yes">124x</span>
448
- <span class="cline-any cline-yes">124x</span>
449
- <span class="cline-any cline-yes">124x</span>
450
- <span class="cline-any cline-yes">124x</span>
451
- <span class="cline-any cline-yes">124x</span>
452
- <span class="cline-any cline-yes">124x</span>
453
- <span class="cline-any cline-yes">11x</span>
454
- <span class="cline-any cline-yes">11x</span>
455
- <span class="cline-any cline-yes">11x</span>
456
- <span class="cline-any cline-yes">11x</span>
457
- <span class="cline-any cline-yes">11x</span>
458
- <span class="cline-any cline-yes">11x</span>
459
- <span class="cline-any cline-yes">11x</span>
460
- <span class="cline-any cline-yes">11x</span>
461
- <span class="cline-any cline-yes">61x</span>
462
- <span class="cline-any cline-no">&nbsp;</span>
463
- <span class="cline-any cline-no">&nbsp;</span>
464
- <span class="cline-any cline-no">&nbsp;</span>
465
- <span class="cline-any cline-no">&nbsp;</span>
466
- <span class="cline-any cline-yes">61x</span>
467
- <span class="cline-any cline-yes">12x</span>
468
- <span class="cline-any cline-yes">12x</span>
469
- <span class="cline-any cline-no">&nbsp;</span>
470
- <span class="cline-any cline-no">&nbsp;</span>
471
- <span class="cline-any cline-no">&nbsp;</span>
472
- <span class="cline-any cline-yes">12x</span>
473
- <span class="cline-any cline-yes">12x</span>
474
- <span class="cline-any cline-yes">12x</span>
475
- <span class="cline-any cline-yes">12x</span>
476
- <span class="cline-any cline-yes">12x</span>
477
- <span class="cline-any cline-no">&nbsp;</span>
478
- <span class="cline-any cline-no">&nbsp;</span>
479
- <span class="cline-any cline-no">&nbsp;</span>
480
- <span class="cline-any cline-yes">12x</span>
481
- <span class="cline-any cline-yes">61x</span>
482
- <span class="cline-any cline-yes">61x</span>
483
- <span class="cline-any cline-yes">11x</span>
484
- <span class="cline-any cline-yes">11x</span>
485
- <span class="cline-any cline-yes">11x</span>
486
- <span class="cline-any cline-yes">11x</span>
487
- <span class="cline-any cline-yes">11x</span>
488
- <span class="cline-any cline-yes">11x</span>
489
- <span class="cline-any cline-yes">11x</span>
490
- <span class="cline-any cline-no">&nbsp;</span>
491
- <span class="cline-any cline-no">&nbsp;</span>
492
- <span class="cline-any cline-no">&nbsp;</span>
493
- <span class="cline-any cline-no">&nbsp;</span>
494
- <span class="cline-any cline-no">&nbsp;</span>
495
- <span class="cline-any cline-no">&nbsp;</span>
311
+ <a name='L246'></a><a href='#L246'>246</a>
312
+ <a name='L247'></a><a href='#L247'>247</a>
313
+ <a name='L248'></a><a href='#L248'>248</a>
314
+ <a name='L249'></a><a href='#L249'>249</a>
315
+ <a name='L250'></a><a href='#L250'>250</a>
316
+ <a name='L251'></a><a href='#L251'>251</a>
317
+ <a name='L252'></a><a href='#L252'>252</a>
318
+ <a name='L253'></a><a href='#L253'>253</a>
319
+ <a name='L254'></a><a href='#L254'>254</a>
320
+ <a name='L255'></a><a href='#L255'>255</a>
321
+ <a name='L256'></a><a href='#L256'>256</a>
322
+ <a name='L257'></a><a href='#L257'>257</a>
323
+ <a name='L258'></a><a href='#L258'>258</a>
324
+ <a name='L259'></a><a href='#L259'>259</a>
325
+ <a name='L260'></a><a href='#L260'>260</a>
326
+ <a name='L261'></a><a href='#L261'>261</a>
327
+ <a name='L262'></a><a href='#L262'>262</a>
328
+ <a name='L263'></a><a href='#L263'>263</a>
329
+ <a name='L264'></a><a href='#L264'>264</a>
330
+ <a name='L265'></a><a href='#L265'>265</a>
331
+ <a name='L266'></a><a href='#L266'>266</a>
332
+ <a name='L267'></a><a href='#L267'>267</a>
333
+ <a name='L268'></a><a href='#L268'>268</a>
334
+ <a name='L269'></a><a href='#L269'>269</a>
335
+ <a name='L270'></a><a href='#L270'>270</a>
336
+ <a name='L271'></a><a href='#L271'>271</a>
337
+ <a name='L272'></a><a href='#L272'>272</a>
338
+ <a name='L273'></a><a href='#L273'>273</a>
339
+ <a name='L274'></a><a href='#L274'>274</a>
340
+ <a name='L275'></a><a href='#L275'>275</a>
341
+ <a name='L276'></a><a href='#L276'>276</a>
342
+ <a name='L277'></a><a href='#L277'>277</a>
343
+ <a name='L278'></a><a href='#L278'>278</a>
344
+ <a name='L279'></a><a href='#L279'>279</a>
345
+ <a name='L280'></a><a href='#L280'>280</a>
346
+ <a name='L281'></a><a href='#L281'>281</a>
347
+ <a name='L282'></a><a href='#L282'>282</a>
348
+ <a name='L283'></a><a href='#L283'>283</a>
349
+ <a name='L284'></a><a href='#L284'>284</a>
350
+ <a name='L285'></a><a href='#L285'>285</a>
351
+ <a name='L286'></a><a href='#L286'>286</a>
352
+ <a name='L287'></a><a href='#L287'>287</a>
353
+ <a name='L288'></a><a href='#L288'>288</a>
354
+ <a name='L289'></a><a href='#L289'>289</a>
355
+ <a name='L290'></a><a href='#L290'>290</a>
356
+ <a name='L291'></a><a href='#L291'>291</a>
357
+ <a name='L292'></a><a href='#L292'>292</a>
358
+ <a name='L293'></a><a href='#L293'>293</a>
359
+ <a name='L294'></a><a href='#L294'>294</a>
360
+ <a name='L295'></a><a href='#L295'>295</a>
361
+ <a name='L296'></a><a href='#L296'>296</a>
362
+ <a name='L297'></a><a href='#L297'>297</a>
363
+ <a name='L298'></a><a href='#L298'>298</a>
364
+ <a name='L299'></a><a href='#L299'>299</a>
365
+ <a name='L300'></a><a href='#L300'>300</a>
366
+ <a name='L301'></a><a href='#L301'>301</a>
367
+ <a name='L302'></a><a href='#L302'>302</a>
368
+ <a name='L303'></a><a href='#L303'>303</a>
369
+ <a name='L304'></a><a href='#L304'>304</a>
370
+ <a name='L305'></a><a href='#L305'>305</a>
371
+ <a name='L306'></a><a href='#L306'>306</a>
372
+ <a name='L307'></a><a href='#L307'>307</a>
373
+ <a name='L308'></a><a href='#L308'>308</a>
374
+ <a name='L309'></a><a href='#L309'>309</a>
375
+ <a name='L310'></a><a href='#L310'>310</a>
376
+ <a name='L311'></a><a href='#L311'>311</a>
377
+ <a name='L312'></a><a href='#L312'>312</a>
378
+ <a name='L313'></a><a href='#L313'>313</a>
379
+ <a name='L314'></a><a href='#L314'>314</a>
380
+ <a name='L315'></a><a href='#L315'>315</a>
381
+ <a name='L316'></a><a href='#L316'>316</a>
382
+ <a name='L317'></a><a href='#L317'>317</a>
383
+ <a name='L318'></a><a href='#L318'>318</a>
384
+ <a name='L319'></a><a href='#L319'>319</a>
385
+ <a name='L320'></a><a href='#L320'>320</a>
386
+ <a name='L321'></a><a href='#L321'>321</a>
387
+ <a name='L322'></a><a href='#L322'>322</a>
388
+ <a name='L323'></a><a href='#L323'>323</a>
389
+ <a name='L324'></a><a href='#L324'>324</a>
390
+ <a name='L325'></a><a href='#L325'>325</a>
391
+ <a name='L326'></a><a href='#L326'>326</a>
392
+ <a name='L327'></a><a href='#L327'>327</a>
393
+ <a name='L328'></a><a href='#L328'>328</a>
394
+ <a name='L329'></a><a href='#L329'>329</a>
395
+ <a name='L330'></a><a href='#L330'>330</a>
396
+ <a name='L331'></a><a href='#L331'>331</a>
397
+ <a name='L332'></a><a href='#L332'>332</a>
398
+ <a name='L333'></a><a href='#L333'>333</a>
399
+ <a name='L334'></a><a href='#L334'>334</a>
400
+ <a name='L335'></a><a href='#L335'>335</a>
401
+ <a name='L336'></a><a href='#L336'>336</a>
402
+ <a name='L337'></a><a href='#L337'>337</a>
403
+ <a name='L338'></a><a href='#L338'>338</a>
404
+ <a name='L339'></a><a href='#L339'>339</a>
405
+ <a name='L340'></a><a href='#L340'>340</a>
406
+ <a name='L341'></a><a href='#L341'>341</a>
407
+ <a name='L342'></a><a href='#L342'>342</a>
408
+ <a name='L343'></a><a href='#L343'>343</a>
409
+ <a name='L344'></a><a href='#L344'>344</a>
410
+ <a name='L345'></a><a href='#L345'>345</a>
411
+ <a name='L346'></a><a href='#L346'>346</a>
412
+ <a name='L347'></a><a href='#L347'>347</a>
413
+ <a name='L348'></a><a href='#L348'>348</a>
414
+ <a name='L349'></a><a href='#L349'>349</a>
415
+ <a name='L350'></a><a href='#L350'>350</a>
416
+ <a name='L351'></a><a href='#L351'>351</a>
417
+ <a name='L352'></a><a href='#L352'>352</a>
418
+ <a name='L353'></a><a href='#L353'>353</a>
419
+ <a name='L354'></a><a href='#L354'>354</a>
420
+ <a name='L355'></a><a href='#L355'>355</a>
421
+ <a name='L356'></a><a href='#L356'>356</a>
422
+ <a name='L357'></a><a href='#L357'>357</a>
423
+ <a name='L358'></a><a href='#L358'>358</a>
424
+ <a name='L359'></a><a href='#L359'>359</a>
425
+ <a name='L360'></a><a href='#L360'>360</a>
426
+ <a name='L361'></a><a href='#L361'>361</a>
427
+ <a name='L362'></a><a href='#L362'>362</a>
428
+ <a name='L363'></a><a href='#L363'>363</a>
429
+ <a name='L364'></a><a href='#L364'>364</a>
430
+ <a name='L365'></a><a href='#L365'>365</a>
431
+ <a name='L366'></a><a href='#L366'>366</a>
432
+ <a name='L367'></a><a href='#L367'>367</a>
433
+ <a name='L368'></a><a href='#L368'>368</a></td><td class="line-coverage quiet"><span class="cline-any cline-yes">15x</span>
434
+ <span class="cline-any cline-yes">15x</span>
435
+ <span class="cline-any cline-yes">15x</span>
436
+ <span class="cline-any cline-yes">15x</span>
437
+ <span class="cline-any cline-yes">15x</span>
438
+ <span class="cline-any cline-yes">15x</span>
439
+ <span class="cline-any cline-yes">15x</span>
440
+ <span class="cline-any cline-yes">15x</span>
441
+ <span class="cline-any cline-yes">15x</span>
442
+ <span class="cline-any cline-yes">15x</span>
443
+ <span class="cline-any cline-yes">15x</span>
444
+ <span class="cline-any cline-yes">15x</span>
445
+ <span class="cline-any cline-yes">15x</span>
446
+ <span class="cline-any cline-yes">15x</span>
447
+ <span class="cline-any cline-yes">15x</span>
448
+ <span class="cline-any cline-yes">15x</span>
449
+ <span class="cline-any cline-yes">15x</span>
450
+ <span class="cline-any cline-yes">15x</span>
451
+ <span class="cline-any cline-yes">15x</span>
452
+ <span class="cline-any cline-yes">15x</span>
453
+ <span class="cline-any cline-yes">15x</span>
454
+ <span class="cline-any cline-yes">15x</span>
455
+ <span class="cline-any cline-yes">15x</span>
456
+ <span class="cline-any cline-yes">15x</span>
457
+ <span class="cline-any cline-yes">15x</span>
458
+ <span class="cline-any cline-yes">15x</span>
459
+ <span class="cline-any cline-yes">15x</span>
460
+ <span class="cline-any cline-yes">15x</span>
461
+ <span class="cline-any cline-yes">15x</span>
462
+ <span class="cline-any cline-yes">15x</span>
463
+ <span class="cline-any cline-yes">15x</span>
464
+ <span class="cline-any cline-yes">15x</span>
465
+ <span class="cline-any cline-yes">15x</span>
466
+ <span class="cline-any cline-yes">15x</span>
467
+ <span class="cline-any cline-yes">15x</span>
468
+ <span class="cline-any cline-yes">15x</span>
469
+ <span class="cline-any cline-yes">15x</span>
470
+ <span class="cline-any cline-yes">15x</span>
471
+ <span class="cline-any cline-yes">15x</span>
472
+ <span class="cline-any cline-yes">15x</span>
473
+ <span class="cline-any cline-yes">15x</span>
474
+ <span class="cline-any cline-yes">15x</span>
475
+ <span class="cline-any cline-yes">15x</span>
476
+ <span class="cline-any cline-yes">5x</span>
477
+ <span class="cline-any cline-yes">15x</span>
478
+ <span class="cline-any cline-yes">15x</span>
479
+ <span class="cline-any cline-yes">142x</span>
480
+ <span class="cline-any cline-yes">15x</span>
481
+ <span class="cline-any cline-yes">15x</span>
482
+ <span class="cline-any cline-yes">15x</span>
483
+ <span class="cline-any cline-yes">15x</span>
484
+ <span class="cline-any cline-yes">15x</span>
485
+ <span class="cline-any cline-yes">15x</span>
486
+ <span class="cline-any cline-yes">15x</span>
487
+ <span class="cline-any cline-yes">15x</span>
488
+ <span class="cline-any cline-yes">15x</span>
489
+ <span class="cline-any cline-yes">15x</span>
490
+ <span class="cline-any cline-yes">15x</span>
491
+ <span class="cline-any cline-yes">15x</span>
492
+ <span class="cline-any cline-yes">15x</span>
493
+ <span class="cline-any cline-yes">15x</span>
494
+ <span class="cline-any cline-yes">15x</span>
495
+ <span class="cline-any cline-yes">15x</span>
496
+ <span class="cline-any cline-yes">15x</span>
497
+ <span class="cline-any cline-yes">15x</span>
498
+ <span class="cline-any cline-yes">15x</span>
499
+ <span class="cline-any cline-yes">15x</span>
500
+ <span class="cline-any cline-yes">15x</span>
501
+ <span class="cline-any cline-yes">15x</span>
502
+ <span class="cline-any cline-yes">15x</span>
503
+ <span class="cline-any cline-yes">15x</span>
504
+ <span class="cline-any cline-yes">15x</span>
505
+ <span class="cline-any cline-yes">15x</span>
506
+ <span class="cline-any cline-yes">15x</span>
507
+ <span class="cline-any cline-yes">15x</span>
508
+ <span class="cline-any cline-yes">15x</span>
509
+ <span class="cline-any cline-yes">15x</span>
510
+ <span class="cline-any cline-yes">15x</span>
511
+ <span class="cline-any cline-yes">15x</span>
512
+ <span class="cline-any cline-yes">15x</span>
513
+ <span class="cline-any cline-yes">15x</span>
514
+ <span class="cline-any cline-yes">15x</span>
515
+ <span class="cline-any cline-yes">15x</span>
516
+ <span class="cline-any cline-yes">15x</span>
517
+ <span class="cline-any cline-yes">15x</span>
518
+ <span class="cline-any cline-yes">15x</span>
519
+ <span class="cline-any cline-yes">15x</span>
520
+ <span class="cline-any cline-yes">15x</span>
521
+ <span class="cline-any cline-yes">15x</span>
522
+ <span class="cline-any cline-yes">15x</span>
523
+ <span class="cline-any cline-yes">15x</span>
524
+ <span class="cline-any cline-yes">30x</span>
525
+ <span class="cline-any cline-yes">15x</span>
526
+ <span class="cline-any cline-yes">15x</span>
527
+ <span class="cline-any cline-yes">15x</span>
528
+ <span class="cline-any cline-yes">15x</span>
529
+ <span class="cline-any cline-yes">15x</span>
530
+ <span class="cline-any cline-yes">15x</span>
531
+ <span class="cline-any cline-yes">15x</span>
532
+ <span class="cline-any cline-yes">15x</span>
533
+ <span class="cline-any cline-yes">15x</span>
534
+ <span class="cline-any cline-yes">15x</span>
535
+ <span class="cline-any cline-yes">15x</span>
536
+ <span class="cline-any cline-yes">30x</span>
537
+ <span class="cline-any cline-yes">15x</span>
538
+ <span class="cline-any cline-yes">15x</span>
539
+ <span class="cline-any cline-yes">15x</span>
540
+ <span class="cline-any cline-yes">15x</span>
541
+ <span class="cline-any cline-yes">15x</span>
542
+ <span class="cline-any cline-yes">15x</span>
543
+ <span class="cline-any cline-yes">15x</span>
544
+ <span class="cline-any cline-yes">15x</span>
545
+ <span class="cline-any cline-yes">15x</span>
546
+ <span class="cline-any cline-yes">15x</span>
547
+ <span class="cline-any cline-yes">15x</span>
548
+ <span class="cline-any cline-yes">15x</span>
549
+ <span class="cline-any cline-yes">15x</span>
550
+ <span class="cline-any cline-yes">15x</span>
551
+ <span class="cline-any cline-yes">15x</span>
552
+ <span class="cline-any cline-yes">135x</span>
553
+ <span class="cline-any cline-yes">135x</span>
554
+ <span class="cline-any cline-yes">135x</span>
555
+ <span class="cline-any cline-yes">135x</span>
556
+ <span class="cline-any cline-yes">135x</span>
557
+ <span class="cline-any cline-yes">135x</span>
558
+ <span class="cline-any cline-yes">135x</span>
496
559
  <span class="cline-any cline-no">&nbsp;</span>
497
- <span class="cline-any cline-no">&nbsp;</span>
498
- <span class="cline-any cline-no">&nbsp;</span>
499
- <span class="cline-any cline-no">&nbsp;</span>
500
- <span class="cline-any cline-yes">11x</span>
501
- <span class="cline-any cline-yes">11x</span>
502
- <span class="cline-any cline-yes">11x</span>
503
- <span class="cline-any cline-yes">11x</span>
504
- <span class="cline-any cline-yes">11x</span>
505
- <span class="cline-any cline-yes">11x</span>
506
- <span class="cline-any cline-yes">4x</span>
507
- <span class="cline-any cline-yes">1x</span>
560
+ <span class="cline-any cline-no">&nbsp;</span>
561
+ <span class="cline-any cline-yes">135x</span>
562
+ <span class="cline-any cline-yes">15x</span>
563
+ <span class="cline-any cline-yes">15x</span>
564
+ <span class="cline-any cline-yes">135x</span>
565
+ <span class="cline-any cline-yes">135x</span>
566
+ <span class="cline-any cline-no">&nbsp;</span>
567
+ <span class="cline-any cline-no">&nbsp;</span>
568
+ <span class="cline-any cline-yes">135x</span>
569
+ <span class="cline-any cline-yes">135x</span>
570
+ <span class="cline-any cline-yes">135x</span>
571
+ <span class="cline-any cline-yes">135x</span>
572
+ <span class="cline-any cline-yes">135x</span>
573
+ <span class="cline-any cline-yes">135x</span>
574
+ <span class="cline-any cline-yes">135x</span>
575
+ <span class="cline-any cline-yes">15x</span>
576
+ <span class="cline-any cline-yes">15x</span>
577
+ <span class="cline-any cline-yes">15x</span>
578
+ <span class="cline-any cline-yes">15x</span>
579
+ <span class="cline-any cline-yes">15x</span>
580
+ <span class="cline-any cline-yes">135x</span>
581
+ <span class="cline-any cline-yes">135x</span>
582
+ <span class="cline-any cline-yes">15x</span>
583
+ <span class="cline-any cline-yes">15x</span>
584
+ <span class="cline-any cline-yes">15x</span>
585
+ <span class="cline-any cline-yes">15x</span>
586
+ <span class="cline-any cline-yes">135x</span>
587
+ <span class="cline-any cline-yes">135x</span>
588
+ <span class="cline-any cline-yes">15x</span>
589
+ <span class="cline-any cline-yes">15x</span>
590
+ <span class="cline-any cline-yes">15x</span>
591
+ <span class="cline-any cline-yes">15x</span>
592
+ <span class="cline-any cline-yes">15x</span>
593
+ <span class="cline-any cline-yes">15x</span>
594
+ <span class="cline-any cline-yes">15x</span>
595
+ <span class="cline-any cline-yes">15x</span>
596
+ <span class="cline-any cline-yes">15x</span>
597
+ <span class="cline-any cline-yes">15x</span>
598
+ <span class="cline-any cline-yes">15x</span>
599
+ <span class="cline-any cline-yes">15x</span>
600
+ <span class="cline-any cline-yes">15x</span>
601
+ <span class="cline-any cline-yes">45x</span>
602
+ <span class="cline-any cline-yes">45x</span>
603
+ <span class="cline-any cline-yes">45x</span>
604
+ <span class="cline-any cline-yes">45x</span>
605
+ <span class="cline-any cline-yes">45x</span>
606
+ <span class="cline-any cline-yes">45x</span>
607
+ <span class="cline-any cline-yes">45x</span>
608
+ <span class="cline-any cline-yes">45x</span>
609
+ <span class="cline-any cline-yes">45x</span>
610
+ <span class="cline-any cline-yes">15x</span>
611
+ <span class="cline-any cline-yes">15x</span>
612
+ <span class="cline-any cline-yes">15x</span>
613
+ <span class="cline-any cline-yes">15x</span>
614
+ <span class="cline-any cline-yes">45x</span>
615
+ <span class="cline-any cline-yes">45x</span>
616
+ <span class="cline-any cline-yes">15x</span>
617
+ <span class="cline-any cline-yes">15x</span>
618
+ <span class="cline-any cline-yes">15x</span>
619
+ <span class="cline-any cline-yes">15x</span>
620
+ <span class="cline-any cline-yes">15x</span>
621
+ <span class="cline-any cline-yes">15x</span>
622
+ <span class="cline-any cline-yes">15x</span>
623
+ <span class="cline-any cline-yes">15x</span>
624
+ <span class="cline-any cline-yes">15x</span>
625
+ <span class="cline-any cline-yes">15x</span>
626
+ <span class="cline-any cline-yes">15x</span>
508
627
  <span class="cline-any cline-yes">1x</span>
628
+ <span class="cline-any cline-yes">15x</span>
629
+ <span class="cline-any cline-yes">15x</span>
630
+ <span class="cline-any cline-yes">15x</span>
631
+ <span class="cline-any cline-yes">15x</span>
632
+ <span class="cline-any cline-yes">15x</span>
633
+ <span class="cline-any cline-yes">15x</span>
634
+ <span class="cline-any cline-yes">15x</span>
635
+ <span class="cline-any cline-yes">15x</span>
636
+ <span class="cline-any cline-yes">15x</span>
637
+ <span class="cline-any cline-yes">15x</span>
638
+ <span class="cline-any cline-yes">15x</span>
639
+ <span class="cline-any cline-yes">15x</span>
640
+ <span class="cline-any cline-yes">15x</span>
641
+ <span class="cline-any cline-yes">15x</span>
642
+ <span class="cline-any cline-yes">771x</span>
643
+ <span class="cline-any cline-no">&nbsp;</span>
644
+ <span class="cline-any cline-no">&nbsp;</span>
645
+ <span class="cline-any cline-yes">771x</span>
646
+ <span class="cline-any cline-yes">771x</span>
647
+ <span class="cline-any cline-no">&nbsp;</span>
648
+ <span class="cline-any cline-no">&nbsp;</span>
649
+ <span class="cline-any cline-no">&nbsp;</span>
650
+ <span class="cline-any cline-no">&nbsp;</span>
651
+ <span class="cline-any cline-no">&nbsp;</span>
652
+ <span class="cline-any cline-yes">771x</span>
653
+ <span class="cline-any cline-yes">771x</span>
654
+ <span class="cline-any cline-yes">15x</span>
655
+ <span class="cline-any cline-yes">15x</span>
656
+ <span class="cline-any cline-yes">15x</span>
657
+ <span class="cline-any cline-yes">15x</span>
658
+ <span class="cline-any cline-yes">15x</span>
659
+ <span class="cline-any cline-yes">142x</span>
660
+ <span class="cline-any cline-yes">15x</span>
661
+ <span class="cline-any cline-yes">15x</span>
662
+ <span class="cline-any cline-yes">142x</span>
663
+ <span class="cline-any cline-yes">142x</span>
664
+ <span class="cline-any cline-yes">15x</span>
665
+ <span class="cline-any cline-yes">15x</span>
666
+ <span class="cline-any cline-yes">15x</span>
667
+ <span class="cline-any cline-yes">15x</span>
668
+ <span class="cline-any cline-yes">15x</span>
669
+ <span class="cline-any cline-yes">15x</span>
670
+ <span class="cline-any cline-yes">15x</span>
671
+ <span class="cline-any cline-yes">15x</span>
672
+ <span class="cline-any cline-yes">15x</span>
673
+ <span class="cline-any cline-yes">8x</span>
674
+ <span class="cline-any cline-yes">8x</span>
675
+ <span class="cline-any cline-yes">8x</span>
676
+ <span class="cline-any cline-yes">8x</span>
677
+ <span class="cline-any cline-yes">15x</span>
678
+ <span class="cline-any cline-yes">15x</span>
679
+ <span class="cline-any cline-yes">15x</span>
680
+ <span class="cline-any cline-yes">15x</span>
681
+ <span class="cline-any cline-yes">15x</span>
682
+ <span class="cline-any cline-no">&nbsp;</span>
683
+ <span class="cline-any cline-no">&nbsp;</span>
684
+ <span class="cline-any cline-no">&nbsp;</span>
685
+ <span class="cline-any cline-no">&nbsp;</span>
686
+ <span class="cline-any cline-no">&nbsp;</span>
687
+ <span class="cline-any cline-no">&nbsp;</span>
688
+ <span class="cline-any cline-no">&nbsp;</span>
689
+ <span class="cline-any cline-yes">15x</span>
690
+ <span class="cline-any cline-yes">15x</span>
691
+ <span class="cline-any cline-yes">15x</span>
692
+ <span class="cline-any cline-yes">15x</span>
693
+ <span class="cline-any cline-yes">15x</span>
694
+ <span class="cline-any cline-yes">15x</span>
695
+ <span class="cline-any cline-yes">15x</span>
696
+ <span class="cline-any cline-yes">30x</span>
697
+ <span class="cline-any cline-yes">15x</span>
698
+ <span class="cline-any cline-yes">15x</span>
699
+ <span class="cline-any cline-yes">15x</span>
700
+ <span class="cline-any cline-yes">15x</span>
701
+ <span class="cline-any cline-yes">15x</span>
702
+ <span class="cline-any cline-yes">15x</span>
703
+ <span class="cline-any cline-yes">15x</span>
704
+ <span class="cline-any cline-yes">15x</span>
705
+ <span class="cline-any cline-yes">15x</span>
706
+ <span class="cline-any cline-yes">15x</span>
707
+ <span class="cline-any cline-yes">15x</span>
708
+ <span class="cline-any cline-no">&nbsp;</span>
709
+ <span class="cline-any cline-no">&nbsp;</span>
710
+ <span class="cline-any cline-no">&nbsp;</span>
711
+ <span class="cline-any cline-no">&nbsp;</span>
712
+ <span class="cline-any cline-no">&nbsp;</span>
713
+ <span class="cline-any cline-no">&nbsp;</span>
714
+ <span class="cline-any cline-no">&nbsp;</span>
715
+ <span class="cline-any cline-no">&nbsp;</span>
716
+ <span class="cline-any cline-no">&nbsp;</span>
717
+ <span class="cline-any cline-no">&nbsp;</span>
718
+ <span class="cline-any cline-no">&nbsp;</span>
719
+ <span class="cline-any cline-no">&nbsp;</span>
720
+ <span class="cline-any cline-no">&nbsp;</span>
721
+ <span class="cline-any cline-no">&nbsp;</span>
722
+ <span class="cline-any cline-no">&nbsp;</span>
723
+ <span class="cline-any cline-yes">15x</span>
724
+ <span class="cline-any cline-yes">30x</span>
725
+ <span class="cline-any cline-yes">15x</span>
726
+ <span class="cline-any cline-yes">15x</span>
727
+ <span class="cline-any cline-yes">15x</span>
728
+ <span class="cline-any cline-yes">15x</span>
729
+ <span class="cline-any cline-yes">15x</span>
730
+ <span class="cline-any cline-yes">15x</span>
731
+ <span class="cline-any cline-yes">15x</span>
732
+ <span class="cline-any cline-yes">15x</span>
733
+ <span class="cline-any cline-yes">15x</span>
734
+ <span class="cline-any cline-yes">15x</span>
735
+ <span class="cline-any cline-yes">15x</span>
736
+ <span class="cline-any cline-yes">15x</span>
737
+ <span class="cline-any cline-yes">152x</span>
738
+ <span class="cline-any cline-yes">152x</span>
739
+ <span class="cline-any cline-yes">152x</span>
740
+ <span class="cline-any cline-yes">152x</span>
741
+ <span class="cline-any cline-yes">152x</span>
742
+ <span class="cline-any cline-yes">152x</span>
743
+ <span class="cline-any cline-yes">15x</span>
744
+ <span class="cline-any cline-yes">15x</span>
745
+ <span class="cline-any cline-yes">15x</span>
746
+ <span class="cline-any cline-yes">15x</span>
747
+ <span class="cline-any cline-yes">15x</span>
748
+ <span class="cline-any cline-yes">15x</span>
749
+ <span class="cline-any cline-yes">15x</span>
750
+ <span class="cline-any cline-yes">15x</span>
751
+ <span class="cline-any cline-yes">66x</span>
752
+ <span class="cline-any cline-no">&nbsp;</span>
753
+ <span class="cline-any cline-no">&nbsp;</span>
754
+ <span class="cline-any cline-no">&nbsp;</span>
755
+ <span class="cline-any cline-no">&nbsp;</span>
756
+ <span class="cline-any cline-yes">66x</span>
757
+ <span class="cline-any cline-yes">17x</span>
758
+ <span class="cline-any cline-yes">17x</span>
759
+ <span class="cline-any cline-no">&nbsp;</span>
760
+ <span class="cline-any cline-no">&nbsp;</span>
761
+ <span class="cline-any cline-no">&nbsp;</span>
762
+ <span class="cline-any cline-yes">17x</span>
763
+ <span class="cline-any cline-yes">17x</span>
764
+ <span class="cline-any cline-yes">17x</span>
765
+ <span class="cline-any cline-yes">17x</span>
766
+ <span class="cline-any cline-yes">17x</span>
767
+ <span class="cline-any cline-no">&nbsp;</span>
768
+ <span class="cline-any cline-no">&nbsp;</span>
769
+ <span class="cline-any cline-no">&nbsp;</span>
770
+ <span class="cline-any cline-yes">17x</span>
771
+ <span class="cline-any cline-yes">66x</span>
772
+ <span class="cline-any cline-yes">66x</span>
773
+ <span class="cline-any cline-yes">15x</span>
774
+ <span class="cline-any cline-yes">15x</span>
775
+ <span class="cline-any cline-yes">15x</span>
776
+ <span class="cline-any cline-yes">15x</span>
777
+ <span class="cline-any cline-yes">15x</span>
778
+ <span class="cline-any cline-yes">15x</span>
779
+ <span class="cline-any cline-yes">15x</span>
780
+ <span class="cline-any cline-no">&nbsp;</span>
781
+ <span class="cline-any cline-no">&nbsp;</span>
782
+ <span class="cline-any cline-no">&nbsp;</span>
783
+ <span class="cline-any cline-no">&nbsp;</span>
784
+ <span class="cline-any cline-no">&nbsp;</span>
785
+ <span class="cline-any cline-no">&nbsp;</span>
786
+ <span class="cline-any cline-yes">15x</span>
787
+ <span class="cline-any cline-yes">15x</span>
788
+ <span class="cline-any cline-yes">15x</span>
789
+ <span class="cline-any cline-yes">15x</span>
790
+ <span class="cline-any cline-yes">15x</span>
791
+ <span class="cline-any cline-yes">15x</span>
792
+ <span class="cline-any cline-yes">5x</span>
509
793
  <span class="cline-any cline-yes">1x</span>
510
794
  <span class="cline-any cline-yes">1x</span>
511
- <span class="cline-any cline-yes">4x</span>
512
- <span class="cline-any cline-yes">4x</span>
513
- <span class="cline-any cline-yes">11x</span>
514
- <span class="cline-any cline-yes">11x</span>
515
- <span class="cline-any cline-yes">11x</span>
516
- <span class="cline-any cline-yes">11x</span>
517
- <span class="cline-any cline-yes">11x</span>
518
- <span class="cline-any cline-yes">11x</span>
519
- <span class="cline-any cline-yes">11x</span>
520
- <span class="cline-any cline-yes">194x</span>
521
- <span class="cline-any cline-yes">194x</span>
522
- <span class="cline-any cline-yes">194x</span>
523
- <span class="cline-any cline-yes">194x</span>
524
- <span class="cline-any cline-yes">194x</span>
525
- <span class="cline-any cline-yes">91x</span>
526
- <span class="cline-any cline-yes">91x</span>
527
- <span class="cline-any cline-yes">91x</span>
528
- <span class="cline-any cline-yes">91x</span>
529
- <span class="cline-any cline-yes">91x</span>
530
- <span class="cline-any cline-yes">91x</span>
531
- <span class="cline-any cline-yes">91x</span>
532
- <span class="cline-any cline-yes">91x</span>
533
- <span class="cline-any cline-yes">91x</span>
534
- <span class="cline-any cline-yes">91x</span>
535
- <span class="cline-any cline-yes">91x</span>
536
- <span class="cline-any cline-yes">91x</span>
537
- <span class="cline-any cline-yes">91x</span>
538
- <span class="cline-any cline-yes">91x</span>
539
- <span class="cline-any cline-yes">91x</span>
540
- <span class="cline-any cline-yes">91x</span>
541
- <span class="cline-any cline-yes">91x</span>
542
- <span class="cline-any cline-yes">91x</span>
543
- <span class="cline-any cline-no">&nbsp;</span>
544
- <span class="cline-any cline-no">&nbsp;</span>
545
- <span class="cline-any cline-no">&nbsp;</span>
546
- <span class="cline-any cline-no">&nbsp;</span>
547
- <span class="cline-any cline-yes">91x</span>
548
- <span class="cline-any cline-yes">91x</span>
549
- <span class="cline-any cline-yes">91x</span>
550
- <span class="cline-any cline-yes">91x</span>
551
- <span class="cline-any cline-yes">194x</span>
552
- <span class="cline-any cline-yes">194x</span>
553
- <span class="cline-any cline-yes">11x</span>
554
- <span class="cline-any cline-yes">11x</span>
555
- <span class="cline-any cline-yes">11x</span>
795
+ <span class="cline-any cline-yes">5x</span>
796
+ <span class="cline-any cline-yes">5x</span>
797
+ <span class="cline-any cline-yes">15x</span>
798
+ <span class="cline-any cline-yes">15x</span>
799
+ <span class="cline-any cline-yes">15x</span>
556
800
  <span class="cline-any cline-neutral">&nbsp;</span></td><td class="text"><pre class="prettyprint lang-js">/* eslint-disable no-console */
557
801
  const EventEmitter = require('node:events');
802
+ const { hrtime } = require('node:process');
558
803
  &nbsp;
559
804
  require('dotenv').config();
560
805
  const merge = require('deepmerge');
806
+ const winston = require('winston');
807
+ const { getFilesPathWithInheritance } = require('./helpers/files');
808
+ const { consoleLogger } = require('./helpers/logger');
809
+ &nbsp;
810
+ const Cache = require('./services/cache/Cache');
561
811
  &nbsp;
562
812
  /**
563
813
  * Main framework class.
564
814
  */
565
815
  class Server {
816
+ #realLogger = null;
817
+ &nbsp;
818
+ #isInited = false;
819
+ &nbsp;
566
820
  /**
567
821
  * Construct new server
568
822
  * @param {Object} config main config object
@@ -588,6 +842,9 @@ class Server {
588
842
  get cache() {
589
843
  return that.getCache();
590
844
  },
845
+ get logger() {
846
+ return that.getLogger();
847
+ },
591
848
  httpServer: null,
592
849
  controllerManager: null,
593
850
  };
@@ -595,28 +852,23 @@ class Server {
595
852
  this.cache = {
596
853
  configs: new Map(),
597
854
  models: new Map(),
855
+ modelConstructors: new Map(),
598
856
  };
599
857
  &nbsp;
600
858
  this.cli = false;
601
859
  }
602
860
  &nbsp;
603
861
  /**
604
- * Start server (http + websocket + init all http and websocet ralated functions)
862
+ * Start server (http + init all http ralated functions)
605
863
  * @param &lt;Promise&gt;callbackBefore404 code that should be executed before adding page 404
606
864
  * @returns {Promise}
607
865
  */
608
866
  async startServer(callbackBefore404 = async () =&gt; Promise.resolve()) {
609
- // eslint-disable-next-line global-require
610
- // const HttpServer = require('./services/http/HttpServer');
611
- // eslint-disable-next-line global-require
612
- // const ControllerManager = require('./controllers/index');
613
- // TODO wait until https://github.com/nodejs/node/issues/35889
614
867
  const [{ default: HttpServer }, { default: ControllerManager }] =
615
868
  await Promise.all([
616
- // eslint-disable-next-line import/extensions
617
869
  import('./services/http/HttpServer.js'), // Speed optimisation
618
- // eslint-disable-next-line import/extensions
619
870
  import('./controllers/index.js'), // Speed optimisation
871
+ this.init(),
620
872
  ]);
621
873
  &nbsp;
622
874
  this.addErrorHandling();
@@ -630,21 +882,116 @@ class Server {
630
882
  await callbackBefore404();
631
883
  this.app.httpServer.add404Page();
632
884
  }
885
+ &nbsp;
886
+ /**
887
+ * Do an initialization (config reading, etc)
888
+ * @returns {Promise}
889
+ */
890
+ async init() {
891
+ if (this.#isInited) {
892
+ return true;
893
+ }
894
+ &nbsp;
895
+ console.time('Server init. Done');
896
+ await Promise.all([this.#initConfigFiles(), this.#loadModelFiles()]);
897
+ &nbsp;
898
+ this.#isInited = true;
899
+ &nbsp;
900
+ console.timeEnd('Server init. Done');
901
+ &nbsp;
902
+ return true;
903
+ }
904
+ &nbsp;
905
+ async #initConfigFiles() {
906
+ const files = await getFilesPathWithInheritance({
907
+ internalFolder: `${__dirname}/config`,
908
+ externalFolder: this.app.foldersConfig.config,
909
+ loggerFileType: 'CONFIG',
910
+ logger: (m) =&gt; consoleLogger('info', m),
911
+ filter: {
912
+ startWithCapital: false,
913
+ },
914
+ });
915
+ &nbsp;
916
+ const configFiles = {};
917
+ &nbsp;
918
+ for (const file of files) {
919
+ const config = file.file.split('.');
920
+ if (!configFiles[config[0]]) {
921
+ configFiles[config[0]] = {};
922
+ }
923
+ if (config.length === 2) {
924
+ configFiles[config[0]].default = file.path;
925
+ }<span class="branch-0 cbranch-no" title="branch not covered" > else {</span>
926
+ <span class="cstat-no" title="statement not covered" > configFiles[config[0]][config[1]] = file.path;</span>
927
+ <span class="cstat-no" title="statement not covered" > }</span>
928
+ }
929
+ &nbsp;
930
+ const loadConfig = async (configName, values) =&gt; {
931
+ const promises = [import(values.default)];
932
+ if (process.env.NODE_ENV &amp;&amp; values[process.env.NODE_ENV]) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
933
+ <span class="cstat-no" title="statement not covered" > promises.push(import(values[process.env.NODE_ENV]));</span>
934
+ <span class="cstat-no" title="statement not covered" > }</span>
935
+ const result = await Promise.all(promises);
936
+ return {
937
+ name: configName,
938
+ finalValue: merge(result[0].default, result[1]<span class="branch-0 cbranch-no" title="branch not covered" >?.default </span>|| {}, {
939
+ arrayMerge: (destinationArray, sourceArray) =&gt; sourceArray,
940
+ }),
941
+ };
942
+ };
943
+ &nbsp;
944
+ const loadingPromises = [];
945
+ &nbsp;
946
+ for (const [configFile, value] of Object.entries(configFiles)) {
947
+ loadingPromises.push(loadConfig(configFile, value));
948
+ }
949
+ &nbsp;
950
+ const configs = await Promise.all(loadingPromises);
951
+ &nbsp;
952
+ for (const config of configs) {
953
+ this.cache.configs.set(config.name, config.finalValue);
954
+ }
955
+ return true;
956
+ }
957
+ &nbsp;
958
+ async #loadModelFiles() {
959
+ const files = await getFilesPathWithInheritance({
960
+ internalFolder: `${__dirname}/models`,
961
+ externalFolder: this.app.foldersConfig.models,
962
+ loggerFileType: 'MODEL',
963
+ logger: (m) =&gt; consoleLogger('info', m),
964
+ });
965
+ &nbsp;
966
+ const promises = [];
967
+ for (const file of files) {
968
+ const t = hrtime.bigint();
969
+ promises.push(
970
+ import(file.path).then((f) =&gt; ({
971
+ name: file.file.split('.')[0],
972
+ file: f,
973
+ took: hrtime.bigint() - t,
974
+ })),
975
+ );
976
+ }
977
+ &nbsp;
978
+ const loadedModels = await Promise.all(promises);
979
+ &nbsp;
980
+ for (const model of loadedModels) {
981
+ this.cache.modelConstructors.set(model.name, model.file.default);
982
+ }
983
+ return true;
984
+ }
633
985
  &nbsp;
634
986
  /**
635
987
  * Add error logging on promise reject
636
988
  */
637
- // eslint-disable-next-line class-methods-use-this
638
989
  addErrorHandling() {
639
- process.on('uncaughtException', console.error);
640
- process.on('unhandledRejection', (reason, p) =&gt; {
641
- <span class="cstat-no" title="statement not covered" > console.log(</span>
642
- <span class="cstat-no" title="statement not covered" > 'Possibly Unhandled Rejection at: Promise ',</span>
643
- <span class="cstat-no" title="statement not covered" > p,</span>
644
- <span class="cstat-no" title="statement not covered" > ' reason: ',</span>
645
- <span class="cstat-no" title="statement not covered" > reason,</span>
646
- <span class="cstat-no" title="statement not covered" > );</span>
647
- <span class="cstat-no" title="statement not covered" > console.trace('unhandledRejection');</span>
990
+ process.on('uncaughtException', (e) =&gt;
991
+ this.app.logger.error('uncaughtException', e),
992
+ );
993
+ process.on('unhandledRejection', (e) =&gt; {
994
+ this.app.logger.error('unhandledRejection', e);
648
995
  });
649
996
  }
650
997
  &nbsp;
@@ -659,26 +1006,91 @@ class Server {
659
1006
  * @returns {Object} config object. Structure depends of config file
660
1007
  */
661
1008
  getConfig(configName) {
662
- // const configName = name.charAt(0).toUpperCase() + name.slice(1);
663
- if (!this.cache.configs.has(configName)) {
664
- let envConfig = {};
665
- if (process.env.NODE_ENV) {
666
- envConfig =
667
- this.getFileWithExtendingInhirence(
668
- 'config',
669
- `${configName}.${process.env.NODE_ENV}.js`,
670
- ) || envConfig;
1009
+ if (!this.#isInited) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
1010
+ <span class="cstat-no" title="statement not covered" > throw new Error('You should call Server.init() before using it');</span>
1011
+ <span class="cstat-no" title="statement not covered" > }</span>
1012
+ &nbsp;
1013
+ if (!this.cache.configs.has(configName)) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
1014
+ <span class="cstat-no" title="statement not covered" > this.logger.warn(</span>
1015
+ <span class="cstat-no" title="statement not covered" > `You asked for config ${configName} that not exists. Please check you codebase `,</span>
1016
+ <span class="cstat-no" title="statement not covered" > );</span>
1017
+ <span class="cstat-no" title="statement not covered" > return {};</span>
1018
+ <span class="cstat-no" title="statement not covered" > }</span>
1019
+ return this.cache.configs.get(configName);
1020
+ }
1021
+ &nbsp;
1022
+ /**
1023
+ * Return or create new logger instance. This is a main logger instance
1024
+ */
1025
+ getLogger() {
1026
+ if (!this.#realLogger) {
1027
+ this.#realLogger = this.#createLogger();
1028
+ }
1029
+ return this.#realLogger;
1030
+ }
1031
+ &nbsp;
1032
+ #createLogger() {
1033
+ const alignColorsAndTime = winston.format.combine(
1034
+ winston.format.colorize({
1035
+ all: true,
1036
+ }),
1037
+ winston.format.timestamp(),
1038
+ winston.format.printf(
1039
+ (info) =&gt;
1040
+ `(${process.pid}) \x1B[32m[${info.label ?? 'SERVER'}]\x1B[39m ${
1041
+ info.timestamp
1042
+ } ${info.level} : ${info.message} ${info?.stack ?? ''} ${
1043
+ info.durationMs <span class="branch-0 cbranch-no" title="branch not covered" >? `Duration: ${info.durationMs}ms` </span>: ''
1044
+ }`,
1045
+ ),
1046
+ );
1047
+ const logConfig = this.app.getConfig('log').transports;
1048
+ <span class="fstat-no" title="function not covered" > function IsConstructor(f) {</span>
1049
+ <span class="cstat-no" title="statement not covered" > try {</span>
1050
+ <span class="cstat-no" title="statement not covered" > Reflect.construct(String, [], f);</span>
1051
+ <span class="cstat-no" title="statement not covered" > } catch (e) {</span>
1052
+ <span class="cstat-no" title="statement not covered" > return false;</span>
1053
+ <span class="cstat-no" title="statement not covered" > }</span>
1054
+ <span class="cstat-no" title="statement not covered" > return true;</span>
1055
+ <span class="cstat-no" title="statement not covered" > }</span>
1056
+ &nbsp;
1057
+ const logger = winston.createLogger({
1058
+ format: winston.format.errors({ stack: true }),
1059
+ level: 'silly',
1060
+ });
1061
+ &nbsp;
1062
+ for (const log of logConfig) {
1063
+ if (log.enable) {
1064
+ if (log.transport === 'console') {
1065
+ logger.add(
1066
+ new winston.transports.Console({
1067
+ level: log.transportOptions.level,
1068
+ format: winston.format.combine(
1069
+ winston.format.colorize(),
1070
+ alignColorsAndTime,
1071
+ ),
1072
+ }),
1073
+ );
1074
+ }<span class="branch-0 cbranch-no" title="branch not covered" > else {</span>
1075
+ <span class="cstat-no" title="statement not covered" > import(log.transport).then((Tr) =&gt; {</span>
1076
+ <span class="cstat-no" title="statement not covered" > let Transport = Tr.default;</span>
1077
+ <span class="cstat-no" title="statement not covered" > if (!IsConstructor(Transport) &amp;&amp; Transport.default) {</span>
1078
+ <span class="cstat-no" title="statement not covered" > Transport = Transport.default;</span>
1079
+ <span class="cstat-no" title="statement not covered" > } else {</span>
1080
+ <span class="cstat-no" title="statement not covered" > console.error(</span>
1081
+ <span class="cstat-no" title="statement not covered" > `${log.transport} not a constructor. Please check it`,</span>
1082
+ <span class="cstat-no" title="statement not covered" > );</span>
1083
+ <span class="cstat-no" title="statement not covered" > return;</span>
1084
+ <span class="cstat-no" title="statement not covered" > }</span>
1085
+ <span class="cstat-no" title="statement not covered" > logger.profile(`Adding new logger ${log.transport}`);</span>
1086
+ <span class="cstat-no" title="statement not covered" > logger.add(new Transport(log.transportOptions));</span>
1087
+ <span class="cstat-no" title="statement not covered" > logger.profile(`Adding new logger ${log.transport}`);</span>
1088
+ <span class="cstat-no" title="statement not covered" > });</span>
1089
+ <span class="cstat-no" title="statement not covered" > }</span>
671
1090
  }
672
- this.cache.configs.set(
673
- configName,
674
- merge(
675
- this.getFileWithExtendingInhirence('config', configName),
676
- envConfig,
677
- { arrayMerge: (destinationArray, sourceArray) =&gt; sourceArray },
678
- ),
679
- );
680
1091
  }
681
- return this.cache.configs.get(configName);
1092
+ &nbsp;
1093
+ return logger;
682
1094
  }
683
1095
  &nbsp;
684
1096
  /**
@@ -704,14 +1116,14 @@ class Server {
704
1116
  */
705
1117
  getModel(modelName) {
706
1118
  if (modelName.endsWith('s')) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
707
- <span class="cstat-no" title="statement not covered" > console.warn(</span>
1119
+ <span class="cstat-no" title="statement not covered" > this.app.logger.warn(</span>
708
1120
  <span class="cstat-no" title="statement not covered" > `Probably your model name '${modelName}' in plural from. Try to avoid plural form`,</span>
709
1121
  <span class="cstat-no" title="statement not covered" > );</span>
710
1122
  <span class="cstat-no" title="statement not covered" > }</span>
711
1123
  if (!this.cache.models.has(modelName)) {
712
- const Model = this.getFileWithExtendingInhirence('models', modelName);
1124
+ const Model = this.cache.modelConstructors.get(modelName);
713
1125
  if (!Model) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
714
- <span class="cstat-no" title="statement not covered" > console.error(`Model not found: ${modelName}`);</span>
1126
+ <span class="cstat-no" title="statement not covered" > this.app.logger.error(`Model not found: ${modelName}`);</span>
715
1127
  <span class="cstat-no" title="statement not covered" > return false;</span>
716
1128
  <span class="cstat-no" title="statement not covered" > }</span>
717
1129
  try {
@@ -719,8 +1131,8 @@ class Server {
719
1131
  &nbsp;
720
1132
  this.cache.models.set(modelName, model.mongooseModel);
721
1133
  } <span class="branch-0 cbranch-no" title="branch not covered" >catch (e) {</span>
722
- <span class="cstat-no" title="statement not covered" > console.error(`Problem with model ${modelName}, ${e.message}`);</span>
723
- <span class="cstat-no" title="statement not covered" > console.error(e);</span>
1134
+ <span class="cstat-no" title="statement not covered" > this.app.logger.error(`Problem with model ${modelName}, ${e.message}`);</span>
1135
+ <span class="cstat-no" title="statement not covered" > this.app.logger.error(e);</span>
724
1136
  <span class="cstat-no" title="statement not covered" > }</span>
725
1137
  }
726
1138
  return this.cache.models.get(modelName);
@@ -733,11 +1145,7 @@ class Server {
733
1145
  */
734
1146
  <span class="fstat-no" title="function not covered" > async runCliCommand(commandName, args) {</span>
735
1147
  <span class="cstat-no" title="statement not covered" > if (!this.cli) {</span>
736
- <span class="cstat-no" title="statement not covered" > // eslint-disable-next-line import/extensions</span>
737
- <span class="cstat-no" title="statement not covered" > // TODO wait until https://github.com/nodejs/node/issues/35889</span>
738
- <span class="cstat-no" title="statement not covered" > // const { default: BaseCli } = await import('./modules/BaseCli.js'); // Speed optimisation</span>
739
- <span class="cstat-no" title="statement not covered" > // eslint-disable-next-line global-require</span>
740
- <span class="cstat-no" title="statement not covered" > const BaseCli = require('./modules/BaseCli');</span>
1148
+ <span class="cstat-no" title="statement not covered" > const { default: BaseCli } = await import('./modules/BaseCli.js'); // Speed optimisation</span>
741
1149
  <span class="cstat-no" title="statement not covered" > this.cli = new BaseCli(this);</span>
742
1150
  <span class="cstat-no" title="statement not covered" > }</span>
743
1151
  <span class="cstat-no" title="statement not covered" > return this.cli.run(commandName, args);</span>
@@ -749,52 +1157,10 @@ class Server {
749
1157
  */
750
1158
  getCache() {
751
1159
  if (!this.cacheService) {
752
- // eslint-disable-next-line global-require
753
- const Cache = require('./services/cache/Cache'); // Speed optimisation
754
1160
  this.cacheService = new Cache(this.app);
755
1161
  }
756
1162
  return this.cacheService;
757
1163
  }
758
- &nbsp;
759
- /**
760
- * Get file using Inhirence (ability to overrite models, configs, etc)
761
- * @param {('models'|'config')} fileType type of file to load
762
- * @param {string} fileName name of file to load
763
- */
764
- getFileWithExtendingInhirence(fileType, fileName) {
765
- let file;
766
- try {
767
- // eslint-disable-next-line global-require, import/no-dynamic-require
768
- file = require(`${this.config.folders[fileType]}/${fileName}`);
769
- } catch (e) {
770
- try {
771
- // eslint-disable-next-line global-require, import/no-dynamic-require
772
- file = require(`./${fileType}/${fileName}`);
773
- } catch (e2) {
774
- const levels = [
775
- 'error',
776
- 'warn',
777
- 'info',
778
- 'http',
779
- 'verbose',
780
- 'debug',
781
- 'silly',
782
- ];
783
- &nbsp;
784
- if (
785
- !process.env.LOGGER_CONSOLE_LEVEL ||
786
- levels.indexOf(process.env.LOGGER_CONSOLE_LEVEL) &gt; 0 // as a warn level
787
- ) <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
788
- <span class="cstat-no" title="statement not covered" > console.warn(</span>
789
- <span class="cstat-no" title="statement not covered" > `Config not found '${fileName}'. This can be a normal (in case this an environment config)`,</span>
790
- <span class="cstat-no" title="statement not covered" > );</span>
791
- <span class="cstat-no" title="statement not covered" > }</span>
792
- &nbsp;
793
- file = false;
794
- }
795
- }
796
- return file;
797
- }
798
1164
  }
799
1165
  &nbsp;
800
1166
  module.exports = Server;
@@ -805,7 +1171,7 @@ module.exports = Server;
805
1171
  <div class='footer quiet pad2 space-top1 center small'>
806
1172
  Code coverage generated by
807
1173
  <a href="https://istanbul.js.org/" target="_blank" rel="noopener noreferrer">istanbul</a>
808
- at 2023-09-05T18:04:40.903Z
1174
+ at 2023-09-21T04:47:08.309Z
809
1175
  </div>
810
1176
  <script src="../prettify.js"></script>
811
1177
  <script>