@hitchy/plugin-auth 0.3.0 → 0.3.1
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/api/policy/authentication.js +80 -26
- package/api/service/auth/manager.js +36 -4
- package/api/service/authentication/passport.js +6 -5
- package/api/service/authentication/strategies.js +57 -34
- package/api/service/authorization/tree.js +8 -8
- package/coverage/index.html +38 -38
- package/coverage/plugin-auth/api/controller/index.html +1 -1
- package/coverage/plugin-auth/api/controller/user.js.html +1 -1
- package/coverage/plugin-auth/api/model/authorization/index.html +1 -1
- package/coverage/plugin-auth/api/model/authorization/rule.js.html +1 -1
- package/coverage/plugin-auth/api/model/index.html +1 -1
- package/coverage/plugin-auth/api/model/role.js.html +1 -1
- package/coverage/plugin-auth/api/model/user-to-role.js.html +1 -1
- package/coverage/plugin-auth/api/model/user.js.html +1 -1
- package/coverage/plugin-auth/api/policy/authentication.js.html +215 -50
- package/coverage/plugin-auth/api/policy/authorization.js.html +1 -1
- package/coverage/plugin-auth/api/policy/index.html +18 -18
- package/coverage/plugin-auth/api/policy/user.js.html +1 -1
- package/coverage/plugin-auth/api/service/auth/index.html +17 -17
- package/coverage/plugin-auth/api/service/auth/manager.js.html +109 -13
- package/coverage/plugin-auth/api/service/authentication/index.html +25 -25
- package/coverage/plugin-auth/api/service/authentication/passport.js.html +14 -11
- package/coverage/plugin-auth/api/service/authentication/strategies.js.html +132 -63
- package/coverage/plugin-auth/api/service/authorization/index.html +1 -1
- package/coverage/plugin-auth/api/service/authorization/node.js.html +1 -1
- package/coverage/plugin-auth/api/service/authorization/policy-generator.js.html +1 -1
- package/coverage/plugin-auth/api/service/authorization/tree.js.html +9 -9
- package/coverage/plugin-auth/config/auth.js.html +1 -1
- package/coverage/plugin-auth/config/index.html +1 -1
- package/coverage/plugin-auth/index.html +1 -1
- package/coverage/plugin-auth/index.js.html +2 -2
- package/coverage/tmp/coverage-8472-1648414315419-0.json +1 -0
- package/index.js +4 -1
- package/package.json +1 -1
- package/coverage/tmp/coverage-6744-1648396809135-0.json +0 -1
|
@@ -23,30 +23,30 @@
|
|
|
23
23
|
<div class='clearfix'>
|
|
24
24
|
|
|
25
25
|
<div class='fl pad1y space-right2'>
|
|
26
|
-
<span class="strong">
|
|
26
|
+
<span class="strong">95.22% </span>
|
|
27
27
|
<span class="quiet">Statements</span>
|
|
28
|
-
<span class='fraction'>
|
|
28
|
+
<span class='fraction'>279/293</span>
|
|
29
29
|
</div>
|
|
30
30
|
|
|
31
31
|
|
|
32
32
|
<div class='fl pad1y space-right2'>
|
|
33
|
-
<span class="strong">
|
|
33
|
+
<span class="strong">85.29% </span>
|
|
34
34
|
<span class="quiet">Branches</span>
|
|
35
|
-
<span class='fraction'>
|
|
35
|
+
<span class='fraction'>58/68</span>
|
|
36
36
|
</div>
|
|
37
37
|
|
|
38
38
|
|
|
39
39
|
<div class='fl pad1y space-right2'>
|
|
40
40
|
<span class="strong">100% </span>
|
|
41
41
|
<span class="quiet">Functions</span>
|
|
42
|
-
<span class='fraction'>
|
|
42
|
+
<span class='fraction'>10/10</span>
|
|
43
43
|
</div>
|
|
44
44
|
|
|
45
45
|
|
|
46
46
|
<div class='fl pad1y space-right2'>
|
|
47
|
-
<span class="strong">
|
|
47
|
+
<span class="strong">95.22% </span>
|
|
48
48
|
<span class="quiet">Lines</span>
|
|
49
|
-
<span class='fraction'>
|
|
49
|
+
<span class='fraction'>279/293</span>
|
|
50
50
|
</div>
|
|
51
51
|
|
|
52
52
|
|
|
@@ -318,7 +318,39 @@
|
|
|
318
318
|
<a name='L259'></a><a href='#L259'>259</a>
|
|
319
319
|
<a name='L260'></a><a href='#L260'>260</a>
|
|
320
320
|
<a name='L261'></a><a href='#L261'>261</a>
|
|
321
|
-
<a name='L262'></a><a href='#L262'>262</a
|
|
321
|
+
<a name='L262'></a><a href='#L262'>262</a>
|
|
322
|
+
<a name='L263'></a><a href='#L263'>263</a>
|
|
323
|
+
<a name='L264'></a><a href='#L264'>264</a>
|
|
324
|
+
<a name='L265'></a><a href='#L265'>265</a>
|
|
325
|
+
<a name='L266'></a><a href='#L266'>266</a>
|
|
326
|
+
<a name='L267'></a><a href='#L267'>267</a>
|
|
327
|
+
<a name='L268'></a><a href='#L268'>268</a>
|
|
328
|
+
<a name='L269'></a><a href='#L269'>269</a>
|
|
329
|
+
<a name='L270'></a><a href='#L270'>270</a>
|
|
330
|
+
<a name='L271'></a><a href='#L271'>271</a>
|
|
331
|
+
<a name='L272'></a><a href='#L272'>272</a>
|
|
332
|
+
<a name='L273'></a><a href='#L273'>273</a>
|
|
333
|
+
<a name='L274'></a><a href='#L274'>274</a>
|
|
334
|
+
<a name='L275'></a><a href='#L275'>275</a>
|
|
335
|
+
<a name='L276'></a><a href='#L276'>276</a>
|
|
336
|
+
<a name='L277'></a><a href='#L277'>277</a>
|
|
337
|
+
<a name='L278'></a><a href='#L278'>278</a>
|
|
338
|
+
<a name='L279'></a><a href='#L279'>279</a>
|
|
339
|
+
<a name='L280'></a><a href='#L280'>280</a>
|
|
340
|
+
<a name='L281'></a><a href='#L281'>281</a>
|
|
341
|
+
<a name='L282'></a><a href='#L282'>282</a>
|
|
342
|
+
<a name='L283'></a><a href='#L283'>283</a>
|
|
343
|
+
<a name='L284'></a><a href='#L284'>284</a>
|
|
344
|
+
<a name='L285'></a><a href='#L285'>285</a>
|
|
345
|
+
<a name='L286'></a><a href='#L286'>286</a>
|
|
346
|
+
<a name='L287'></a><a href='#L287'>287</a>
|
|
347
|
+
<a name='L288'></a><a href='#L288'>288</a>
|
|
348
|
+
<a name='L289'></a><a href='#L289'>289</a>
|
|
349
|
+
<a name='L290'></a><a href='#L290'>290</a>
|
|
350
|
+
<a name='L291'></a><a href='#L291'>291</a>
|
|
351
|
+
<a name='L292'></a><a href='#L292'>292</a>
|
|
352
|
+
<a name='L293'></a><a href='#L293'>293</a>
|
|
353
|
+
<a name='L294'></a><a href='#L294'>294</a></td><td class="line-coverage quiet"><span class="cline-any cline-yes">1x</span>
|
|
322
354
|
<span class="cline-any cline-yes">1x</span>
|
|
323
355
|
<span class="cline-any cline-yes">1x</span>
|
|
324
356
|
<span class="cline-any cline-yes">18x</span>
|
|
@@ -578,14 +610,46 @@
|
|
|
578
610
|
<span class="cline-any cline-yes">18x</span>
|
|
579
611
|
<span class="cline-any cline-yes">18x</span>
|
|
580
612
|
<span class="cline-any cline-yes">18x</span>
|
|
613
|
+
<span class="cline-any cline-yes">18x</span>
|
|
614
|
+
<span class="cline-any cline-yes">18x</span>
|
|
615
|
+
<span class="cline-any cline-yes">18x</span>
|
|
616
|
+
<span class="cline-any cline-yes">18x</span>
|
|
617
|
+
<span class="cline-any cline-yes">18x</span>
|
|
618
|
+
<span class="cline-any cline-yes">18x</span>
|
|
619
|
+
<span class="cline-any cline-yes">18x</span>
|
|
620
|
+
<span class="cline-any cline-yes">9x</span>
|
|
621
|
+
<span class="cline-any cline-yes">9x</span>
|
|
622
|
+
<span class="cline-any cline-yes">9x</span>
|
|
623
|
+
<span class="cline-any cline-yes">9x</span>
|
|
624
|
+
<span class="cline-any cline-yes">9x</span>
|
|
625
|
+
<span class="cline-any cline-yes">9x</span>
|
|
626
|
+
<span class="cline-any cline-no"> </span>
|
|
627
|
+
<span class="cline-any cline-yes">9x</span>
|
|
628
|
+
<span class="cline-any cline-yes">9x</span>
|
|
629
|
+
<span class="cline-any cline-yes">9x</span>
|
|
630
|
+
<span class="cline-any cline-yes">9x</span>
|
|
631
|
+
<span class="cline-any cline-yes">9x</span>
|
|
632
|
+
<span class="cline-any cline-yes">9x</span>
|
|
633
|
+
<span class="cline-any cline-yes">9x</span>
|
|
634
|
+
<span class="cline-any cline-no"> </span>
|
|
635
|
+
<span class="cline-any cline-no"> </span>
|
|
636
|
+
<span class="cline-any cline-no"> </span>
|
|
637
|
+
<span class="cline-any cline-yes">9x</span>
|
|
638
|
+
<span class="cline-any cline-yes">9x</span>
|
|
639
|
+
<span class="cline-any cline-no"> </span>
|
|
640
|
+
<span class="cline-any cline-yes">9x</span>
|
|
641
|
+
<span class="cline-any cline-yes">9x</span>
|
|
642
|
+
<span class="cline-any cline-yes">18x</span>
|
|
643
|
+
<span class="cline-any cline-yes">18x</span>
|
|
644
|
+
<span class="cline-any cline-yes">18x</span>
|
|
581
645
|
<span class="cline-any cline-yes">1x</span>
|
|
582
646
|
<span class="cline-any cline-neutral"> </span></td><td class="text"><pre class="prettyprint lang-js">"use strict";
|
|
583
647
|
|
|
584
648
|
module.exports = function() {
|
|
585
649
|
const api = this;
|
|
586
|
-
const { models } = api.runtime;
|
|
650
|
+
const { models, services } = api.runtime;
|
|
587
651
|
|
|
588
|
-
const
|
|
652
|
+
const logDebug = api.log( "hitchy:plugin:auth:debug" );
|
|
589
653
|
|
|
590
654
|
/**
|
|
591
655
|
* Implements several helper methods meant to simplify user/role management.
|
|
@@ -808,7 +872,7 @@ module.exports = function() {
|
|
|
808
872
|
const users = await this.listUsersOfRole( role );
|
|
809
873
|
|
|
810
874
|
if ( users.length > 0 ) {
|
|
811
|
-
|
|
875
|
+
logDebug( "admin user found" );
|
|
812
876
|
|
|
813
877
|
return users;
|
|
814
878
|
}
|
|
@@ -822,7 +886,7 @@ module.exports = function() {
|
|
|
822
886
|
} else {
|
|
823
887
|
const config = api.config.auth.admin;
|
|
824
888
|
|
|
825
|
-
|
|
889
|
+
logDebug( "creating admin user" );
|
|
826
890
|
|
|
827
891
|
user = new models.User();
|
|
828
892
|
|
|
@@ -836,6 +900,38 @@ module.exports = function() {
|
|
|
836
900
|
|
|
837
901
|
return [user];
|
|
838
902
|
}
|
|
903
|
+
|
|
904
|
+
/**
|
|
905
|
+
* Checks if named user can be authenticated locally using provided
|
|
906
|
+
* password.
|
|
907
|
+
*
|
|
908
|
+
* @param {string} username name of user to authenticate
|
|
909
|
+
* @param {string} password password of named to user
|
|
910
|
+
* @return {Promise<User>} promises successfully authenticated user
|
|
911
|
+
*/
|
|
912
|
+
static async checkAuthentication( username, password ) {
|
|
913
|
+
const candidates = ( await models.User
|
|
914
|
+
.find( { eq: { name: username } }, {}, { loadRecords: true } ) )
|
|
915
|
+
.filter( user => !user.strategy <span class="branch-0 cbranch-no" title="branch not covered" >|| user.strategy === "local" </span>);
|
|
916
|
+
|
|
917
|
+
switch ( candidates.length ) {
|
|
918
|
+
<span class="branch-0 cbranch-no" title="branch not covered" > case 0 :</span>
|
|
919
|
+
<span class="cstat-no" title="statement not covered" > throw new services.HttpException( 400, `no such local user: ${username}` );</span>
|
|
920
|
+
|
|
921
|
+
case 1 : {
|
|
922
|
+
const [user] = candidates;
|
|
923
|
+
|
|
924
|
+
if ( await user.verifyPassword( password ) ) {
|
|
925
|
+
return user;
|
|
926
|
+
}
|
|
927
|
+
<span class="cstat-no" title="statement not covered" ><span class="branch-0 cbranch-no" title="branch not covered" ></span></span>
|
|
928
|
+
<span class="cstat-no" title="statement not covered" > throw new services.HttpException( 400, "invalid password" );</span>
|
|
929
|
+
<span class="cstat-no" title="statement not covered" > }</span>
|
|
930
|
+
|
|
931
|
+
<span class="branch-0 cbranch-no" title="branch not covered" > default :</span>
|
|
932
|
+
<span class="cstat-no" title="statement not covered" > throw new services.HttpException( 400, "ambiguous username" );</span>
|
|
933
|
+
}
|
|
934
|
+
}
|
|
839
935
|
}
|
|
840
936
|
|
|
841
937
|
return AuthManager;
|
|
@@ -847,7 +943,7 @@ module.exports = function() {
|
|
|
847
943
|
<div class='footer quiet pad2 space-top1 center small'>
|
|
848
944
|
Code coverage generated by
|
|
849
945
|
<a href="https://istanbul.js.org/" target="_blank">istanbul</a>
|
|
850
|
-
at Sun Mar 27 2022
|
|
946
|
+
at Sun Mar 27 2022 22:51:56 GMT+0200 (Mitteleuropäische Sommerzeit)
|
|
851
947
|
</div>
|
|
852
948
|
</div>
|
|
853
949
|
<script src="../../../../prettify.js"></script>
|
|
@@ -23,30 +23,30 @@
|
|
|
23
23
|
<div class='clearfix'>
|
|
24
24
|
|
|
25
25
|
<div class='fl pad1y space-right2'>
|
|
26
|
-
<span class="strong">
|
|
26
|
+
<span class="strong">82.48% </span>
|
|
27
27
|
<span class="quiet">Statements</span>
|
|
28
|
-
<span class='fraction'>
|
|
28
|
+
<span class='fraction'>292/354</span>
|
|
29
29
|
</div>
|
|
30
30
|
|
|
31
31
|
|
|
32
32
|
<div class='fl pad1y space-right2'>
|
|
33
|
-
<span class="strong">
|
|
33
|
+
<span class="strong">79.06% </span>
|
|
34
34
|
<span class="quiet">Branches</span>
|
|
35
|
-
<span class='fraction'>
|
|
35
|
+
<span class='fraction'>34/43</span>
|
|
36
36
|
</div>
|
|
37
37
|
|
|
38
38
|
|
|
39
39
|
<div class='fl pad1y space-right2'>
|
|
40
|
-
<span class="strong">
|
|
40
|
+
<span class="strong">86.66% </span>
|
|
41
41
|
<span class="quiet">Functions</span>
|
|
42
|
-
<span class='fraction'>13/
|
|
42
|
+
<span class='fraction'>13/15</span>
|
|
43
43
|
</div>
|
|
44
44
|
|
|
45
45
|
|
|
46
46
|
<div class='fl pad1y space-right2'>
|
|
47
|
-
<span class="strong">
|
|
47
|
+
<span class="strong">82.48% </span>
|
|
48
48
|
<span class="quiet">Lines</span>
|
|
49
|
-
<span class='fraction'>
|
|
49
|
+
<span class='fraction'>292/354</span>
|
|
50
50
|
</div>
|
|
51
51
|
|
|
52
52
|
|
|
@@ -74,32 +74,32 @@
|
|
|
74
74
|
</thead>
|
|
75
75
|
<tbody><tr>
|
|
76
76
|
<td class="file high" data-value="passport.js"><a href="passport.js.html">passport.js</a></td>
|
|
77
|
-
<td data-value="94.
|
|
77
|
+
<td data-value="94.36" class="pic high">
|
|
78
78
|
<div class="chart"><div class="cover-fill" style="width: 94%"></div><div class="cover-empty" style="width: 6%"></div></div>
|
|
79
79
|
</td>
|
|
80
|
-
<td data-value="94.
|
|
81
|
-
<td data-value="
|
|
80
|
+
<td data-value="94.36" class="pct high">94.36%</td>
|
|
81
|
+
<td data-value="71" class="abs high">67/71</td>
|
|
82
82
|
<td data-value="81.81" class="pct high">81.81%</td>
|
|
83
83
|
<td data-value="11" class="abs high">9/11</td>
|
|
84
84
|
<td data-value="100" class="pct high">100%</td>
|
|
85
85
|
<td data-value="2" class="abs high">2/2</td>
|
|
86
|
-
<td data-value="94.
|
|
87
|
-
<td data-value="
|
|
86
|
+
<td data-value="94.36" class="pct high">94.36%</td>
|
|
87
|
+
<td data-value="71" class="abs high">67/71</td>
|
|
88
88
|
</tr>
|
|
89
89
|
|
|
90
90
|
<tr>
|
|
91
|
-
<td class="file
|
|
92
|
-
<td data-value="
|
|
93
|
-
<div class="chart"><div class="cover-fill" style="width:
|
|
91
|
+
<td class="file medium" data-value="strategies.js"><a href="strategies.js.html">strategies.js</a></td>
|
|
92
|
+
<td data-value="79.5" class="pic medium">
|
|
93
|
+
<div class="chart"><div class="cover-fill" style="width: 79%"></div><div class="cover-empty" style="width: 21%"></div></div>
|
|
94
94
|
</td>
|
|
95
|
-
<td data-value="
|
|
96
|
-
<td data-value="
|
|
97
|
-
<td data-value="
|
|
98
|
-
<td data-value="
|
|
99
|
-
<td data-value="
|
|
100
|
-
<td data-value="
|
|
101
|
-
<td data-value="
|
|
102
|
-
<td data-value="
|
|
95
|
+
<td data-value="79.5" class="pct medium">79.5%</td>
|
|
96
|
+
<td data-value="283" class="abs medium">225/283</td>
|
|
97
|
+
<td data-value="78.12" class="pct medium">78.12%</td>
|
|
98
|
+
<td data-value="32" class="abs medium">25/32</td>
|
|
99
|
+
<td data-value="84.61" class="pct high">84.61%</td>
|
|
100
|
+
<td data-value="13" class="abs high">11/13</td>
|
|
101
|
+
<td data-value="79.5" class="pct medium">79.5%</td>
|
|
102
|
+
<td data-value="283" class="abs medium">225/283</td>
|
|
103
103
|
</tr>
|
|
104
104
|
|
|
105
105
|
</tbody>
|
|
@@ -110,7 +110,7 @@
|
|
|
110
110
|
<div class='footer quiet pad2 space-top1 center small'>
|
|
111
111
|
Code coverage generated by
|
|
112
112
|
<a href="https://istanbul.js.org/" target="_blank">istanbul</a>
|
|
113
|
-
at Sun Mar 27 2022
|
|
113
|
+
at Sun Mar 27 2022 22:51:56 GMT+0200 (Mitteleuropäische Sommerzeit)
|
|
114
114
|
</div>
|
|
115
115
|
</div>
|
|
116
116
|
<script src="../../../../prettify.js"></script>
|
|
@@ -23,9 +23,9 @@
|
|
|
23
23
|
<div class='clearfix'>
|
|
24
24
|
|
|
25
25
|
<div class='fl pad1y space-right2'>
|
|
26
|
-
<span class="strong">94.
|
|
26
|
+
<span class="strong">94.36% </span>
|
|
27
27
|
<span class="quiet">Statements</span>
|
|
28
|
-
<span class='fraction'>
|
|
28
|
+
<span class='fraction'>67/71</span>
|
|
29
29
|
</div>
|
|
30
30
|
|
|
31
31
|
|
|
@@ -44,9 +44,9 @@
|
|
|
44
44
|
|
|
45
45
|
|
|
46
46
|
<div class='fl pad1y space-right2'>
|
|
47
|
-
<span class="strong">94.
|
|
47
|
+
<span class="strong">94.36% </span>
|
|
48
48
|
<span class="quiet">Lines</span>
|
|
49
|
-
<span class='fraction'>
|
|
49
|
+
<span class='fraction'>67/71</span>
|
|
50
50
|
</div>
|
|
51
51
|
|
|
52
52
|
|
|
@@ -127,7 +127,8 @@
|
|
|
127
127
|
<a name='L68'></a><a href='#L68'>68</a>
|
|
128
128
|
<a name='L69'></a><a href='#L69'>69</a>
|
|
129
129
|
<a name='L70'></a><a href='#L70'>70</a>
|
|
130
|
-
<a name='L71'></a><a href='#L71'>71</a
|
|
130
|
+
<a name='L71'></a><a href='#L71'>71</a>
|
|
131
|
+
<a name='L72'></a><a href='#L72'>72</a></td><td class="line-coverage quiet"><span class="cline-any cline-yes">1x</span>
|
|
131
132
|
<span class="cline-any cline-yes">1x</span>
|
|
132
133
|
<span class="cline-any cline-yes">1x</span>
|
|
133
134
|
<span class="cline-any cline-yes">1x</span>
|
|
@@ -150,6 +151,7 @@
|
|
|
150
151
|
<span class="cline-any cline-yes">18x</span>
|
|
151
152
|
<span class="cline-any cline-yes">18x</span>
|
|
152
153
|
<span class="cline-any cline-yes">18x</span>
|
|
154
|
+
<span class="cline-any cline-yes">18x</span>
|
|
153
155
|
<span class="cline-any cline-yes">11x</span>
|
|
154
156
|
<span class="cline-any cline-yes">11x</span>
|
|
155
157
|
<span class="cline-any cline-yes">11x</span>
|
|
@@ -203,8 +205,9 @@ const PassportLib = require( "passport" );
|
|
|
203
205
|
|
|
204
206
|
module.exports = function() {
|
|
205
207
|
const api = this;
|
|
206
|
-
|
|
207
|
-
const
|
|
208
|
+
|
|
209
|
+
const logAlert = api.log( "hitchy:plugin:auth:alert" );
|
|
210
|
+
const logDebug = api.log( "hitchy:plugin:auth:debug" );
|
|
208
211
|
|
|
209
212
|
const passport = new PassportLib.Passport();
|
|
210
213
|
|
|
@@ -220,7 +223,7 @@ module.exports = function() {
|
|
|
220
223
|
|
|
221
224
|
// set up passport to persist current user in server-side session
|
|
222
225
|
passport.serializeUser( ( user, done ) => {
|
|
223
|
-
|
|
226
|
+
logDebug( `serializeUser: { name: ${user.name}, uuid: ${user.uuid} }` );
|
|
224
227
|
|
|
225
228
|
done( null, user.uuid );
|
|
226
229
|
} );
|
|
@@ -239,7 +242,7 @@ module.exports = function() {
|
|
|
239
242
|
.then( roles => {
|
|
240
243
|
user.roles = roles;
|
|
241
244
|
|
|
242
|
-
|
|
245
|
+
logDebug( `still authenticated user: name: ${user.name}, uuid: ${user.uuid}, roles: ${roles.join( "," )}` );
|
|
243
246
|
|
|
244
247
|
done( null, user );
|
|
245
248
|
} )
|
|
@@ -259,7 +262,7 @@ module.exports = function() {
|
|
|
259
262
|
try {
|
|
260
263
|
passport.use( name, strategy );
|
|
261
264
|
} <span class="branch-0 cbranch-no" title="branch not covered" >catch ( error ) {</span>
|
|
262
|
-
<span class="cstat-no" title="statement not covered" >
|
|
265
|
+
<span class="cstat-no" title="statement not covered" > logAlert( `using passport strategy ${name} failed:`, error );</span>
|
|
263
266
|
<span class="cstat-no" title="statement not covered" > }</span>
|
|
264
267
|
}
|
|
265
268
|
}
|
|
@@ -274,7 +277,7 @@ module.exports = function() {
|
|
|
274
277
|
<div class='footer quiet pad2 space-top1 center small'>
|
|
275
278
|
Code coverage generated by
|
|
276
279
|
<a href="https://istanbul.js.org/" target="_blank">istanbul</a>
|
|
277
|
-
at Sun Mar 27 2022
|
|
280
|
+
at Sun Mar 27 2022 22:51:56 GMT+0200 (Mitteleuropäische Sommerzeit)
|
|
278
281
|
</div>
|
|
279
282
|
</div>
|
|
280
283
|
<script src="../../../../prettify.js"></script>
|