@sentry/warden 0.30.0 → 0.31.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 (185) hide show
  1. package/CHANGELOG.md +246 -0
  2. package/README.md +2 -1
  3. package/coverage/lcov-report/base.css +224 -0
  4. package/coverage/lcov-report/block-navigation.js +87 -0
  5. package/coverage/lcov-report/favicon.png +0 -0
  6. package/coverage/lcov-report/index.html +446 -0
  7. package/coverage/lcov-report/prettify.css +1 -0
  8. package/coverage/lcov-report/prettify.js +2 -0
  9. package/coverage/lcov-report/sort-arrow-sprite.png +0 -0
  10. package/coverage/lcov-report/sorter.js +210 -0
  11. package/coverage/lcov-report/src/action/checks/index.html +116 -0
  12. package/coverage/lcov-report/src/action/checks/manager.ts.html +499 -0
  13. package/coverage/lcov-report/src/action/error-reporting.ts.html +181 -0
  14. package/coverage/lcov-report/src/action/fix-evaluation/github.ts.html +508 -0
  15. package/coverage/lcov-report/src/action/fix-evaluation/index.html +161 -0
  16. package/coverage/lcov-report/src/action/fix-evaluation/index.ts.html +1243 -0
  17. package/coverage/lcov-report/src/action/fix-evaluation/judge.ts.html +817 -0
  18. package/coverage/lcov-report/src/action/fix-evaluation/types.ts.html +274 -0
  19. package/coverage/lcov-report/src/action/index.html +161 -0
  20. package/coverage/lcov-report/src/action/inputs.ts.html +529 -0
  21. package/coverage/lcov-report/src/action/pi-ncc-compat.ts.html +292 -0
  22. package/coverage/lcov-report/src/action/review/coordination.ts.html +208 -0
  23. package/coverage/lcov-report/src/action/review/index.html +131 -0
  24. package/coverage/lcov-report/src/action/review/poster.ts.html +1051 -0
  25. package/coverage/lcov-report/src/action/review-state.ts.html +280 -0
  26. package/coverage/lcov-report/src/action/triggers/executor.ts.html +856 -0
  27. package/coverage/lcov-report/src/action/triggers/index.html +116 -0
  28. package/coverage/lcov-report/src/action/workflow/base.ts.html +1135 -0
  29. package/coverage/lcov-report/src/action/workflow/index.html +146 -0
  30. package/coverage/lcov-report/src/action/workflow/pr-workflow.ts.html +2713 -0
  31. package/coverage/lcov-report/src/action/workflow/schedule.ts.html +1027 -0
  32. package/coverage/lcov-report/src/cli/args.ts.html +1657 -0
  33. package/coverage/lcov-report/src/cli/commands/add.ts.html +1567 -0
  34. package/coverage/lcov-report/src/cli/commands/build.ts.html +1618 -0
  35. package/coverage/lcov-report/src/cli/commands/index.html +191 -0
  36. package/coverage/lcov-report/src/cli/commands/init.ts.html +1357 -0
  37. package/coverage/lcov-report/src/cli/commands/runs.ts.html +2560 -0
  38. package/coverage/lcov-report/src/cli/commands/setup-app/browser.ts.html +214 -0
  39. package/coverage/lcov-report/src/cli/commands/setup-app/credentials.ts.html +220 -0
  40. package/coverage/lcov-report/src/cli/commands/setup-app/index.html +161 -0
  41. package/coverage/lcov-report/src/cli/commands/setup-app/manifest.ts.html +235 -0
  42. package/coverage/lcov-report/src/cli/commands/setup-app/server.ts.html +601 -0
  43. package/coverage/lcov-report/src/cli/commands/setup-app.ts.html +571 -0
  44. package/coverage/lcov-report/src/cli/commands/sync.ts.html +475 -0
  45. package/coverage/lcov-report/src/cli/context.ts.html +532 -0
  46. package/coverage/lcov-report/src/cli/diff-apply.ts.html +334 -0
  47. package/coverage/lcov-report/src/cli/files.ts.html +904 -0
  48. package/coverage/lcov-report/src/cli/fix.ts.html +1060 -0
  49. package/coverage/lcov-report/src/cli/git.ts.html +1201 -0
  50. package/coverage/lcov-report/src/cli/help.ts.html +1696 -0
  51. package/coverage/lcov-report/src/cli/index.html +281 -0
  52. package/coverage/lcov-report/src/cli/input.ts.html +397 -0
  53. package/coverage/lcov-report/src/cli/log-cleanup.ts.html +337 -0
  54. package/coverage/lcov-report/src/cli/main.ts.html +5107 -0
  55. package/coverage/lcov-report/src/cli/output/box.ts.html +790 -0
  56. package/coverage/lcov-report/src/cli/output/formatters.ts.html +1099 -0
  57. package/coverage/lcov-report/src/cli/output/icons.ts.html +142 -0
  58. package/coverage/lcov-report/src/cli/output/index.html +281 -0
  59. package/coverage/lcov-report/src/cli/output/index.ts.html +295 -0
  60. package/coverage/lcov-report/src/cli/output/ink-runner.tsx.html +1597 -0
  61. package/coverage/lcov-report/src/cli/output/jsonl-schema-gen.ts.html +355 -0
  62. package/coverage/lcov-report/src/cli/output/jsonl.ts.html +2137 -0
  63. package/coverage/lcov-report/src/cli/output/live-status.tsx.html +916 -0
  64. package/coverage/lcov-report/src/cli/output/reporter.ts.html +1630 -0
  65. package/coverage/lcov-report/src/cli/output/tasks.ts.html +3193 -0
  66. package/coverage/lcov-report/src/cli/output/tty.ts.html +310 -0
  67. package/coverage/lcov-report/src/cli/output/verbosity.ts.html +181 -0
  68. package/coverage/lcov-report/src/cli/signals.ts.html +199 -0
  69. package/coverage/lcov-report/src/cli/terminal.ts.html +1060 -0
  70. package/coverage/lcov-report/src/config/index.html +161 -0
  71. package/coverage/lcov-report/src/config/index.ts.html +94 -0
  72. package/coverage/lcov-report/src/config/loader.ts.html +1753 -0
  73. package/coverage/lcov-report/src/config/schema.ts.html +910 -0
  74. package/coverage/lcov-report/src/config/writer.ts.html +538 -0
  75. package/coverage/lcov-report/src/diff/apply.ts.html +241 -0
  76. package/coverage/lcov-report/src/diff/classify.ts.html +361 -0
  77. package/coverage/lcov-report/src/diff/coalesce.ts.html +1123 -0
  78. package/coverage/lcov-report/src/diff/context.ts.html +952 -0
  79. package/coverage/lcov-report/src/diff/index.html +191 -0
  80. package/coverage/lcov-report/src/diff/index.ts.html +100 -0
  81. package/coverage/lcov-report/src/diff/parser.ts.html +532 -0
  82. package/coverage/lcov-report/src/evals/harness.ts.html +700 -0
  83. package/coverage/lcov-report/src/evals/index.html +221 -0
  84. package/coverage/lcov-report/src/evals/index.ts.html +955 -0
  85. package/coverage/lcov-report/src/evals/names.ts.html +121 -0
  86. package/coverage/lcov-report/src/evals/runner.ts.html +664 -0
  87. package/coverage/lcov-report/src/evals/scaffold.ts.html +970 -0
  88. package/coverage/lcov-report/src/evals/types.ts.html +661 -0
  89. package/coverage/lcov-report/src/evals/usage.ts.html +178 -0
  90. package/coverage/lcov-report/src/evals/verify.ts.html +1054 -0
  91. package/coverage/lcov-report/src/event/context.ts.html +490 -0
  92. package/coverage/lcov-report/src/event/index.html +116 -0
  93. package/coverage/lcov-report/src/index.html +116 -0
  94. package/coverage/lcov-report/src/output/dedup.ts.html +2950 -0
  95. package/coverage/lcov-report/src/output/github-checks.ts.html +1579 -0
  96. package/coverage/lcov-report/src/output/index.html +161 -0
  97. package/coverage/lcov-report/src/output/renderer.ts.html +988 -0
  98. package/coverage/lcov-report/src/output/stale.ts.html +640 -0
  99. package/coverage/lcov-report/src/sdk/analyze.ts.html +3010 -0
  100. package/coverage/lcov-report/src/sdk/auth.ts.html +217 -0
  101. package/coverage/lcov-report/src/sdk/circuit-breaker.ts.html +304 -0
  102. package/coverage/lcov-report/src/sdk/errors.ts.html +658 -0
  103. package/coverage/lcov-report/src/sdk/extract.ts.html +1810 -0
  104. package/coverage/lcov-report/src/sdk/fix-quality.ts.html +841 -0
  105. package/coverage/lcov-report/src/sdk/haiku.ts.html +1456 -0
  106. package/coverage/lcov-report/src/sdk/index.html +416 -0
  107. package/coverage/lcov-report/src/sdk/json-output.ts.html +508 -0
  108. package/coverage/lcov-report/src/sdk/model-pricing.json.html +499 -0
  109. package/coverage/lcov-report/src/sdk/otel.ts.html +433 -0
  110. package/coverage/lcov-report/src/sdk/post-process.ts.html +412 -0
  111. package/coverage/lcov-report/src/sdk/prepare.ts.html +400 -0
  112. package/coverage/lcov-report/src/sdk/pricing.ts.html +778 -0
  113. package/coverage/lcov-report/src/sdk/prompt-sections.ts.html +595 -0
  114. package/coverage/lcov-report/src/sdk/prompt.ts.html +451 -0
  115. package/coverage/lcov-report/src/sdk/report-files.ts.html +166 -0
  116. package/coverage/lcov-report/src/sdk/retry.ts.html +202 -0
  117. package/coverage/lcov-report/src/sdk/runner.ts.html +400 -0
  118. package/coverage/lcov-report/src/sdk/runtimes/claude.ts.html +1693 -0
  119. package/coverage/lcov-report/src/sdk/runtimes/index.html +176 -0
  120. package/coverage/lcov-report/src/sdk/runtimes/index.ts.html +244 -0
  121. package/coverage/lcov-report/src/sdk/runtimes/model-selectors.ts.html +328 -0
  122. package/coverage/lcov-report/src/sdk/runtimes/pi.ts.html +2104 -0
  123. package/coverage/lcov-report/src/sdk/runtimes/types.ts.html +508 -0
  124. package/coverage/lcov-report/src/sdk/types.ts.html +730 -0
  125. package/coverage/lcov-report/src/sdk/usage.ts.html +502 -0
  126. package/coverage/lcov-report/src/sdk/verify.ts.html +1027 -0
  127. package/coverage/lcov-report/src/sentry.ts.html +994 -0
  128. package/coverage/lcov-report/src/skill-builder/agentic.ts.html +1063 -0
  129. package/coverage/lcov-report/src/skill-builder/authoring-provider.ts.html +334 -0
  130. package/coverage/lcov-report/src/skill-builder/definition.ts.html +748 -0
  131. package/coverage/lcov-report/src/skill-builder/index.html +236 -0
  132. package/coverage/lcov-report/src/skill-builder/outline-contract.ts.html +400 -0
  133. package/coverage/lcov-report/src/skill-builder/outline-state.ts.html +382 -0
  134. package/coverage/lcov-report/src/skill-builder/outline.ts.html +1402 -0
  135. package/coverage/lcov-report/src/skill-builder/skill-contract.ts.html +382 -0
  136. package/coverage/lcov-report/src/skill-builder/skill-prompts.ts.html +1180 -0
  137. package/coverage/lcov-report/src/skill-builder/skill.ts.html +2398 -0
  138. package/coverage/lcov-report/src/skills/index.html +131 -0
  139. package/coverage/lcov-report/src/skills/loader.ts.html +1693 -0
  140. package/coverage/lcov-report/src/skills/remote.ts.html +1909 -0
  141. package/coverage/lcov-report/src/triggers/index.html +116 -0
  142. package/coverage/lcov-report/src/triggers/matcher.ts.html +841 -0
  143. package/coverage/lcov-report/src/types/index.html +116 -0
  144. package/coverage/lcov-report/src/types/index.ts.html +1240 -0
  145. package/coverage/lcov-report/src/utils/async.ts.html +331 -0
  146. package/coverage/lcov-report/src/utils/exec.ts.html +496 -0
  147. package/coverage/lcov-report/src/utils/index.html +176 -0
  148. package/coverage/lcov-report/src/utils/index.ts.html +313 -0
  149. package/coverage/lcov-report/src/utils/path.ts.html +202 -0
  150. package/coverage/lcov-report/src/utils/version.ts.html +136 -0
  151. package/coverage/lcov.info +19134 -0
  152. package/dist/cli/commands/runs.d.ts +1 -1
  153. package/dist/cli/commands/runs.d.ts.map +1 -1
  154. package/dist/cli/commands/runs.js +1 -1
  155. package/dist/cli/commands/runs.js.map +1 -1
  156. package/dist/cli/files.d.ts.map +1 -1
  157. package/dist/cli/files.js +10 -11
  158. package/dist/cli/files.js.map +1 -1
  159. package/dist/sdk/verify.d.ts.map +1 -1
  160. package/dist/sdk/verify.js +3 -2
  161. package/dist/sdk/verify.js.map +1 -1
  162. package/dist/skill-builder/outline.d.ts.map +1 -1
  163. package/dist/skill-builder/outline.js.map +1 -1
  164. package/package.json +8 -3
  165. package/test-results.junit.xml +4329 -0
  166. package/dist/evals/index.d.ts +0 -22
  167. package/dist/evals/index.d.ts.map +0 -1
  168. package/dist/evals/index.js +0 -92
  169. package/dist/evals/index.js.map +0 -1
  170. package/dist/evals/judge.d.ts +0 -12
  171. package/dist/evals/judge.d.ts.map +0 -1
  172. package/dist/evals/judge.js +0 -171
  173. package/dist/evals/judge.js.map +0 -1
  174. package/dist/evals/runner.d.ts +0 -18
  175. package/dist/evals/runner.d.ts.map +0 -1
  176. package/dist/evals/runner.js +0 -149
  177. package/dist/evals/runner.js.map +0 -1
  178. package/dist/evals/setup.d.ts +0 -2
  179. package/dist/evals/setup.d.ts.map +0 -1
  180. package/dist/evals/setup.js +0 -22
  181. package/dist/evals/setup.js.map +0 -1
  182. package/dist/evals/types.d.ts +0 -160
  183. package/dist/evals/types.d.ts.map +0 -1
  184. package/dist/evals/types.js +0 -148
  185. package/dist/evals/types.js.map +0 -1
@@ -0,0 +1,1597 @@
1
+
2
+ <!doctype html>
3
+ <html lang="en">
4
+
5
+ <head>
6
+ <title>Code coverage report for src/cli/output/ink-runner.tsx</title>
7
+ <meta charset="utf-8" />
8
+ <link rel="stylesheet" href="../../../prettify.css" />
9
+ <link rel="stylesheet" href="../../../base.css" />
10
+ <link rel="shortcut icon" type="image/x-icon" href="../../../favicon.png" />
11
+ <meta name="viewport" content="width=device-width, initial-scale=1" />
12
+ <style type='text/css'>
13
+ .coverage-summary .sorter {
14
+ background-image: url(../../../sort-arrow-sprite.png);
15
+ }
16
+ </style>
17
+ </head>
18
+
19
+ <body>
20
+ <div class='wrapper'>
21
+ <div class='pad1'>
22
+ <h1><a href="../../../index.html">All files</a> / <a href="index.html">src/cli/output</a> ink-runner.tsx</h1>
23
+ <div class='clearfix'>
24
+
25
+ <div class='fl pad1y space-right2'>
26
+ <span class="strong">55.55% </span>
27
+ <span class="quiet">Statements</span>
28
+ <span class='fraction'>115/207</span>
29
+ </div>
30
+
31
+
32
+ <div class='fl pad1y space-right2'>
33
+ <span class="strong">48% </span>
34
+ <span class="quiet">Branches</span>
35
+ <span class='fraction'>72/150</span>
36
+ </div>
37
+
38
+
39
+ <div class='fl pad1y space-right2'>
40
+ <span class="strong">43.33% </span>
41
+ <span class="quiet">Functions</span>
42
+ <span class='fraction'>26/60</span>
43
+ </div>
44
+
45
+
46
+ <div class='fl pad1y space-right2'>
47
+ <span class="strong">58.01% </span>
48
+ <span class="quiet">Lines</span>
49
+ <span class='fraction'>105/181</span>
50
+ </div>
51
+
52
+
53
+ </div>
54
+ <p class="quiet">
55
+ Press <em>n</em> or <em>j</em> to go to the next uncovered block, <em>b</em>, <em>p</em> or <em>k</em> for the previous block.
56
+ </p>
57
+ <template id="filterTemplate">
58
+ <div class="quiet">
59
+ Filter:
60
+ <input type="search" id="fileSearch">
61
+ </div>
62
+ </template>
63
+ </div>
64
+ <div class='status-line medium'></div>
65
+ <pre><table class="coverage">
66
+ <tr><td class="line-count quiet"><a name='L1'></a><a href='#L1'>1</a>
67
+ <a name='L2'></a><a href='#L2'>2</a>
68
+ <a name='L3'></a><a href='#L3'>3</a>
69
+ <a name='L4'></a><a href='#L4'>4</a>
70
+ <a name='L5'></a><a href='#L5'>5</a>
71
+ <a name='L6'></a><a href='#L6'>6</a>
72
+ <a name='L7'></a><a href='#L7'>7</a>
73
+ <a name='L8'></a><a href='#L8'>8</a>
74
+ <a name='L9'></a><a href='#L9'>9</a>
75
+ <a name='L10'></a><a href='#L10'>10</a>
76
+ <a name='L11'></a><a href='#L11'>11</a>
77
+ <a name='L12'></a><a href='#L12'>12</a>
78
+ <a name='L13'></a><a href='#L13'>13</a>
79
+ <a name='L14'></a><a href='#L14'>14</a>
80
+ <a name='L15'></a><a href='#L15'>15</a>
81
+ <a name='L16'></a><a href='#L16'>16</a>
82
+ <a name='L17'></a><a href='#L17'>17</a>
83
+ <a name='L18'></a><a href='#L18'>18</a>
84
+ <a name='L19'></a><a href='#L19'>19</a>
85
+ <a name='L20'></a><a href='#L20'>20</a>
86
+ <a name='L21'></a><a href='#L21'>21</a>
87
+ <a name='L22'></a><a href='#L22'>22</a>
88
+ <a name='L23'></a><a href='#L23'>23</a>
89
+ <a name='L24'></a><a href='#L24'>24</a>
90
+ <a name='L25'></a><a href='#L25'>25</a>
91
+ <a name='L26'></a><a href='#L26'>26</a>
92
+ <a name='L27'></a><a href='#L27'>27</a>
93
+ <a name='L28'></a><a href='#L28'>28</a>
94
+ <a name='L29'></a><a href='#L29'>29</a>
95
+ <a name='L30'></a><a href='#L30'>30</a>
96
+ <a name='L31'></a><a href='#L31'>31</a>
97
+ <a name='L32'></a><a href='#L32'>32</a>
98
+ <a name='L33'></a><a href='#L33'>33</a>
99
+ <a name='L34'></a><a href='#L34'>34</a>
100
+ <a name='L35'></a><a href='#L35'>35</a>
101
+ <a name='L36'></a><a href='#L36'>36</a>
102
+ <a name='L37'></a><a href='#L37'>37</a>
103
+ <a name='L38'></a><a href='#L38'>38</a>
104
+ <a name='L39'></a><a href='#L39'>39</a>
105
+ <a name='L40'></a><a href='#L40'>40</a>
106
+ <a name='L41'></a><a href='#L41'>41</a>
107
+ <a name='L42'></a><a href='#L42'>42</a>
108
+ <a name='L43'></a><a href='#L43'>43</a>
109
+ <a name='L44'></a><a href='#L44'>44</a>
110
+ <a name='L45'></a><a href='#L45'>45</a>
111
+ <a name='L46'></a><a href='#L46'>46</a>
112
+ <a name='L47'></a><a href='#L47'>47</a>
113
+ <a name='L48'></a><a href='#L48'>48</a>
114
+ <a name='L49'></a><a href='#L49'>49</a>
115
+ <a name='L50'></a><a href='#L50'>50</a>
116
+ <a name='L51'></a><a href='#L51'>51</a>
117
+ <a name='L52'></a><a href='#L52'>52</a>
118
+ <a name='L53'></a><a href='#L53'>53</a>
119
+ <a name='L54'></a><a href='#L54'>54</a>
120
+ <a name='L55'></a><a href='#L55'>55</a>
121
+ <a name='L56'></a><a href='#L56'>56</a>
122
+ <a name='L57'></a><a href='#L57'>57</a>
123
+ <a name='L58'></a><a href='#L58'>58</a>
124
+ <a name='L59'></a><a href='#L59'>59</a>
125
+ <a name='L60'></a><a href='#L60'>60</a>
126
+ <a name='L61'></a><a href='#L61'>61</a>
127
+ <a name='L62'></a><a href='#L62'>62</a>
128
+ <a name='L63'></a><a href='#L63'>63</a>
129
+ <a name='L64'></a><a href='#L64'>64</a>
130
+ <a name='L65'></a><a href='#L65'>65</a>
131
+ <a name='L66'></a><a href='#L66'>66</a>
132
+ <a name='L67'></a><a href='#L67'>67</a>
133
+ <a name='L68'></a><a href='#L68'>68</a>
134
+ <a name='L69'></a><a href='#L69'>69</a>
135
+ <a name='L70'></a><a href='#L70'>70</a>
136
+ <a name='L71'></a><a href='#L71'>71</a>
137
+ <a name='L72'></a><a href='#L72'>72</a>
138
+ <a name='L73'></a><a href='#L73'>73</a>
139
+ <a name='L74'></a><a href='#L74'>74</a>
140
+ <a name='L75'></a><a href='#L75'>75</a>
141
+ <a name='L76'></a><a href='#L76'>76</a>
142
+ <a name='L77'></a><a href='#L77'>77</a>
143
+ <a name='L78'></a><a href='#L78'>78</a>
144
+ <a name='L79'></a><a href='#L79'>79</a>
145
+ <a name='L80'></a><a href='#L80'>80</a>
146
+ <a name='L81'></a><a href='#L81'>81</a>
147
+ <a name='L82'></a><a href='#L82'>82</a>
148
+ <a name='L83'></a><a href='#L83'>83</a>
149
+ <a name='L84'></a><a href='#L84'>84</a>
150
+ <a name='L85'></a><a href='#L85'>85</a>
151
+ <a name='L86'></a><a href='#L86'>86</a>
152
+ <a name='L87'></a><a href='#L87'>87</a>
153
+ <a name='L88'></a><a href='#L88'>88</a>
154
+ <a name='L89'></a><a href='#L89'>89</a>
155
+ <a name='L90'></a><a href='#L90'>90</a>
156
+ <a name='L91'></a><a href='#L91'>91</a>
157
+ <a name='L92'></a><a href='#L92'>92</a>
158
+ <a name='L93'></a><a href='#L93'>93</a>
159
+ <a name='L94'></a><a href='#L94'>94</a>
160
+ <a name='L95'></a><a href='#L95'>95</a>
161
+ <a name='L96'></a><a href='#L96'>96</a>
162
+ <a name='L97'></a><a href='#L97'>97</a>
163
+ <a name='L98'></a><a href='#L98'>98</a>
164
+ <a name='L99'></a><a href='#L99'>99</a>
165
+ <a name='L100'></a><a href='#L100'>100</a>
166
+ <a name='L101'></a><a href='#L101'>101</a>
167
+ <a name='L102'></a><a href='#L102'>102</a>
168
+ <a name='L103'></a><a href='#L103'>103</a>
169
+ <a name='L104'></a><a href='#L104'>104</a>
170
+ <a name='L105'></a><a href='#L105'>105</a>
171
+ <a name='L106'></a><a href='#L106'>106</a>
172
+ <a name='L107'></a><a href='#L107'>107</a>
173
+ <a name='L108'></a><a href='#L108'>108</a>
174
+ <a name='L109'></a><a href='#L109'>109</a>
175
+ <a name='L110'></a><a href='#L110'>110</a>
176
+ <a name='L111'></a><a href='#L111'>111</a>
177
+ <a name='L112'></a><a href='#L112'>112</a>
178
+ <a name='L113'></a><a href='#L113'>113</a>
179
+ <a name='L114'></a><a href='#L114'>114</a>
180
+ <a name='L115'></a><a href='#L115'>115</a>
181
+ <a name='L116'></a><a href='#L116'>116</a>
182
+ <a name='L117'></a><a href='#L117'>117</a>
183
+ <a name='L118'></a><a href='#L118'>118</a>
184
+ <a name='L119'></a><a href='#L119'>119</a>
185
+ <a name='L120'></a><a href='#L120'>120</a>
186
+ <a name='L121'></a><a href='#L121'>121</a>
187
+ <a name='L122'></a><a href='#L122'>122</a>
188
+ <a name='L123'></a><a href='#L123'>123</a>
189
+ <a name='L124'></a><a href='#L124'>124</a>
190
+ <a name='L125'></a><a href='#L125'>125</a>
191
+ <a name='L126'></a><a href='#L126'>126</a>
192
+ <a name='L127'></a><a href='#L127'>127</a>
193
+ <a name='L128'></a><a href='#L128'>128</a>
194
+ <a name='L129'></a><a href='#L129'>129</a>
195
+ <a name='L130'></a><a href='#L130'>130</a>
196
+ <a name='L131'></a><a href='#L131'>131</a>
197
+ <a name='L132'></a><a href='#L132'>132</a>
198
+ <a name='L133'></a><a href='#L133'>133</a>
199
+ <a name='L134'></a><a href='#L134'>134</a>
200
+ <a name='L135'></a><a href='#L135'>135</a>
201
+ <a name='L136'></a><a href='#L136'>136</a>
202
+ <a name='L137'></a><a href='#L137'>137</a>
203
+ <a name='L138'></a><a href='#L138'>138</a>
204
+ <a name='L139'></a><a href='#L139'>139</a>
205
+ <a name='L140'></a><a href='#L140'>140</a>
206
+ <a name='L141'></a><a href='#L141'>141</a>
207
+ <a name='L142'></a><a href='#L142'>142</a>
208
+ <a name='L143'></a><a href='#L143'>143</a>
209
+ <a name='L144'></a><a href='#L144'>144</a>
210
+ <a name='L145'></a><a href='#L145'>145</a>
211
+ <a name='L146'></a><a href='#L146'>146</a>
212
+ <a name='L147'></a><a href='#L147'>147</a>
213
+ <a name='L148'></a><a href='#L148'>148</a>
214
+ <a name='L149'></a><a href='#L149'>149</a>
215
+ <a name='L150'></a><a href='#L150'>150</a>
216
+ <a name='L151'></a><a href='#L151'>151</a>
217
+ <a name='L152'></a><a href='#L152'>152</a>
218
+ <a name='L153'></a><a href='#L153'>153</a>
219
+ <a name='L154'></a><a href='#L154'>154</a>
220
+ <a name='L155'></a><a href='#L155'>155</a>
221
+ <a name='L156'></a><a href='#L156'>156</a>
222
+ <a name='L157'></a><a href='#L157'>157</a>
223
+ <a name='L158'></a><a href='#L158'>158</a>
224
+ <a name='L159'></a><a href='#L159'>159</a>
225
+ <a name='L160'></a><a href='#L160'>160</a>
226
+ <a name='L161'></a><a href='#L161'>161</a>
227
+ <a name='L162'></a><a href='#L162'>162</a>
228
+ <a name='L163'></a><a href='#L163'>163</a>
229
+ <a name='L164'></a><a href='#L164'>164</a>
230
+ <a name='L165'></a><a href='#L165'>165</a>
231
+ <a name='L166'></a><a href='#L166'>166</a>
232
+ <a name='L167'></a><a href='#L167'>167</a>
233
+ <a name='L168'></a><a href='#L168'>168</a>
234
+ <a name='L169'></a><a href='#L169'>169</a>
235
+ <a name='L170'></a><a href='#L170'>170</a>
236
+ <a name='L171'></a><a href='#L171'>171</a>
237
+ <a name='L172'></a><a href='#L172'>172</a>
238
+ <a name='L173'></a><a href='#L173'>173</a>
239
+ <a name='L174'></a><a href='#L174'>174</a>
240
+ <a name='L175'></a><a href='#L175'>175</a>
241
+ <a name='L176'></a><a href='#L176'>176</a>
242
+ <a name='L177'></a><a href='#L177'>177</a>
243
+ <a name='L178'></a><a href='#L178'>178</a>
244
+ <a name='L179'></a><a href='#L179'>179</a>
245
+ <a name='L180'></a><a href='#L180'>180</a>
246
+ <a name='L181'></a><a href='#L181'>181</a>
247
+ <a name='L182'></a><a href='#L182'>182</a>
248
+ <a name='L183'></a><a href='#L183'>183</a>
249
+ <a name='L184'></a><a href='#L184'>184</a>
250
+ <a name='L185'></a><a href='#L185'>185</a>
251
+ <a name='L186'></a><a href='#L186'>186</a>
252
+ <a name='L187'></a><a href='#L187'>187</a>
253
+ <a name='L188'></a><a href='#L188'>188</a>
254
+ <a name='L189'></a><a href='#L189'>189</a>
255
+ <a name='L190'></a><a href='#L190'>190</a>
256
+ <a name='L191'></a><a href='#L191'>191</a>
257
+ <a name='L192'></a><a href='#L192'>192</a>
258
+ <a name='L193'></a><a href='#L193'>193</a>
259
+ <a name='L194'></a><a href='#L194'>194</a>
260
+ <a name='L195'></a><a href='#L195'>195</a>
261
+ <a name='L196'></a><a href='#L196'>196</a>
262
+ <a name='L197'></a><a href='#L197'>197</a>
263
+ <a name='L198'></a><a href='#L198'>198</a>
264
+ <a name='L199'></a><a href='#L199'>199</a>
265
+ <a name='L200'></a><a href='#L200'>200</a>
266
+ <a name='L201'></a><a href='#L201'>201</a>
267
+ <a name='L202'></a><a href='#L202'>202</a>
268
+ <a name='L203'></a><a href='#L203'>203</a>
269
+ <a name='L204'></a><a href='#L204'>204</a>
270
+ <a name='L205'></a><a href='#L205'>205</a>
271
+ <a name='L206'></a><a href='#L206'>206</a>
272
+ <a name='L207'></a><a href='#L207'>207</a>
273
+ <a name='L208'></a><a href='#L208'>208</a>
274
+ <a name='L209'></a><a href='#L209'>209</a>
275
+ <a name='L210'></a><a href='#L210'>210</a>
276
+ <a name='L211'></a><a href='#L211'>211</a>
277
+ <a name='L212'></a><a href='#L212'>212</a>
278
+ <a name='L213'></a><a href='#L213'>213</a>
279
+ <a name='L214'></a><a href='#L214'>214</a>
280
+ <a name='L215'></a><a href='#L215'>215</a>
281
+ <a name='L216'></a><a href='#L216'>216</a>
282
+ <a name='L217'></a><a href='#L217'>217</a>
283
+ <a name='L218'></a><a href='#L218'>218</a>
284
+ <a name='L219'></a><a href='#L219'>219</a>
285
+ <a name='L220'></a><a href='#L220'>220</a>
286
+ <a name='L221'></a><a href='#L221'>221</a>
287
+ <a name='L222'></a><a href='#L222'>222</a>
288
+ <a name='L223'></a><a href='#L223'>223</a>
289
+ <a name='L224'></a><a href='#L224'>224</a>
290
+ <a name='L225'></a><a href='#L225'>225</a>
291
+ <a name='L226'></a><a href='#L226'>226</a>
292
+ <a name='L227'></a><a href='#L227'>227</a>
293
+ <a name='L228'></a><a href='#L228'>228</a>
294
+ <a name='L229'></a><a href='#L229'>229</a>
295
+ <a name='L230'></a><a href='#L230'>230</a>
296
+ <a name='L231'></a><a href='#L231'>231</a>
297
+ <a name='L232'></a><a href='#L232'>232</a>
298
+ <a name='L233'></a><a href='#L233'>233</a>
299
+ <a name='L234'></a><a href='#L234'>234</a>
300
+ <a name='L235'></a><a href='#L235'>235</a>
301
+ <a name='L236'></a><a href='#L236'>236</a>
302
+ <a name='L237'></a><a href='#L237'>237</a>
303
+ <a name='L238'></a><a href='#L238'>238</a>
304
+ <a name='L239'></a><a href='#L239'>239</a>
305
+ <a name='L240'></a><a href='#L240'>240</a>
306
+ <a name='L241'></a><a href='#L241'>241</a>
307
+ <a name='L242'></a><a href='#L242'>242</a>
308
+ <a name='L243'></a><a href='#L243'>243</a>
309
+ <a name='L244'></a><a href='#L244'>244</a>
310
+ <a name='L245'></a><a href='#L245'>245</a>
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>
434
+ <a name='L369'></a><a href='#L369'>369</a>
435
+ <a name='L370'></a><a href='#L370'>370</a>
436
+ <a name='L371'></a><a href='#L371'>371</a>
437
+ <a name='L372'></a><a href='#L372'>372</a>
438
+ <a name='L373'></a><a href='#L373'>373</a>
439
+ <a name='L374'></a><a href='#L374'>374</a>
440
+ <a name='L375'></a><a href='#L375'>375</a>
441
+ <a name='L376'></a><a href='#L376'>376</a>
442
+ <a name='L377'></a><a href='#L377'>377</a>
443
+ <a name='L378'></a><a href='#L378'>378</a>
444
+ <a name='L379'></a><a href='#L379'>379</a>
445
+ <a name='L380'></a><a href='#L380'>380</a>
446
+ <a name='L381'></a><a href='#L381'>381</a>
447
+ <a name='L382'></a><a href='#L382'>382</a>
448
+ <a name='L383'></a><a href='#L383'>383</a>
449
+ <a name='L384'></a><a href='#L384'>384</a>
450
+ <a name='L385'></a><a href='#L385'>385</a>
451
+ <a name='L386'></a><a href='#L386'>386</a>
452
+ <a name='L387'></a><a href='#L387'>387</a>
453
+ <a name='L388'></a><a href='#L388'>388</a>
454
+ <a name='L389'></a><a href='#L389'>389</a>
455
+ <a name='L390'></a><a href='#L390'>390</a>
456
+ <a name='L391'></a><a href='#L391'>391</a>
457
+ <a name='L392'></a><a href='#L392'>392</a>
458
+ <a name='L393'></a><a href='#L393'>393</a>
459
+ <a name='L394'></a><a href='#L394'>394</a>
460
+ <a name='L395'></a><a href='#L395'>395</a>
461
+ <a name='L396'></a><a href='#L396'>396</a>
462
+ <a name='L397'></a><a href='#L397'>397</a>
463
+ <a name='L398'></a><a href='#L398'>398</a>
464
+ <a name='L399'></a><a href='#L399'>399</a>
465
+ <a name='L400'></a><a href='#L400'>400</a>
466
+ <a name='L401'></a><a href='#L401'>401</a>
467
+ <a name='L402'></a><a href='#L402'>402</a>
468
+ <a name='L403'></a><a href='#L403'>403</a>
469
+ <a name='L404'></a><a href='#L404'>404</a>
470
+ <a name='L405'></a><a href='#L405'>405</a>
471
+ <a name='L406'></a><a href='#L406'>406</a>
472
+ <a name='L407'></a><a href='#L407'>407</a>
473
+ <a name='L408'></a><a href='#L408'>408</a>
474
+ <a name='L409'></a><a href='#L409'>409</a>
475
+ <a name='L410'></a><a href='#L410'>410</a>
476
+ <a name='L411'></a><a href='#L411'>411</a>
477
+ <a name='L412'></a><a href='#L412'>412</a>
478
+ <a name='L413'></a><a href='#L413'>413</a>
479
+ <a name='L414'></a><a href='#L414'>414</a>
480
+ <a name='L415'></a><a href='#L415'>415</a>
481
+ <a name='L416'></a><a href='#L416'>416</a>
482
+ <a name='L417'></a><a href='#L417'>417</a>
483
+ <a name='L418'></a><a href='#L418'>418</a>
484
+ <a name='L419'></a><a href='#L419'>419</a>
485
+ <a name='L420'></a><a href='#L420'>420</a>
486
+ <a name='L421'></a><a href='#L421'>421</a>
487
+ <a name='L422'></a><a href='#L422'>422</a>
488
+ <a name='L423'></a><a href='#L423'>423</a>
489
+ <a name='L424'></a><a href='#L424'>424</a>
490
+ <a name='L425'></a><a href='#L425'>425</a>
491
+ <a name='L426'></a><a href='#L426'>426</a>
492
+ <a name='L427'></a><a href='#L427'>427</a>
493
+ <a name='L428'></a><a href='#L428'>428</a>
494
+ <a name='L429'></a><a href='#L429'>429</a>
495
+ <a name='L430'></a><a href='#L430'>430</a>
496
+ <a name='L431'></a><a href='#L431'>431</a>
497
+ <a name='L432'></a><a href='#L432'>432</a>
498
+ <a name='L433'></a><a href='#L433'>433</a>
499
+ <a name='L434'></a><a href='#L434'>434</a>
500
+ <a name='L435'></a><a href='#L435'>435</a>
501
+ <a name='L436'></a><a href='#L436'>436</a>
502
+ <a name='L437'></a><a href='#L437'>437</a>
503
+ <a name='L438'></a><a href='#L438'>438</a>
504
+ <a name='L439'></a><a href='#L439'>439</a>
505
+ <a name='L440'></a><a href='#L440'>440</a>
506
+ <a name='L441'></a><a href='#L441'>441</a>
507
+ <a name='L442'></a><a href='#L442'>442</a>
508
+ <a name='L443'></a><a href='#L443'>443</a>
509
+ <a name='L444'></a><a href='#L444'>444</a>
510
+ <a name='L445'></a><a href='#L445'>445</a>
511
+ <a name='L446'></a><a href='#L446'>446</a>
512
+ <a name='L447'></a><a href='#L447'>447</a>
513
+ <a name='L448'></a><a href='#L448'>448</a>
514
+ <a name='L449'></a><a href='#L449'>449</a>
515
+ <a name='L450'></a><a href='#L450'>450</a>
516
+ <a name='L451'></a><a href='#L451'>451</a>
517
+ <a name='L452'></a><a href='#L452'>452</a>
518
+ <a name='L453'></a><a href='#L453'>453</a>
519
+ <a name='L454'></a><a href='#L454'>454</a>
520
+ <a name='L455'></a><a href='#L455'>455</a>
521
+ <a name='L456'></a><a href='#L456'>456</a>
522
+ <a name='L457'></a><a href='#L457'>457</a>
523
+ <a name='L458'></a><a href='#L458'>458</a>
524
+ <a name='L459'></a><a href='#L459'>459</a>
525
+ <a name='L460'></a><a href='#L460'>460</a>
526
+ <a name='L461'></a><a href='#L461'>461</a>
527
+ <a name='L462'></a><a href='#L462'>462</a>
528
+ <a name='L463'></a><a href='#L463'>463</a>
529
+ <a name='L464'></a><a href='#L464'>464</a>
530
+ <a name='L465'></a><a href='#L465'>465</a>
531
+ <a name='L466'></a><a href='#L466'>466</a>
532
+ <a name='L467'></a><a href='#L467'>467</a>
533
+ <a name='L468'></a><a href='#L468'>468</a>
534
+ <a name='L469'></a><a href='#L469'>469</a>
535
+ <a name='L470'></a><a href='#L470'>470</a>
536
+ <a name='L471'></a><a href='#L471'>471</a>
537
+ <a name='L472'></a><a href='#L472'>472</a>
538
+ <a name='L473'></a><a href='#L473'>473</a>
539
+ <a name='L474'></a><a href='#L474'>474</a>
540
+ <a name='L475'></a><a href='#L475'>475</a>
541
+ <a name='L476'></a><a href='#L476'>476</a>
542
+ <a name='L477'></a><a href='#L477'>477</a>
543
+ <a name='L478'></a><a href='#L478'>478</a>
544
+ <a name='L479'></a><a href='#L479'>479</a>
545
+ <a name='L480'></a><a href='#L480'>480</a>
546
+ <a name='L481'></a><a href='#L481'>481</a>
547
+ <a name='L482'></a><a href='#L482'>482</a>
548
+ <a name='L483'></a><a href='#L483'>483</a>
549
+ <a name='L484'></a><a href='#L484'>484</a>
550
+ <a name='L485'></a><a href='#L485'>485</a>
551
+ <a name='L486'></a><a href='#L486'>486</a>
552
+ <a name='L487'></a><a href='#L487'>487</a>
553
+ <a name='L488'></a><a href='#L488'>488</a>
554
+ <a name='L489'></a><a href='#L489'>489</a>
555
+ <a name='L490'></a><a href='#L490'>490</a>
556
+ <a name='L491'></a><a href='#L491'>491</a>
557
+ <a name='L492'></a><a href='#L492'>492</a>
558
+ <a name='L493'></a><a href='#L493'>493</a>
559
+ <a name='L494'></a><a href='#L494'>494</a>
560
+ <a name='L495'></a><a href='#L495'>495</a>
561
+ <a name='L496'></a><a href='#L496'>496</a>
562
+ <a name='L497'></a><a href='#L497'>497</a>
563
+ <a name='L498'></a><a href='#L498'>498</a>
564
+ <a name='L499'></a><a href='#L499'>499</a>
565
+ <a name='L500'></a><a href='#L500'>500</a>
566
+ <a name='L501'></a><a href='#L501'>501</a>
567
+ <a name='L502'></a><a href='#L502'>502</a>
568
+ <a name='L503'></a><a href='#L503'>503</a>
569
+ <a name='L504'></a><a href='#L504'>504</a>
570
+ <a name='L505'></a><a href='#L505'>505</a></td><td class="line-coverage quiet"><span class="cline-any cline-neutral">&nbsp;</span>
571
+ <span class="cline-any cline-neutral">&nbsp;</span>
572
+ <span class="cline-any cline-neutral">&nbsp;</span>
573
+ <span class="cline-any cline-neutral">&nbsp;</span>
574
+ <span class="cline-any cline-neutral">&nbsp;</span>
575
+ <span class="cline-any cline-neutral">&nbsp;</span>
576
+ <span class="cline-any cline-neutral">&nbsp;</span>
577
+ <span class="cline-any cline-neutral">&nbsp;</span>
578
+ <span class="cline-any cline-neutral">&nbsp;</span>
579
+ <span class="cline-any cline-neutral">&nbsp;</span>
580
+ <span class="cline-any cline-neutral">&nbsp;</span>
581
+ <span class="cline-any cline-neutral">&nbsp;</span>
582
+ <span class="cline-any cline-neutral">&nbsp;</span>
583
+ <span class="cline-any cline-neutral">&nbsp;</span>
584
+ <span class="cline-any cline-neutral">&nbsp;</span>
585
+ <span class="cline-any cline-neutral">&nbsp;</span>
586
+ <span class="cline-any cline-neutral">&nbsp;</span>
587
+ <span class="cline-any cline-neutral">&nbsp;</span>
588
+ <span class="cline-any cline-neutral">&nbsp;</span>
589
+ <span class="cline-any cline-neutral">&nbsp;</span>
590
+ <span class="cline-any cline-neutral">&nbsp;</span>
591
+ <span class="cline-any cline-neutral">&nbsp;</span>
592
+ <span class="cline-any cline-neutral">&nbsp;</span>
593
+ <span class="cline-any cline-neutral">&nbsp;</span>
594
+ <span class="cline-any cline-neutral">&nbsp;</span>
595
+ <span class="cline-any cline-neutral">&nbsp;</span>
596
+ <span class="cline-any cline-neutral">&nbsp;</span>
597
+ <span class="cline-any cline-neutral">&nbsp;</span>
598
+ <span class="cline-any cline-neutral">&nbsp;</span>
599
+ <span class="cline-any cline-neutral">&nbsp;</span>
600
+ <span class="cline-any cline-neutral">&nbsp;</span>
601
+ <span class="cline-any cline-neutral">&nbsp;</span>
602
+ <span class="cline-any cline-neutral">&nbsp;</span>
603
+ <span class="cline-any cline-neutral">&nbsp;</span>
604
+ <span class="cline-any cline-neutral">&nbsp;</span>
605
+ <span class="cline-any cline-neutral">&nbsp;</span>
606
+ <span class="cline-any cline-neutral">&nbsp;</span>
607
+ <span class="cline-any cline-neutral">&nbsp;</span>
608
+ <span class="cline-any cline-neutral">&nbsp;</span>
609
+ <span class="cline-any cline-neutral">&nbsp;</span>
610
+ <span class="cline-any cline-neutral">&nbsp;</span>
611
+ <span class="cline-any cline-neutral">&nbsp;</span>
612
+ <span class="cline-any cline-neutral">&nbsp;</span>
613
+ <span class="cline-any cline-neutral">&nbsp;</span>
614
+ <span class="cline-any cline-no">&nbsp;</span>
615
+ <span class="cline-any cline-neutral">&nbsp;</span>
616
+ <span class="cline-any cline-no">&nbsp;</span>
617
+ <span class="cline-any cline-no">&nbsp;</span>
618
+ <span class="cline-any cline-no">&nbsp;</span>
619
+ <span class="cline-any cline-neutral">&nbsp;</span>
620
+ <span class="cline-any cline-no">&nbsp;</span>
621
+ <span class="cline-any cline-neutral">&nbsp;</span>
622
+ <span class="cline-any cline-neutral">&nbsp;</span>
623
+ <span class="cline-any cline-no">&nbsp;</span>
624
+ <span class="cline-any cline-neutral">&nbsp;</span>
625
+ <span class="cline-any cline-neutral">&nbsp;</span>
626
+ <span class="cline-any cline-neutral">&nbsp;</span>
627
+ <span class="cline-any cline-no">&nbsp;</span>
628
+ <span class="cline-any cline-no">&nbsp;</span>
629
+ <span class="cline-any cline-neutral">&nbsp;</span>
630
+ <span class="cline-any cline-neutral">&nbsp;</span>
631
+ <span class="cline-any cline-neutral">&nbsp;</span>
632
+ <span class="cline-any cline-neutral">&nbsp;</span>
633
+ <span class="cline-any cline-neutral">&nbsp;</span>
634
+ <span class="cline-any cline-neutral">&nbsp;</span>
635
+ <span class="cline-any cline-neutral">&nbsp;</span>
636
+ <span class="cline-any cline-neutral">&nbsp;</span>
637
+ <span class="cline-any cline-yes">6x</span>
638
+ <span class="cline-any cline-yes">6x</span>
639
+ <span class="cline-any cline-yes">1x</span>
640
+ <span class="cline-any cline-yes">6x</span>
641
+ <span class="cline-any cline-neutral">&nbsp;</span>
642
+ <span class="cline-any cline-yes">6x</span>
643
+ <span class="cline-any cline-yes">4x</span>
644
+ <span class="cline-any cline-neutral">&nbsp;</span>
645
+ <span class="cline-any cline-neutral">&nbsp;</span>
646
+ <span class="cline-any cline-yes">2x</span>
647
+ <span class="cline-any cline-neutral">&nbsp;</span>
648
+ <span class="cline-any cline-neutral">&nbsp;</span>
649
+ <span class="cline-any cline-neutral">&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-no">&nbsp;</span>
653
+ <span class="cline-any cline-no">&nbsp;</span>
654
+ <span class="cline-any cline-no">&nbsp;</span>
655
+ <span class="cline-any cline-neutral">&nbsp;</span>
656
+ <span class="cline-any cline-no">&nbsp;</span>
657
+ <span class="cline-any cline-neutral">&nbsp;</span>
658
+ <span class="cline-any cline-neutral">&nbsp;</span>
659
+ <span class="cline-any cline-neutral">&nbsp;</span>
660
+ <span class="cline-any cline-neutral">&nbsp;</span>
661
+ <span class="cline-any cline-neutral">&nbsp;</span>
662
+ <span class="cline-any cline-neutral">&nbsp;</span>
663
+ <span class="cline-any cline-neutral">&nbsp;</span>
664
+ <span class="cline-any cline-neutral">&nbsp;</span>
665
+ <span class="cline-any cline-neutral">&nbsp;</span>
666
+ <span class="cline-any cline-no">&nbsp;</span>
667
+ <span class="cline-any cline-neutral">&nbsp;</span>
668
+ <span class="cline-any cline-neutral">&nbsp;</span>
669
+ <span class="cline-any cline-neutral">&nbsp;</span>
670
+ <span class="cline-any cline-neutral">&nbsp;</span>
671
+ <span class="cline-any cline-neutral">&nbsp;</span>
672
+ <span class="cline-any cline-neutral">&nbsp;</span>
673
+ <span class="cline-any cline-neutral">&nbsp;</span>
674
+ <span class="cline-any cline-neutral">&nbsp;</span>
675
+ <span class="cline-any cline-no">&nbsp;</span>
676
+ <span class="cline-any cline-no">&nbsp;</span>
677
+ <span class="cline-any cline-neutral">&nbsp;</span>
678
+ <span class="cline-any cline-neutral">&nbsp;</span>
679
+ <span class="cline-any cline-neutral">&nbsp;</span>
680
+ <span class="cline-any cline-neutral">&nbsp;</span>
681
+ <span class="cline-any cline-neutral">&nbsp;</span>
682
+ <span class="cline-any cline-neutral">&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-neutral">&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-neutral">&nbsp;</span>
690
+ <span class="cline-any cline-neutral">&nbsp;</span>
691
+ <span class="cline-any cline-neutral">&nbsp;</span>
692
+ <span class="cline-any cline-neutral">&nbsp;</span>
693
+ <span class="cline-any cline-neutral">&nbsp;</span>
694
+ <span class="cline-any cline-neutral">&nbsp;</span>
695
+ <span class="cline-any cline-neutral">&nbsp;</span>
696
+ <span class="cline-any cline-no">&nbsp;</span>
697
+ <span class="cline-any cline-neutral">&nbsp;</span>
698
+ <span class="cline-any cline-neutral">&nbsp;</span>
699
+ <span class="cline-any cline-neutral">&nbsp;</span>
700
+ <span class="cline-any cline-neutral">&nbsp;</span>
701
+ <span class="cline-any cline-neutral">&nbsp;</span>
702
+ <span class="cline-any cline-neutral">&nbsp;</span>
703
+ <span class="cline-any cline-neutral">&nbsp;</span>
704
+ <span class="cline-any cline-neutral">&nbsp;</span>
705
+ <span class="cline-any cline-neutral">&nbsp;</span>
706
+ <span class="cline-any cline-neutral">&nbsp;</span>
707
+ <span class="cline-any cline-no">&nbsp;</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-neutral">&nbsp;</span>
711
+ <span class="cline-any cline-no">&nbsp;</span>
712
+ <span class="cline-any cline-neutral">&nbsp;</span>
713
+ <span class="cline-any cline-neutral">&nbsp;</span>
714
+ <span class="cline-any cline-neutral">&nbsp;</span>
715
+ <span class="cline-any cline-no">&nbsp;</span>
716
+ <span class="cline-any cline-neutral">&nbsp;</span>
717
+ <span class="cline-any cline-neutral">&nbsp;</span>
718
+ <span class="cline-any cline-neutral">&nbsp;</span>
719
+ <span class="cline-any cline-no">&nbsp;</span>
720
+ <span class="cline-any cline-neutral">&nbsp;</span>
721
+ <span class="cline-any cline-neutral">&nbsp;</span>
722
+ <span class="cline-any cline-no">&nbsp;</span>
723
+ <span class="cline-any cline-neutral">&nbsp;</span>
724
+ <span class="cline-any cline-neutral">&nbsp;</span>
725
+ <span class="cline-any cline-no">&nbsp;</span>
726
+ <span class="cline-any cline-neutral">&nbsp;</span>
727
+ <span class="cline-any cline-neutral">&nbsp;</span>
728
+ <span class="cline-any cline-neutral">&nbsp;</span>
729
+ <span class="cline-any cline-neutral">&nbsp;</span>
730
+ <span class="cline-any cline-neutral">&nbsp;</span>
731
+ <span class="cline-any cline-neutral">&nbsp;</span>
732
+ <span class="cline-any cline-neutral">&nbsp;</span>
733
+ <span class="cline-any cline-neutral">&nbsp;</span>
734
+ <span class="cline-any cline-neutral">&nbsp;</span>
735
+ <span class="cline-any cline-neutral">&nbsp;</span>
736
+ <span class="cline-any cline-neutral">&nbsp;</span>
737
+ <span class="cline-any cline-neutral">&nbsp;</span>
738
+ <span class="cline-any cline-neutral">&nbsp;</span>
739
+ <span class="cline-any cline-neutral">&nbsp;</span>
740
+ <span class="cline-any cline-neutral">&nbsp;</span>
741
+ <span class="cline-any cline-neutral">&nbsp;</span>
742
+ <span class="cline-any cline-neutral">&nbsp;</span>
743
+ <span class="cline-any cline-neutral">&nbsp;</span>
744
+ <span class="cline-any cline-neutral">&nbsp;</span>
745
+ <span class="cline-any cline-neutral">&nbsp;</span>
746
+ <span class="cline-any cline-neutral">&nbsp;</span>
747
+ <span class="cline-any cline-neutral">&nbsp;</span>
748
+ <span class="cline-any cline-neutral">&nbsp;</span>
749
+ <span class="cline-any cline-yes">1x</span>
750
+ <span class="cline-any cline-yes">1x</span>
751
+ <span class="cline-any cline-neutral">&nbsp;</span>
752
+ <span class="cline-any cline-neutral">&nbsp;</span>
753
+ <span class="cline-any cline-neutral">&nbsp;</span>
754
+ <span class="cline-any cline-neutral">&nbsp;</span>
755
+ <span class="cline-any cline-neutral">&nbsp;</span>
756
+ <span class="cline-any cline-neutral">&nbsp;</span>
757
+ <span class="cline-any cline-neutral">&nbsp;</span>
758
+ <span class="cline-any cline-neutral">&nbsp;</span>
759
+ <span class="cline-any cline-neutral">&nbsp;</span>
760
+ <span class="cline-any cline-neutral">&nbsp;</span>
761
+ <span class="cline-any cline-yes">12x</span>
762
+ <span class="cline-any cline-yes">2x</span>
763
+ <span class="cline-any cline-neutral">&nbsp;</span>
764
+ <span class="cline-any cline-yes">12x</span>
765
+ <span class="cline-any cline-neutral">&nbsp;</span>
766
+ <span class="cline-any cline-neutral">&nbsp;</span>
767
+ <span class="cline-any cline-neutral">&nbsp;</span>
768
+ <span class="cline-any cline-neutral">&nbsp;</span>
769
+ <span class="cline-any cline-neutral">&nbsp;</span>
770
+ <span class="cline-any cline-neutral">&nbsp;</span>
771
+ <span class="cline-any cline-neutral">&nbsp;</span>
772
+ <span class="cline-any cline-neutral">&nbsp;</span>
773
+ <span class="cline-any cline-neutral">&nbsp;</span>
774
+ <span class="cline-any cline-neutral">&nbsp;</span>
775
+ <span class="cline-any cline-yes">6x</span>
776
+ <span class="cline-any cline-neutral">&nbsp;</span>
777
+ <span class="cline-any cline-no">&nbsp;</span>
778
+ <span class="cline-any cline-neutral">&nbsp;</span>
779
+ <span class="cline-any cline-neutral">&nbsp;</span>
780
+ <span class="cline-any cline-neutral">&nbsp;</span>
781
+ <span class="cline-any cline-neutral">&nbsp;</span>
782
+ <span class="cline-any cline-yes">12x</span>
783
+ <span class="cline-any cline-neutral">&nbsp;</span>
784
+ <span class="cline-any cline-neutral">&nbsp;</span>
785
+ <span class="cline-any cline-neutral">&nbsp;</span>
786
+ <span class="cline-any cline-yes">2x</span>
787
+ <span class="cline-any cline-yes">2x</span>
788
+ <span class="cline-any cline-yes">2x</span>
789
+ <span class="cline-any cline-yes">2x</span>
790
+ <span class="cline-any cline-neutral">&nbsp;</span>
791
+ <span class="cline-any cline-yes">2x</span>
792
+ <span class="cline-any cline-yes">6x</span>
793
+ <span class="cline-any cline-no">&nbsp;</span>
794
+ <span class="cline-any cline-yes">2x</span>
795
+ <span class="cline-any cline-neutral">&nbsp;</span>
796
+ <span class="cline-any cline-yes">2x</span>
797
+ <span class="cline-any cline-yes">2x</span>
798
+ <span class="cline-any cline-yes">2x</span>
799
+ <span class="cline-any cline-neutral">&nbsp;</span>
800
+ <span class="cline-any cline-neutral">&nbsp;</span>
801
+ <span class="cline-any cline-neutral">&nbsp;</span>
802
+ <span class="cline-any cline-neutral">&nbsp;</span>
803
+ <span class="cline-any cline-neutral">&nbsp;</span>
804
+ <span class="cline-any cline-yes">5x</span>
805
+ <span class="cline-any cline-yes">5x</span>
806
+ <span class="cline-any cline-yes">5x</span>
807
+ <span class="cline-any cline-yes">5x</span>
808
+ <span class="cline-any cline-neutral">&nbsp;</span>
809
+ <span class="cline-any cline-yes">5x</span>
810
+ <span class="cline-any cline-yes">4x</span>
811
+ <span class="cline-any cline-yes">1x</span>
812
+ <span class="cline-any cline-yes">1x</span>
813
+ <span class="cline-any cline-no">&nbsp;</span>
814
+ <span class="cline-any cline-no">&nbsp;</span>
815
+ <span class="cline-any cline-no">&nbsp;</span>
816
+ <span class="cline-any cline-no">&nbsp;</span>
817
+ <span class="cline-any cline-neutral">&nbsp;</span>
818
+ <span class="cline-any cline-neutral">&nbsp;</span>
819
+ <span class="cline-any cline-neutral">&nbsp;</span>
820
+ <span class="cline-any cline-yes">5x</span>
821
+ <span class="cline-any cline-yes">4x</span>
822
+ <span class="cline-any cline-yes">2x</span>
823
+ <span class="cline-any cline-neutral">&nbsp;</span>
824
+ <span class="cline-any cline-yes">4x</span>
825
+ <span class="cline-any cline-yes">4x</span>
826
+ <span class="cline-any cline-no">&nbsp;</span>
827
+ <span class="cline-any cline-neutral">&nbsp;</span>
828
+ <span class="cline-any cline-neutral">&nbsp;</span>
829
+ <span class="cline-any cline-neutral">&nbsp;</span>
830
+ <span class="cline-any cline-neutral">&nbsp;</span>
831
+ <span class="cline-any cline-neutral">&nbsp;</span>
832
+ <span class="cline-any cline-neutral">&nbsp;</span>
833
+ <span class="cline-any cline-neutral">&nbsp;</span>
834
+ <span class="cline-any cline-neutral">&nbsp;</span>
835
+ <span class="cline-any cline-neutral">&nbsp;</span>
836
+ <span class="cline-any cline-neutral">&nbsp;</span>
837
+ <span class="cline-any cline-neutral">&nbsp;</span>
838
+ <span class="cline-any cline-neutral">&nbsp;</span>
839
+ <span class="cline-any cline-yes">6x</span>
840
+ <span class="cline-any cline-neutral">&nbsp;</span>
841
+ <span class="cline-any cline-yes">6x</span>
842
+ <span class="cline-any cline-neutral">&nbsp;</span>
843
+ <span class="cline-any cline-no">&nbsp;</span>
844
+ <span class="cline-any cline-neutral">&nbsp;</span>
845
+ <span class="cline-any cline-neutral">&nbsp;</span>
846
+ <span class="cline-any cline-neutral">&nbsp;</span>
847
+ <span class="cline-any cline-yes">6x</span>
848
+ <span class="cline-any cline-neutral">&nbsp;</span>
849
+ <span class="cline-any cline-yes">1x</span>
850
+ <span class="cline-any cline-yes">1x</span>
851
+ <span class="cline-any cline-yes">1x</span>
852
+ <span class="cline-any cline-yes">1x</span>
853
+ <span class="cline-any cline-neutral">&nbsp;</span>
854
+ <span class="cline-any cline-neutral">&nbsp;</span>
855
+ <span class="cline-any cline-neutral">&nbsp;</span>
856
+ <span class="cline-any cline-neutral">&nbsp;</span>
857
+ <span class="cline-any cline-neutral">&nbsp;</span>
858
+ <span class="cline-any cline-yes">1x</span>
859
+ <span class="cline-any cline-neutral">&nbsp;</span>
860
+ <span class="cline-any cline-neutral">&nbsp;</span>
861
+ <span class="cline-any cline-neutral">&nbsp;</span>
862
+ <span class="cline-any cline-neutral">&nbsp;</span>
863
+ <span class="cline-any cline-yes">1x</span>
864
+ <span class="cline-any cline-yes">1x</span>
865
+ <span class="cline-any cline-yes">1x</span>
866
+ <span class="cline-any cline-no">&nbsp;</span>
867
+ <span class="cline-any cline-neutral">&nbsp;</span>
868
+ <span class="cline-any cline-neutral">&nbsp;</span>
869
+ <span class="cline-any cline-neutral">&nbsp;</span>
870
+ <span class="cline-any cline-neutral">&nbsp;</span>
871
+ <span class="cline-any cline-neutral">&nbsp;</span>
872
+ <span class="cline-any cline-neutral">&nbsp;</span>
873
+ <span class="cline-any cline-neutral">&nbsp;</span>
874
+ <span class="cline-any cline-no">&nbsp;</span>
875
+ <span class="cline-any cline-no">&nbsp;</span>
876
+ <span class="cline-any cline-neutral">&nbsp;</span>
877
+ <span class="cline-any cline-neutral">&nbsp;</span>
878
+ <span class="cline-any cline-neutral">&nbsp;</span>
879
+ <span class="cline-any cline-neutral">&nbsp;</span>
880
+ <span class="cline-any cline-yes">1x</span>
881
+ <span class="cline-any cline-neutral">&nbsp;</span>
882
+ <span class="cline-any cline-neutral">&nbsp;</span>
883
+ <span class="cline-any cline-neutral">&nbsp;</span>
884
+ <span class="cline-any cline-yes">5x</span>
885
+ <span class="cline-any cline-neutral">&nbsp;</span>
886
+ <span class="cline-any cline-neutral">&nbsp;</span>
887
+ <span class="cline-any cline-neutral">&nbsp;</span>
888
+ <span class="cline-any cline-yes">5x</span>
889
+ <span class="cline-any cline-neutral">&nbsp;</span>
890
+ <span class="cline-any cline-neutral">&nbsp;</span>
891
+ <span class="cline-any cline-yes">5x</span>
892
+ <span class="cline-any cline-yes">5x</span>
893
+ <span class="cline-any cline-neutral">&nbsp;</span>
894
+ <span class="cline-any cline-yes">5x</span>
895
+ <span class="cline-any cline-neutral">&nbsp;</span>
896
+ <span class="cline-any cline-neutral">&nbsp;</span>
897
+ <span class="cline-any cline-yes">5x</span>
898
+ <span class="cline-any cline-neutral">&nbsp;</span>
899
+ <span class="cline-any cline-neutral">&nbsp;</span>
900
+ <span class="cline-any cline-neutral">&nbsp;</span>
901
+ <span class="cline-any cline-neutral">&nbsp;</span>
902
+ <span class="cline-any cline-neutral">&nbsp;</span>
903
+ <span class="cline-any cline-neutral">&nbsp;</span>
904
+ <span class="cline-any cline-neutral">&nbsp;</span>
905
+ <span class="cline-any cline-neutral">&nbsp;</span>
906
+ <span class="cline-any cline-yes">5x</span>
907
+ <span class="cline-any cline-yes">5x</span>
908
+ <span class="cline-any cline-yes">5x</span>
909
+ <span class="cline-any cline-yes">13x</span>
910
+ <span class="cline-any cline-yes">5x</span>
911
+ <span class="cline-any cline-yes">5x</span>
912
+ <span class="cline-any cline-yes">5x</span>
913
+ <span class="cline-any cline-yes">5x</span>
914
+ <span class="cline-any cline-yes">5x</span>
915
+ <span class="cline-any cline-neutral">&nbsp;</span>
916
+ <span class="cline-any cline-neutral">&nbsp;</span>
917
+ <span class="cline-any cline-neutral">&nbsp;</span>
918
+ <span class="cline-any cline-neutral">&nbsp;</span>
919
+ <span class="cline-any cline-yes">5x</span>
920
+ <span class="cline-any cline-yes">6x</span>
921
+ <span class="cline-any cline-no">&nbsp;</span>
922
+ <span class="cline-any cline-neutral">&nbsp;</span>
923
+ <span class="cline-any cline-no">&nbsp;</span>
924
+ <span class="cline-any cline-no">&nbsp;</span>
925
+ <span class="cline-any cline-no">&nbsp;</span>
926
+ <span class="cline-any cline-neutral">&nbsp;</span>
927
+ <span class="cline-any cline-neutral">&nbsp;</span>
928
+ <span class="cline-any cline-neutral">&nbsp;</span>
929
+ <span class="cline-any cline-neutral">&nbsp;</span>
930
+ <span class="cline-any cline-neutral">&nbsp;</span>
931
+ <span class="cline-any cline-yes">5x</span>
932
+ <span class="cline-any cline-yes">1x</span>
933
+ <span class="cline-any cline-no">&nbsp;</span>
934
+ <span class="cline-any cline-no">&nbsp;</span>
935
+ <span class="cline-any cline-neutral">&nbsp;</span>
936
+ <span class="cline-any cline-neutral">&nbsp;</span>
937
+ <span class="cline-any cline-neutral">&nbsp;</span>
938
+ <span class="cline-any cline-neutral">&nbsp;</span>
939
+ <span class="cline-any cline-yes">5x</span>
940
+ <span class="cline-any cline-neutral">&nbsp;</span>
941
+ <span class="cline-any cline-yes">4x</span>
942
+ <span class="cline-any cline-yes">4x</span>
943
+ <span class="cline-any cline-neutral">&nbsp;</span>
944
+ <span class="cline-any cline-neutral">&nbsp;</span>
945
+ <span class="cline-any cline-yes">2x</span>
946
+ <span class="cline-any cline-yes">2x</span>
947
+ <span class="cline-any cline-yes">2x</span>
948
+ <span class="cline-any cline-yes">2x</span>
949
+ <span class="cline-any cline-yes">2x</span>
950
+ <span class="cline-any cline-yes">2x</span>
951
+ <span class="cline-any cline-neutral">&nbsp;</span>
952
+ <span class="cline-any cline-yes">2x</span>
953
+ <span class="cline-any cline-yes">2x</span>
954
+ <span class="cline-any cline-neutral">&nbsp;</span>
955
+ <span class="cline-any cline-neutral">&nbsp;</span>
956
+ <span class="cline-any cline-neutral">&nbsp;</span>
957
+ <span class="cline-any cline-yes">2x</span>
958
+ <span class="cline-any cline-yes">2x</span>
959
+ <span class="cline-any cline-yes">2x</span>
960
+ <span class="cline-any cline-yes">2x</span>
961
+ <span class="cline-any cline-yes">2x</span>
962
+ <span class="cline-any cline-yes">2x</span>
963
+ <span class="cline-any cline-neutral">&nbsp;</span>
964
+ <span class="cline-any cline-neutral">&nbsp;</span>
965
+ <span class="cline-any cline-neutral">&nbsp;</span>
966
+ <span class="cline-any cline-neutral">&nbsp;</span>
967
+ <span class="cline-any cline-yes">4x</span>
968
+ <span class="cline-any cline-yes">4x</span>
969
+ <span class="cline-any cline-yes">4x</span>
970
+ <span class="cline-any cline-yes">4x</span>
971
+ <span class="cline-any cline-yes">4x</span>
972
+ <span class="cline-any cline-neutral">&nbsp;</span>
973
+ <span class="cline-any cline-neutral">&nbsp;</span>
974
+ <span class="cline-any cline-neutral">&nbsp;</span>
975
+ <span class="cline-any cline-neutral">&nbsp;</span>
976
+ <span class="cline-any cline-neutral">&nbsp;</span>
977
+ <span class="cline-any cline-neutral">&nbsp;</span>
978
+ <span class="cline-any cline-neutral">&nbsp;</span>
979
+ <span class="cline-any cline-neutral">&nbsp;</span>
980
+ <span class="cline-any cline-neutral">&nbsp;</span>
981
+ <span class="cline-any cline-yes">4x</span>
982
+ <span class="cline-any cline-no">&nbsp;</span>
983
+ <span class="cline-any cline-neutral">&nbsp;</span>
984
+ <span class="cline-any cline-yes">4x</span>
985
+ <span class="cline-any cline-neutral">&nbsp;</span>
986
+ <span class="cline-any cline-neutral">&nbsp;</span>
987
+ <span class="cline-any cline-no">&nbsp;</span>
988
+ <span class="cline-any cline-neutral">&nbsp;</span>
989
+ <span class="cline-any cline-neutral">&nbsp;</span>
990
+ <span class="cline-any cline-yes">1x</span>
991
+ <span class="cline-any cline-yes">1x</span>
992
+ <span class="cline-any cline-neutral">&nbsp;</span>
993
+ <span class="cline-any cline-neutral">&nbsp;</span>
994
+ <span class="cline-any cline-no">&nbsp;</span>
995
+ <span class="cline-any cline-no">&nbsp;</span>
996
+ <span class="cline-any cline-neutral">&nbsp;</span>
997
+ <span class="cline-any cline-no">&nbsp;</span>
998
+ <span class="cline-any cline-no">&nbsp;</span>
999
+ <span class="cline-any cline-neutral">&nbsp;</span>
1000
+ <span class="cline-any cline-no">&nbsp;</span>
1001
+ <span class="cline-any cline-neutral">&nbsp;</span>
1002
+ <span class="cline-any cline-neutral">&nbsp;</span>
1003
+ <span class="cline-any cline-no">&nbsp;</span>
1004
+ <span class="cline-any cline-neutral">&nbsp;</span>
1005
+ <span class="cline-any cline-neutral">&nbsp;</span>
1006
+ <span class="cline-any cline-no">&nbsp;</span>
1007
+ <span class="cline-any cline-no">&nbsp;</span>
1008
+ <span class="cline-any cline-no">&nbsp;</span>
1009
+ <span class="cline-any cline-no">&nbsp;</span>
1010
+ <span class="cline-any cline-neutral">&nbsp;</span>
1011
+ <span class="cline-any cline-neutral">&nbsp;</span>
1012
+ <span class="cline-any cline-neutral">&nbsp;</span>
1013
+ <span class="cline-any cline-no">&nbsp;</span>
1014
+ <span class="cline-any cline-no">&nbsp;</span>
1015
+ <span class="cline-any cline-no">&nbsp;</span>
1016
+ <span class="cline-any cline-neutral">&nbsp;</span>
1017
+ <span class="cline-any cline-neutral">&nbsp;</span>
1018
+ <span class="cline-any cline-neutral">&nbsp;</span>
1019
+ <span class="cline-any cline-neutral">&nbsp;</span>
1020
+ <span class="cline-any cline-no">&nbsp;</span>
1021
+ <span class="cline-any cline-no">&nbsp;</span>
1022
+ <span class="cline-any cline-no">&nbsp;</span>
1023
+ <span class="cline-any cline-neutral">&nbsp;</span>
1024
+ <span class="cline-any cline-neutral">&nbsp;</span>
1025
+ <span class="cline-any cline-neutral">&nbsp;</span>
1026
+ <span class="cline-any cline-neutral">&nbsp;</span>
1027
+ <span class="cline-any cline-no">&nbsp;</span>
1028
+ <span class="cline-any cline-no">&nbsp;</span>
1029
+ <span class="cline-any cline-no">&nbsp;</span>
1030
+ <span class="cline-any cline-no">&nbsp;</span>
1031
+ <span class="cline-any cline-neutral">&nbsp;</span>
1032
+ <span class="cline-any cline-no">&nbsp;</span>
1033
+ <span class="cline-any cline-neutral">&nbsp;</span>
1034
+ <span class="cline-any cline-neutral">&nbsp;</span>
1035
+ <span class="cline-any cline-neutral">&nbsp;</span>
1036
+ <span class="cline-any cline-neutral">&nbsp;</span>
1037
+ <span class="cline-any cline-no">&nbsp;</span>
1038
+ <span class="cline-any cline-no">&nbsp;</span>
1039
+ <span class="cline-any cline-no">&nbsp;</span>
1040
+ <span class="cline-any cline-no">&nbsp;</span>
1041
+ <span class="cline-any cline-no">&nbsp;</span>
1042
+ <span class="cline-any cline-neutral">&nbsp;</span>
1043
+ <span class="cline-any cline-neutral">&nbsp;</span>
1044
+ <span class="cline-any cline-neutral">&nbsp;</span>
1045
+ <span class="cline-any cline-neutral">&nbsp;</span>
1046
+ <span class="cline-any cline-neutral">&nbsp;</span>
1047
+ <span class="cline-any cline-yes">6x</span>
1048
+ <span class="cline-any cline-neutral">&nbsp;</span>
1049
+ <span class="cline-any cline-neutral">&nbsp;</span>
1050
+ <span class="cline-any cline-yes">6x</span>
1051
+ <span class="cline-any cline-yes">6x</span>
1052
+ <span class="cline-any cline-yes">6x</span>
1053
+ <span class="cline-any cline-neutral">&nbsp;</span>
1054
+ <span class="cline-any cline-neutral">&nbsp;</span>
1055
+ <span class="cline-any cline-neutral">&nbsp;</span>
1056
+ <span class="cline-any cline-neutral">&nbsp;</span>
1057
+ <span class="cline-any cline-neutral">&nbsp;</span>
1058
+ <span class="cline-any cline-neutral">&nbsp;</span>
1059
+ <span class="cline-any cline-neutral">&nbsp;</span>
1060
+ <span class="cline-any cline-yes">6x</span>
1061
+ <span class="cline-any cline-neutral">&nbsp;</span>
1062
+ <span class="cline-any cline-neutral">&nbsp;</span>
1063
+ <span class="cline-any cline-neutral">&nbsp;</span>
1064
+ <span class="cline-any cline-neutral">&nbsp;</span>
1065
+ <span class="cline-any cline-yes">5x</span>
1066
+ <span class="cline-any cline-yes">5x</span>
1067
+ <span class="cline-any cline-yes">5x</span>
1068
+ <span class="cline-any cline-yes">5x</span>
1069
+ <span class="cline-any cline-neutral">&nbsp;</span>
1070
+ <span class="cline-any cline-yes">5x</span>
1071
+ <span class="cline-any cline-neutral">&nbsp;</span>
1072
+ <span class="cline-any cline-yes">5x</span>
1073
+ <span class="cline-any cline-neutral">&nbsp;</span>
1074
+ <span class="cline-any cline-neutral">&nbsp;</span></td><td class="text"><pre class="prettyprint lang-js">/**
1075
+ * Ink-based skill runner with real-time progress display.
1076
+ *
1077
+ * While skills run, the dynamic Ink area shows running skills and active files.
1078
+ * After Ink unmounts, the full per-skill + per-file breakdown is printed to
1079
+ * stderr, followed by the normal findings report.
1080
+ *
1081
+ * UI updates are batched via setImmediate() to prevent rapid consecutive
1082
+ * rerender() calls from producing duplicate output lines.
1083
+ *
1084
+ * Reporter spec: specs/reporters.md
1085
+ * Terminal output design guide: specs/terminal-output.md
1086
+ */
1087
+ &nbsp;
1088
+ import React, { useState, useEffect } from 'react';
1089
+ import { render, Box, Text, Static } from 'ink';
1090
+ import chalk from 'chalk';
1091
+ import {
1092
+ composeTasksWithFailFast,
1093
+ runComposedSkillTasks,
1094
+ type SkillTaskOptions,
1095
+ type SkillTaskResult,
1096
+ type RunTasksOptions,
1097
+ type SkillProgressCallbacks,
1098
+ type SkillState,
1099
+ type FileState,
1100
+ } from './tasks.js';
1101
+ import { formatDuration, formatCost, truncate, countBySeverity, formatSeverityDot, pluralize, totalAuxiliaryCost } from './formatters.js';
1102
+ import { Semaphore } from '../../utils/index.js';
1103
+ import { Verbosity } from './verbosity.js';
1104
+ import { ICON_CHECK, ICON_SKIPPED, ICON_PENDING, ICON_ERROR, SPINNER_FRAMES } from './icons.js';
1105
+ import figures from 'figures';
1106
+ import type { Finding, SkillReport } from '../../types/index.js';
1107
+ import { ProviderFailureCircuitBreaker } from '../../sdk/circuit-breaker.js';
1108
+ import { findingAppliesToFile } from '../../sdk/report-files.js';
1109
+ &nbsp;
1110
+ interface SkillRunnerProps {
1111
+ skills: SkillState[];
1112
+ warnings: string[];
1113
+ interrupted: boolean;
1114
+ failFastTriggered: boolean;
1115
+ }
1116
+ &nbsp;
1117
+ function <span class="fstat-no" title="function not covered" >Spinner(): React.ReactElement {</span>
1118
+ const [frame, setFrame<span class="cstat-no" title="statement not covered" >] = useState(0);</span>
1119
+ &nbsp;
1120
+ <span class="cstat-no" title="statement not covered" > useEffect(<span class="fstat-no" title="function not covered" >() =&gt; {</span></span>
1121
+ const timer = <span class="cstat-no" title="statement not covered" >setInterval(<span class="fstat-no" title="function not covered" >() =&gt; {</span></span>
1122
+ <span class="cstat-no" title="statement not covered" > setFrame(<span class="fstat-no" title="function not covered" >(<span class="cstat-no" title="statement not covered" >f</span>) =&gt; (f + 1) % SPINNER_FRAMES.length)</span>;</span>
1123
+ }, 80);
1124
+ <span class="cstat-no" title="statement not covered" > return <span class="fstat-no" title="function not covered" >() =&gt; <span class="cstat-no" title="statement not covered" >c</span>learInterval(timer);</span></span>
1125
+ }, []);
1126
+ &nbsp;
1127
+ <span class="cstat-no" title="statement not covered" > return &lt;Text color="yellow"&gt;{SPINNER_FRAMES[frame]}&lt;/Text&gt;;</span>
1128
+ }
1129
+ &nbsp;
1130
+ function <span class="fstat-no" title="function not covered" >FileProgress({</span> file }: { file: FileState }): React.ReactElement {
1131
+ const <span class="cstat-no" title="statement not covered" >filename = truncate(file.filename, 50);</span>
1132
+ <span class="cstat-no" title="statement not covered" > return (</span>
1133
+ &lt;Box&gt;
1134
+ &lt;Spinner /&gt;
1135
+ &lt;Text&gt; {filename} [{file.currentHunk}/{file.totalHunks}]&lt;/Text&gt;
1136
+ &lt;/Box&gt;
1137
+ );
1138
+ }
1139
+ &nbsp;
1140
+ export function getSkillCostUSD(skill: SkillState): number | undefined {
1141
+ const hasFileUsage = skill.files.some((file) =&gt; file.usage !== undefined);
1142
+ const primaryCost = skill.usage?.costUSD
1143
+ ?? (hasFileUsage ? skill.files.reduce((sum, file) =&gt; sum + (file.usage?.costUSD ?? <span class="branch-1 cbranch-no" title="branch not covered" >0), 0</span>) : undefined);
1144
+ const auxiliaryCost = skill.auxiliaryUsage ? totalAuxiliaryCost(skill.auxiliaryUsage) : 0;
1145
+ &nbsp;
1146
+ if (primaryCost === undefined &amp;&amp; auxiliaryCost === 0) {
1147
+ return undefined;
1148
+ }
1149
+ &nbsp;
1150
+ return (primaryCost ?? <span class="branch-1 cbranch-no" title="branch not covered" >0) + a</span>uxiliaryCost;
1151
+ }
1152
+ &nbsp;
1153
+ function <span class="fstat-no" title="function not covered" >RunningSkill({</span> skill }: { skill: SkillState }): React.ReactElement {
1154
+ const activeFiles = <span class="cstat-no" title="statement not covered" >skill.files.filter(<span class="fstat-no" title="function not covered" >(f</span>) =&gt; <span class="cstat-no" title="statement not covered" >f.status === 'running')</span>;</span>
1155
+ const doneCount = <span class="cstat-no" title="statement not covered" >skill.files.filter(<span class="fstat-no" title="function not covered" >(f</span>) =&gt; <span class="cstat-no" title="statement not covered" >f.status === 'done' || f.status === 'skipped')</span>.length;</span>
1156
+ const totalCount = <span class="cstat-no" title="statement not covered" >skill.files.length;</span>
1157
+ const findingCount = <span class="cstat-no" title="statement not covered" >skill.files.reduce(<span class="fstat-no" title="function not covered" >(s</span>um, f) =&gt; <span class="cstat-no" title="statement not covered" >sum + f.findings.length, 0</span>);</span>
1158
+ const cost = <span class="cstat-no" title="statement not covered" >getSkillCostUSD(skill);</span>
1159
+ &nbsp;
1160
+ <span class="cstat-no" title="statement not covered" > return (</span>
1161
+ &lt;Box flexDirection="column"&gt;
1162
+ &lt;Box&gt;
1163
+ &lt;Spinner /&gt;
1164
+ &lt;Text&gt; {skill.displayName}&lt;/Text&gt;
1165
+ {totalCount &gt; 0 &amp;&amp; &lt;Text dimColor&gt; [{doneCount}/{totalCount} files]&lt;/Text&gt;}
1166
+ {findingCount &gt; 0 &amp;&amp; &lt;Text&gt; {findingCount} {findingCount === 1 ? 'finding' : 'findings'}&lt;/Text&gt;}
1167
+ {cost !== undefined &amp;&amp; cost &gt; 0 &amp;&amp; &lt;Text dimColor&gt; {formatCost(cost)}&lt;/Text&gt;}
1168
+ &lt;/Box&gt;
1169
+ {activeFiles.map(<span class="fstat-no" title="function not covered" >(f</span>ile) =&gt; (
1170
+ <span class="cstat-no" title="statement not covered" > &lt;Box key={file.filename} marginLeft={2}&gt;</span>
1171
+ &lt;FileProgress file={file} /&gt;
1172
+ &lt;/Box&gt;
1173
+ ))}
1174
+ &lt;/Box&gt;
1175
+ );
1176
+ }
1177
+ &nbsp;
1178
+ function <span class="fstat-no" title="function not covered" >CompletedSkill({</span> skill }: { skill: SkillState }): React.ReactElement {
1179
+ <span class="cstat-no" title="statement not covered" > if (skill.status === 'skipped') {</span>
1180
+ <span class="cstat-no" title="statement not covered" > return (</span>
1181
+ &lt;Text&gt;
1182
+ &lt;Text color="yellow"&gt;{ICON_SKIPPED}&lt;/Text&gt; {skill.displayName} &lt;Text dimColor&gt;[skipped]&lt;/Text&gt;
1183
+ &lt;/Text&gt;
1184
+ );
1185
+ }
1186
+ &nbsp;
1187
+ const findingCount = <span class="cstat-no" title="statement not covered" >skill.findings.length;</span>
1188
+ const cost = <span class="cstat-no" title="statement not covered" >getSkillCostUSD(skill);</span>
1189
+ const duration = <span class="cstat-no" title="statement not covered" >skill.durationMs ? formatDuration(skill.durationMs) : undefined;</span>
1190
+ &nbsp;
1191
+ <span class="cstat-no" title="statement not covered" > if (skill.status === 'error') {</span>
1192
+ <span class="cstat-no" title="statement not covered" > return (</span>
1193
+ &lt;Text&gt;
1194
+ &lt;Text color="red"&gt;{ICON_ERROR}&lt;/Text&gt; {skill.displayName}
1195
+ {duration &amp;&amp; &lt;Text dimColor&gt; [{duration}]&lt;/Text&gt;}
1196
+ &lt;/Text&gt;
1197
+ );
1198
+ }
1199
+ &nbsp;
1200
+ <span class="cstat-no" title="statement not covered" > return (</span>
1201
+ &lt;Text&gt;
1202
+ &lt;Text color="green"&gt;{ICON_CHECK}&lt;/Text&gt; {skill.displayName}
1203
+ {duration &amp;&amp; &lt;Text dimColor&gt; [{duration}]&lt;/Text&gt;}
1204
+ {findingCount &gt; 0 &amp;&amp; &lt;Text&gt; {findingCount} {findingCount === 1 ? 'finding' : 'findings'}&lt;/Text&gt;}
1205
+ {cost !== undefined &amp;&amp; cost &gt; 0 &amp;&amp; &lt;Text dimColor&gt; {formatCost(cost)}&lt;/Text&gt;}
1206
+ &lt;/Text&gt;
1207
+ );
1208
+ }
1209
+ &nbsp;
1210
+ function <span class="fstat-no" title="function not covered" >SkillRunner({</span> skills, warnings, interrupted, failFastTriggered }: SkillRunnerProps): React.ReactElement {
1211
+ const completed = <span class="cstat-no" title="statement not covered" >skills.filter(<span class="fstat-no" title="function not covered" >(s</span>) =&gt; <span class="cstat-no" title="statement not covered" >s.status === 'done' || s.status === 'skipped' || s.status === 'error')</span>;</span>
1212
+ const running = <span class="cstat-no" title="statement not covered" >skills.filter(<span class="fstat-no" title="function not covered" >(s</span>) =&gt; <span class="cstat-no" title="statement not covered" >s.status === 'running')</span>;</span>
1213
+ const pending = <span class="cstat-no" title="statement not covered" >skills.filter(<span class="fstat-no" title="function not covered" >(s</span>) =&gt; <span class="cstat-no" title="statement not covered" >s.status === 'pending')</span>;</span>
1214
+ &nbsp;
1215
+ <span class="cstat-no" title="statement not covered" > return (</span>
1216
+ &lt;Box flexDirection="column"&gt;
1217
+ &lt;Static items={warnings}&gt;
1218
+ {<span class="fstat-no" title="function not covered" >(w</span>arning, index) =&gt; (
1219
+ <span class="cstat-no" title="statement not covered" > &lt;Text key={index}&gt;{warning}&lt;/Text&gt;</span>
1220
+ )}
1221
+ &lt;/Static&gt;
1222
+ {completed.map(<span class="fstat-no" title="function not covered" >(s</span>kill) =&gt; (
1223
+ <span class="cstat-no" title="statement not covered" > &lt;CompletedSkill key={skill.name} skill={skill} /&gt;</span>
1224
+ ))}
1225
+ {running.map(<span class="fstat-no" title="function not covered" >(s</span>kill) =&gt; (
1226
+ <span class="cstat-no" title="statement not covered" > &lt;RunningSkill key={skill.name} skill={skill} /&gt;</span>
1227
+ ))}
1228
+ {pending.map(<span class="fstat-no" title="function not covered" >(s</span>kill) =&gt; (
1229
+ <span class="cstat-no" title="statement not covered" > &lt;Text key={skill.name} dimColor&gt;</span>
1230
+ {ICON_PENDING} {skill.displayName}
1231
+ &lt;/Text&gt;
1232
+ ))}
1233
+ {failFastTriggered &amp;&amp; (
1234
+ &lt;Text color="yellow" dimColor&gt;
1235
+ {figures.warning} Stopping {'\u2014'} finding detected (--fail-fast)
1236
+ &lt;/Text&gt;
1237
+ )}
1238
+ {interrupted &amp;&amp; !failFastTriggered &amp;&amp; (
1239
+ &lt;Text color="yellow" dimColor&gt;
1240
+ {figures.warning} Interrupted, finishing up... (press Ctrl+C again to force exit)
1241
+ &lt;/Text&gt;
1242
+ )}
1243
+ &lt;/Box&gt;
1244
+ );
1245
+ }
1246
+ &nbsp;
1247
+ /** Create a terminal skill state for skills that were skipped or errored before starting. */
1248
+ function makeTerminalSkillState(
1249
+ tasks: SkillTaskOptions[],
1250
+ name: string,
1251
+ overrides: Partial&lt;SkillState&gt;
1252
+ ): SkillState {
1253
+ const task = tasks.find((t) =&gt; t.name === name);
1254
+ return {
1255
+ name,
1256
+ displayName: task?.displayName ?? <span class="branch-1 cbranch-no" title="branch not covered" >name,</span>
1257
+ status: 'pending',
1258
+ files: [],
1259
+ findings: [],
1260
+ ...overrides,
1261
+ };
1262
+ }
1263
+ &nbsp;
1264
+ /** No-op callbacks for quiet mode. */
1265
+ const noop = (): void =&gt; {
1266
+ return;
1267
+ };
1268
+ const noopCallbacks: SkillProgressCallbacks = {
1269
+ onSkillStart: noop,
1270
+ onSkillUpdate: noop,
1271
+ onFileUpdate: noop,
1272
+ onChunkComplete: noop,
1273
+ onSkillComplete: noop,
1274
+ onSkillSkipped: noop,
1275
+ onSkillError: noop,
1276
+ };
1277
+ &nbsp;
1278
+ function syncFileFindingsWithFinalReport(files: FileState[], findings: Finding[]): FileState[] {
1279
+ return files.map((file) =&gt; ({
1280
+ ...file,
1281
+ findings: findings.filter(<span class="fstat-no" title="function not covered" >(<span class="cstat-no" title="statement not covered" >f</span>inding) =&gt; findingAppliesToFile(finding, file.filename))</span>,
1282
+ }));
1283
+ }
1284
+ &nbsp;
1285
+ /** Severity levels in display order. */
1286
+ const SEVERITY_LEVELS = ['high', 'medium', 'low'] as const;
1287
+ &nbsp;
1288
+ /** Print the per-file line within a skill summary. */
1289
+ function printFileSummary(file: FileState): void {
1290
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (file.status === 'done') {
1291
+ const filename = truncate(file.filename, 50);
1292
+ const counts = countBySeverity(file.findings);
1293
+ let line = ` ${chalk.green(ICON_CHECK)} ${filename} ${chalk.dim(`[${file.totalHunks}/${file.totalHunks}]`)}`;
1294
+ &nbsp;
1295
+ const severityParts = SEVERITY_LEVELS
1296
+ .filter((s) =&gt; counts[s] &gt; 0)
1297
+ .map(<span class="fstat-no" title="function not covered" >(s</span>) =&gt; <span class="cstat-no" title="statement not covered" >`${formatSeverityDot(s)} ${counts[s]}`)</span>;
1298
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (severityParts.length &gt; 0) <span class="cstat-no" title="statement not covered" >line += ` ${severityParts.join(' ')}`;</span>
1299
+ &nbsp;
1300
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (file.durationMs !== undefined) <span class="cstat-no" title="statement not covered" >line += chalk.dim(` ${formatDuration(file.durationMs)}`);</span>
1301
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (file.usage !== undefined) <span class="cstat-no" title="statement not covered" >line += chalk.dim(` ${formatCost(file.usage.costUSD)}`);</span>
1302
+ process.stderr.write(`${line}\n`);
1303
+ }
1304
+ }
1305
+ &nbsp;
1306
+ /** Print the full skill + file breakdown to stderr after Ink unmounts. */
1307
+ function printSkillSummary(skillStates: SkillState[]): void {
1308
+ for (const skill of skillStates) {
1309
+ const duration = skill.durationMs ? chalk.dim(` [${formatDuration(skill.durationMs)}]`) : '';
1310
+ const cost = getSkillCostUSD(skill);
1311
+ const costText = cost !== undefined &amp;&amp; cost &gt; 0 ? chalk.dim(` ${formatCost(cost)}`) : '';
1312
+ &nbsp;
1313
+ if (skill.status === 'done') {
1314
+ process.stderr.write(`${chalk.green(ICON_CHECK)} ${skill.displayName}${duration}${costText}\n`);
1315
+ } else if (skill.status === 'skipped') {
1316
+ process.stderr.write(`${chalk.yellow(ICON_SKIPPED)} ${skill.displayName} ${chalk.dim('[skipped]')}\n`);
1317
+ <span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="else path not taken" >E</span>} else if (skill.status === 'error') {</span>
1318
+ <span class="cstat-no" title="statement not covered" > process.stderr.write(`${chalk.red(ICON_ERROR)} ${skill.displayName}${duration}\n`);</span>
1319
+ <span class="cstat-no" title="statement not covered" > if (skill.error) {</span>
1320
+ <span class="cstat-no" title="statement not covered" > process.stderr.write(`${chalk.red(` Error: ${skill.error}`)}\n`);</span>
1321
+ }
1322
+ }
1323
+ &nbsp;
1324
+ if (skill.status === 'done' || skill.status === 'error') {
1325
+ for (const file of skill.files) {
1326
+ printFileSummary(file);
1327
+ }
1328
+ const skippedCount = skill.files.filter((f) =&gt; f.status === 'skipped').length;
1329
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (skippedCount &gt; 0) {
1330
+ <span class="cstat-no" title="statement not covered" > process.stderr.write(` ${chalk.dim(`${skippedCount} ${pluralize(skippedCount, 'file')} skipped`)}\n`);</span>
1331
+ }
1332
+ }
1333
+ }
1334
+ }
1335
+ &nbsp;
1336
+ /**
1337
+ * Run skill tasks with Ink-based real-time progress display.
1338
+ */
1339
+ export async function runSkillTasksWithInk(
1340
+ tasks: SkillTaskOptions[],
1341
+ options: RunTasksOptions
1342
+ ): Promise&lt;SkillTaskResult[]&gt; {
1343
+ const { verbosity, concurrency, failFastController, onSkillComplete: streamHook, onChunkComplete } = options;
1344
+ &nbsp;
1345
+ const fireStreamHook = streamHook
1346
+ ? <span class="fstat-no" title="function not covered" ><span class="branch-0 cbranch-no" title="branch not covered" >(r</span>eport: SkillReport) =&gt; {</span>
1347
+ <span class="cstat-no" title="statement not covered" > try { <span class="cstat-no" title="statement not covered" >streamHook(report); }</span> catch { /* streaming hook must not break the run */ }</span>
1348
+ }
1349
+ : undefined;
1350
+ &nbsp;
1351
+ if (tasks.length === 0 || verbosity === Verbosity.Quiet) {
1352
+ // No tasks or quiet mode - run without UI using global semaphore.
1353
+ const semaphore = new Semaphore(concurrency);
1354
+ const circuitAbortController = new AbortController();
1355
+ const circuitBreaker = new ProviderFailureCircuitBreaker({ abortController: circuitAbortController });
1356
+ const composedTasks = composeTasksWithFailFast(
1357
+ tasks,
1358
+ failFastController,
1359
+ circuitBreaker,
1360
+ circuitAbortController,
1361
+ );
1362
+ const callbacks: SkillProgressCallbacks = {
1363
+ ...noopCallbacks,
1364
+ ...(fireStreamHook || failFastController
1365
+ ? {
1366
+ onSkillComplete: (name: string, report) =&gt; {
1367
+ noopCallbacks.onSkillComplete(name, report);
1368
+ fireStreamHook?.(report);
1369
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (failFastController &amp;&amp; report.findings.length &gt; 0) {
1370
+ <span class="cstat-no" title="statement not covered" > failFastController.abort();</span>
1371
+ }
1372
+ },
1373
+ }
1374
+ : <span class="branch-1 cbranch-no" title="branch not covered" >{}),</span>
1375
+ ...(onChunkComplete
1376
+ ? <span class="branch-0 cbranch-no" title="branch not covered" >{</span>
1377
+ onChunkComplete: <span class="fstat-no" title="function not covered" >(n</span>ame, chunk) =&gt; {
1378
+ <span class="cstat-no" title="statement not covered" > noopCallbacks.onChunkComplete?.(name, chunk);</span>
1379
+ <span class="cstat-no" title="statement not covered" > try { <span class="cstat-no" title="statement not covered" >onChunkComplete(name, chunk); }</span> catch { /* streaming hook must not break the run */ }</span>
1380
+ },
1381
+ }
1382
+ : {}),
1383
+ };
1384
+ return runComposedSkillTasks(composedTasks, callbacks, semaphore);
1385
+ }
1386
+ &nbsp;
1387
+ // Track skill states
1388
+ const skillStates: SkillState[] = [];
1389
+ &nbsp;
1390
+ // Warnings are rendered via Ink's Static component so they appear above the
1391
+ // dynamic spinner area without corrupting it.
1392
+ const warnings: string[] = [];
1393
+ &nbsp;
1394
+ // Track interrupt state for rendering in the Ink component
1395
+ let interrupted = false;
1396
+ let failFastTriggered = false;
1397
+ &nbsp;
1398
+ process.stderr.write(`${chalk.bold('SKILLS')}\n`);
1399
+ &nbsp;
1400
+ // Create Ink instance
1401
+ const { rerender, unmount, clear } = render(
1402
+ &lt;SkillRunner skills={skillStates} warnings={[]} interrupted={false} failFastTriggered={false} /&gt;,
1403
+ { stdout: process.stderr }
1404
+ );
1405
+ &nbsp;
1406
+ // Batch UI updates to prevent rapid consecutive rerenders that cause duplicate lines.
1407
+ // Without batching, multiple callbacks firing in quick succession (e.g., 5 files
1408
+ // starting simultaneously) trigger 5 immediate rerenders, which Ink cannot
1409
+ // process correctly, resulting in the same line appearing multiple times.
1410
+ let updatePending = false;
1411
+ let unmounted = false;
1412
+ const updateUI = () =&gt; {
1413
+ if (updatePending || unmounted) return;
1414
+ updatePending = true;
1415
+ setImmediate(() =&gt; {
1416
+ updatePending = false;
1417
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (unmounted) <span class="cstat-no" title="statement not covered" >return;</span>
1418
+ rerender(&lt;SkillRunner skills={[...skillStates]} warnings={[...warnings]} interrupted={interrupted} failFastTriggered={failFastTriggered} /&gt;);
1419
+ });
1420
+ };
1421
+ &nbsp;
1422
+ // Listen for abort signal to show interrupt message in the Ink UI
1423
+ const abortSignal = tasks[0]?.runnerOptions?.abortController?.signal;
1424
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (abortSignal &amp;&amp; <span class="branch-1 cbranch-no" title="branch not covered" >!abortSignal.aborted) {</span>
1425
+ <span class="cstat-no" title="statement not covered" > abortSignal.addEventListener('abort', <span class="fstat-no" title="function not covered" >() =&gt; {</span></span>
1426
+ // Only show interrupt message for user SIGINT, not fail-fast
1427
+ <span class="cstat-no" title="statement not covered" > if (!failFastController?.signal.aborted) {</span>
1428
+ <span class="cstat-no" title="statement not covered" > interrupted = true;</span>
1429
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1430
+ }
1431
+ }, { once: true });
1432
+ }
1433
+ &nbsp;
1434
+ // Show fail-fast message when triggered
1435
+ if (failFastController) {
1436
+ failFastController.signal.addEventListener('abort', <span class="fstat-no" title="function not covered" >() =&gt; {</span>
1437
+ <span class="cstat-no" title="statement not covered" > failFastTriggered = true;</span>
1438
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1439
+ }, { once: true });
1440
+ }
1441
+ &nbsp;
1442
+ // Callbacks to update state
1443
+ const callbacks: SkillProgressCallbacks = {
1444
+ onSkillStart: (skill) =&gt; {
1445
+ skillStates.push(skill);
1446
+ updateUI();
1447
+ },
1448
+ onSkillUpdate: (name, updates) =&gt; {
1449
+ const idx = skillStates.findIndex((s) =&gt; s.name === name);
1450
+ const existing = skillStates[idx];
1451
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (idx &gt;= 0 &amp;&amp; existing) {
1452
+ const next: SkillState = { ...existing, ...updates };
1453
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (updates.findings !== undefined) {
1454
+ next.files = syncFileFindingsWithFinalReport(next.files, updates.findings);
1455
+ }
1456
+ skillStates[idx] = next;
1457
+ updateUI();
1458
+ }
1459
+ },
1460
+ onFileUpdate: (skillName, filename, updates) =&gt; {
1461
+ const skill = skillStates.find((s) =&gt; s.name === skillName);
1462
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (skill) {
1463
+ const file = skill.files.find((f) =&gt; f.filename === filename);
1464
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (file) {
1465
+ Object.assign(file, updates);
1466
+ updateUI();
1467
+ }
1468
+ }
1469
+ },
1470
+ onSkillComplete: (name, report) =&gt; {
1471
+ fireStreamHook?.(report);
1472
+ const idx = skillStates.findIndex((s) =&gt; s.name === name);
1473
+ const existing = skillStates[idx];
1474
+ <span class="missing-if-branch" title="else path not taken" >E</span>if (idx &gt;= 0 &amp;&amp; existing) {
1475
+ skillStates[idx] = {
1476
+ ...existing,
1477
+ status: existing.status === 'error' || existing.status === 'skipped' ? existing.status : 'done',
1478
+ durationMs: report.durationMs,
1479
+ findings: report.findings,
1480
+ usage: report.usage,
1481
+ auxiliaryUsage: report.auxiliaryUsage,
1482
+ files: syncFileFindingsWithFinalReport(existing.files, report.findings),
1483
+ };
1484
+ }
1485
+ <span class="missing-if-branch" title="if path not taken" >I</span>if (failFastController &amp;&amp; report.findings.length &gt; 0) {
1486
+ <span class="cstat-no" title="statement not covered" > failFastController.abort();</span>
1487
+ }
1488
+ updateUI();
1489
+ },
1490
+ onChunkComplete: <span class="fstat-no" title="function not covered" >(n</span>ame, chunk) =&gt; {
1491
+ <span class="cstat-no" title="statement not covered" > try { <span class="cstat-no" title="statement not covered" >onChunkComplete?.(name, chunk); }</span> catch { /* streaming hook must not break the run */ }</span>
1492
+ },
1493
+ onSkillSkipped: (name) =&gt; {
1494
+ skillStates.push(makeTerminalSkillState(tasks, name, { status: 'skipped' }));
1495
+ updateUI();
1496
+ },
1497
+ onSkillError: <span class="fstat-no" title="function not covered" >(n</span>ame, error) =&gt; {
1498
+ const idx = <span class="cstat-no" title="statement not covered" >skillStates.findIndex(<span class="fstat-no" title="function not covered" >(s</span>) =&gt; <span class="cstat-no" title="statement not covered" >s.name === name)</span>;</span>
1499
+ const existing = <span class="cstat-no" title="statement not covered" >skillStates[idx];</span>
1500
+ &nbsp;
1501
+ <span class="cstat-no" title="statement not covered" > if (idx &gt;= 0 &amp;&amp; existing) {</span>
1502
+ <span class="cstat-no" title="statement not covered" > skillStates[idx] = { ...existing, status: 'error', error };</span>
1503
+ } else {
1504
+ <span class="cstat-no" title="statement not covered" > skillStates.push(makeTerminalSkillState(tasks, name, { status: 'error', error }));</span>
1505
+ }
1506
+ &nbsp;
1507
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1508
+ },
1509
+ onLargePrompt: <span class="fstat-no" title="function not covered" >(_</span>skillName, filename, lineRange, chars, estimatedTokens) =&gt; {
1510
+ const location = <span class="cstat-no" title="statement not covered" >`${filename}:${lineRange}`;</span>
1511
+ const size = <span class="cstat-no" title="statement not covered" >`${Math.round(chars / 1000)}k chars (~${Math.round(estimatedTokens / 1000)}k tokens)`;</span>
1512
+ <span class="cstat-no" title="statement not covered" > warnings.push(`${chalk.yellow(figures.warning)} Large prompt for ${location}: ${size}`);</span>
1513
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1514
+ },
1515
+ onPromptSize: verbosity &gt;= Verbosity.Debug
1516
+ ? <span class="fstat-no" title="function not covered" ><span class="branch-0 cbranch-no" title="branch not covered" >(_</span>skillName, filename, lineRange, systemChars, userChars, totalChars, estimatedTokens) =&gt; {</span>
1517
+ const location = <span class="cstat-no" title="statement not covered" >`${filename}:${lineRange}`;</span>
1518
+ <span class="cstat-no" title="statement not covered" > warnings.push(chalk.dim(`[debug] Prompt for ${location}: system=${systemChars}, user=${userChars}, total=${totalChars} chars (~${estimatedTokens} tokens)`));</span>
1519
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1520
+ }
1521
+ : undefined,
1522
+ onHunkFailed: verbosity &gt;= Verbosity.Verbose
1523
+ ? <span class="fstat-no" title="function not covered" ><span class="branch-0 cbranch-no" title="branch not covered" >(_</span>skillName, filename, lineRange, error) =&gt; {</span>
1524
+ const location = <span class="cstat-no" title="statement not covered" >`${filename}:${lineRange}`;</span>
1525
+ <span class="cstat-no" title="statement not covered" > warnings.push(`${chalk.yellow(figures.warning)} Chunk failed: ${location} ${chalk.dim(`\u2014 ${error}`)}`);</span>
1526
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1527
+ }
1528
+ : undefined,
1529
+ onExtractionFailure: verbosity &gt;= Verbosity.Verbose
1530
+ ? <span class="fstat-no" title="function not covered" ><span class="branch-0 cbranch-no" title="branch not covered" >(_</span>skillName, filename, lineRange, error, preview) =&gt; {</span>
1531
+ const location = <span class="cstat-no" title="statement not covered" >`${filename}:${lineRange}`;</span>
1532
+ <span class="cstat-no" title="statement not covered" > warnings.push(`${chalk.yellow(figures.warning)} Extraction failed: ${location} ${chalk.dim(`\u2014 ${error}`)}`);</span>
1533
+ <span class="cstat-no" title="statement not covered" > if (verbosity &gt;= Verbosity.Debug &amp;&amp; preview) {</span>
1534
+ <span class="cstat-no" title="statement not covered" > warnings.push(chalk.dim(`[debug] Output preview: ${preview.slice(0, 200)}`));</span>
1535
+ }
1536
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1537
+ }
1538
+ : undefined,
1539
+ onRetry: verbosity &gt;= Verbosity.Verbose
1540
+ ? <span class="fstat-no" title="function not covered" ><span class="branch-0 cbranch-no" title="branch not covered" >(_</span>skillName, filename, lineRange, attempt, maxRetries, error, delayMs) =&gt; {</span>
1541
+ const location = <span class="cstat-no" title="statement not covered" >`${filename}:${lineRange}`;</span>
1542
+ const retryInfo = <span class="cstat-no" title="statement not covered" >`attempt ${attempt}/${maxRetries}`;</span>
1543
+ const delay = <span class="cstat-no" title="statement not covered" >delayMs &gt; 0 ? `, retrying in ${Math.round(delayMs / 1000)}s` : '';</span>
1544
+ <span class="cstat-no" title="statement not covered" > warnings.push(chalk.dim(`[debug] Retry ${location} (${retryInfo}${delay}): ${error}`));</span>
1545
+ <span class="cstat-no" title="statement not covered" > updateUI();</span>
1546
+ }
1547
+ : undefined,
1548
+ };
1549
+ &nbsp;
1550
+ // Global semaphore gates file-level work across all skills.
1551
+ const semaphore = new Semaphore(concurrency);
1552
+ &nbsp;
1553
+ // Compose per-task abort controllers: fire on SIGINT, fail-fast, or provider circuit breaker.
1554
+ const circuitAbortController = new AbortController();
1555
+ const circuitBreaker = new ProviderFailureCircuitBreaker({ abortController: circuitAbortController });
1556
+ const composedTasks = composeTasksWithFailFast(
1557
+ tasks,
1558
+ failFastController,
1559
+ circuitBreaker,
1560
+ circuitAbortController,
1561
+ );
1562
+ &nbsp;
1563
+ // Launch all skills in parallel; the semaphore is the sole concurrency gate.
1564
+ const results = await runComposedSkillTasks(composedTasks, callbacks, semaphore);
1565
+ &nbsp;
1566
+ // Flush any pending setImmediate from updateUI so last-tick warnings are
1567
+ // rendered before we tear down. setImmediate is FIFO, so our callback runs
1568
+ // after the queued rerender.
1569
+ await new Promise((resolve) =&gt; setImmediate(resolve));
1570
+ unmounted = true;
1571
+ clear();
1572
+ unmount();
1573
+ &nbsp;
1574
+ printSkillSummary(skillStates);
1575
+ &nbsp;
1576
+ return results;
1577
+ }
1578
+ &nbsp;</pre></td></tr></table></pre>
1579
+
1580
+ <div class='push'></div><!-- for sticky footer -->
1581
+ </div><!-- /wrapper -->
1582
+ <div class='footer quiet pad2 space-top1 center small'>
1583
+ Code coverage generated by
1584
+ <a href="https://istanbul.js.org/" target="_blank" rel="noopener noreferrer">istanbul</a>
1585
+ at 2026-05-17T04:35:52.381Z
1586
+ </div>
1587
+ <script src="../../../prettify.js"></script>
1588
+ <script>
1589
+ window.onload = function () {
1590
+ prettyPrint();
1591
+ };
1592
+ </script>
1593
+ <script src="../../../sorter.js"></script>
1594
+ <script src="../../../block-navigation.js"></script>
1595
+ </body>
1596
+ </html>
1597
+