@rekog/mcp-nest 1.5.0 → 1.5.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.github/workflows/pipeline.yml +11 -1
- package/README.md +28 -42
- package/coverage/clover.xml +324 -325
- package/coverage/coverage-final.json +20 -20
- package/coverage/lcov-report/decorators/constants.ts.html +4 -4
- package/coverage/lcov-report/decorators/index.html +1 -1
- package/coverage/lcov-report/decorators/index.ts.html +5 -5
- package/coverage/lcov-report/decorators/prompt.decorator.ts.html +4 -4
- package/coverage/lcov-report/decorators/resource.decorator.ts.html +4 -4
- package/coverage/lcov-report/decorators/tool.decorator.ts.html +5 -5
- package/coverage/lcov-report/index.html +37 -37
- package/coverage/lcov-report/services/index.html +9 -39
- package/coverage/lcov-report/services/mcp-registry.service.ts.html +6 -6
- package/coverage/lcov-report/tests/index.html +21 -21
- package/coverage/lcov-report/tests/utils.ts.html +45 -45
- package/coverage/lcov.info +446 -449
- package/dist/interfaces/mcp-tool.interface.d.ts +7 -1
- package/dist/interfaces/mcp-tool.interface.d.ts.map +1 -1
- package/dist/services/handlers/mcp-handler.base.d.ts +3 -5
- package/dist/services/handlers/mcp-handler.base.d.ts.map +1 -1
- package/dist/services/handlers/mcp-handler.base.js +6 -2
- package/dist/services/handlers/mcp-handler.base.js.map +1 -1
- package/dist/transport/streamable-http.controller.factory.js +2 -2
- package/dist/transport/streamable-http.controller.factory.js.map +1 -1
- package/package.json +5 -3
- package/playground/resources/greeting.tool.ts +4 -3
- package/tests/mcp-tool.e2e.spec.ts +74 -10
- package/tsconfig.build.tsbuildinfo +1 -1
- package/coverage/lcov-report/services/handlers/index.html +0 -161
- package/coverage/lcov-report/services/handlers/mcp-handler.base.ts.html +0 -421
- package/coverage/lcov-report/services/handlers/mcp-prompts.handler.ts.html +0 -385
- package/coverage/lcov-report/services/handlers/mcp-resources.handler.ts.html +0 -361
- package/coverage/lcov-report/services/handlers/mcp-tools.handler.ts.html +0 -355
- package/coverage/lcov-report/services/mcp-executor.service.ts.html +0 -199
- package/coverage/lcov-report/services/sse-ping.service.ts.html +0 -499
- package/coverage/lcov-report/transport/index.html +0 -131
- package/coverage/lcov-report/transport/sse.controller.factory.ts.html +0 -532
- package/coverage/lcov-report/transport/streamable-http.controller.factory.ts.html +0 -1258
|
@@ -1,1258 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
<!doctype html>
|
|
3
|
-
<html lang="en">
|
|
4
|
-
|
|
5
|
-
<head>
|
|
6
|
-
<title>Code coverage report for transport/streamable-http.controller.factory.ts</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">transport</a> streamable-http.controller.factory.ts</h1>
|
|
23
|
-
<div class='clearfix'>
|
|
24
|
-
|
|
25
|
-
<div class='fl pad1y space-right2'>
|
|
26
|
-
<span class="strong">11.96% </span>
|
|
27
|
-
<span class="quiet">Statements</span>
|
|
28
|
-
<span class='fraction'>14/117</span>
|
|
29
|
-
</div>
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
<div class='fl pad1y space-right2'>
|
|
33
|
-
<span class="strong">3.33% </span>
|
|
34
|
-
<span class="quiet">Branches</span>
|
|
35
|
-
<span class='fraction'>2/60</span>
|
|
36
|
-
</div>
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
<div class='fl pad1y space-right2'>
|
|
40
|
-
<span class="strong">5.88% </span>
|
|
41
|
-
<span class="quiet">Functions</span>
|
|
42
|
-
<span class='fraction'>1/17</span>
|
|
43
|
-
</div>
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
<div class='fl pad1y space-right2'>
|
|
47
|
-
<span class="strong">11.2% </span>
|
|
48
|
-
<span class="quiet">Lines</span>
|
|
49
|
-
<span class='fraction'>13/116</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 low'></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></td><td class="line-coverage quiet"><span class="cline-any cline-yes">1x</span>
|
|
458
|
-
<span class="cline-any cline-neutral"> </span>
|
|
459
|
-
<span class="cline-any cline-neutral"> </span>
|
|
460
|
-
<span class="cline-any cline-neutral"> </span>
|
|
461
|
-
<span class="cline-any cline-neutral"> </span>
|
|
462
|
-
<span class="cline-any cline-neutral"> </span>
|
|
463
|
-
<span class="cline-any cline-neutral"> </span>
|
|
464
|
-
<span class="cline-any cline-neutral"> </span>
|
|
465
|
-
<span class="cline-any cline-neutral"> </span>
|
|
466
|
-
<span class="cline-any cline-neutral"> </span>
|
|
467
|
-
<span class="cline-any cline-neutral"> </span>
|
|
468
|
-
<span class="cline-any cline-neutral"> </span>
|
|
469
|
-
<span class="cline-any cline-neutral"> </span>
|
|
470
|
-
<span class="cline-any cline-neutral"> </span>
|
|
471
|
-
<span class="cline-any cline-neutral"> </span>
|
|
472
|
-
<span class="cline-any cline-neutral"> </span>
|
|
473
|
-
<span class="cline-any cline-yes">1x</span>
|
|
474
|
-
<span class="cline-any cline-yes">1x</span>
|
|
475
|
-
<span class="cline-any cline-neutral"> </span>
|
|
476
|
-
<span class="cline-any cline-neutral"> </span>
|
|
477
|
-
<span class="cline-any cline-yes">1x</span>
|
|
478
|
-
<span class="cline-any cline-yes">1x</span>
|
|
479
|
-
<span class="cline-any cline-neutral"> </span>
|
|
480
|
-
<span class="cline-any cline-yes">1x</span>
|
|
481
|
-
<span class="cline-any cline-yes">1x</span>
|
|
482
|
-
<span class="cline-any cline-neutral"> </span>
|
|
483
|
-
<span class="cline-any cline-neutral"> </span>
|
|
484
|
-
<span class="cline-any cline-neutral"> </span>
|
|
485
|
-
<span class="cline-any cline-neutral"> </span>
|
|
486
|
-
<span class="cline-any cline-neutral"> </span>
|
|
487
|
-
<span class="cline-any cline-yes">1x</span>
|
|
488
|
-
<span class="cline-any cline-neutral"> </span>
|
|
489
|
-
<span class="cline-any cline-neutral"> </span>
|
|
490
|
-
<span class="cline-any cline-neutral"> </span>
|
|
491
|
-
<span class="cline-any cline-neutral"> </span>
|
|
492
|
-
<span class="cline-any cline-neutral"> </span>
|
|
493
|
-
<span class="cline-any cline-neutral"> </span>
|
|
494
|
-
<span class="cline-any cline-neutral"> </span>
|
|
495
|
-
<span class="cline-any cline-yes">2x</span>
|
|
496
|
-
<span class="cline-any cline-no"> </span>
|
|
497
|
-
<span class="cline-any cline-no"> </span>
|
|
498
|
-
<span class="cline-any cline-neutral"> </span>
|
|
499
|
-
<span class="cline-any cline-no"> </span>
|
|
500
|
-
<span class="cline-any cline-neutral"> </span>
|
|
501
|
-
<span class="cline-any cline-neutral"> </span>
|
|
502
|
-
<span class="cline-any cline-no"> </span>
|
|
503
|
-
<span class="cline-any cline-no"> </span>
|
|
504
|
-
<span class="cline-any cline-no"> </span>
|
|
505
|
-
<span class="cline-any cline-neutral"> </span>
|
|
506
|
-
<span class="cline-any cline-neutral"> </span>
|
|
507
|
-
<span class="cline-any cline-no"> </span>
|
|
508
|
-
<span class="cline-any cline-no"> </span>
|
|
509
|
-
<span class="cline-any cline-no"> </span>
|
|
510
|
-
<span class="cline-any cline-neutral"> </span>
|
|
511
|
-
<span class="cline-any cline-neutral"> </span>
|
|
512
|
-
<span class="cline-any cline-no"> </span>
|
|
513
|
-
<span class="cline-any cline-neutral"> </span>
|
|
514
|
-
<span class="cline-any cline-neutral"> </span>
|
|
515
|
-
<span class="cline-any cline-no"> </span>
|
|
516
|
-
<span class="cline-any cline-no"> </span>
|
|
517
|
-
<span class="cline-any cline-neutral"> </span>
|
|
518
|
-
<span class="cline-any cline-no"> </span>
|
|
519
|
-
<span class="cline-any cline-neutral"> </span>
|
|
520
|
-
<span class="cline-any cline-neutral"> </span>
|
|
521
|
-
<span class="cline-any cline-no"> </span>
|
|
522
|
-
<span class="cline-any cline-neutral"> </span>
|
|
523
|
-
<span class="cline-any cline-neutral"> </span>
|
|
524
|
-
<span class="cline-any cline-neutral"> </span>
|
|
525
|
-
<span class="cline-any cline-neutral"> </span>
|
|
526
|
-
<span class="cline-any cline-neutral"> </span>
|
|
527
|
-
<span class="cline-any cline-neutral"> </span>
|
|
528
|
-
<span class="cline-any cline-neutral"> </span>
|
|
529
|
-
<span class="cline-any cline-neutral"> </span>
|
|
530
|
-
<span class="cline-any cline-no"> </span>
|
|
531
|
-
<span class="cline-any cline-neutral"> </span>
|
|
532
|
-
<span class="cline-any cline-neutral"> </span>
|
|
533
|
-
<span class="cline-any cline-no"> </span>
|
|
534
|
-
<span class="cline-any cline-neutral"> </span>
|
|
535
|
-
<span class="cline-any cline-no"> </span>
|
|
536
|
-
<span class="cline-any cline-neutral"> </span>
|
|
537
|
-
<span class="cline-any cline-neutral"> </span>
|
|
538
|
-
<span class="cline-any cline-neutral"> </span>
|
|
539
|
-
<span class="cline-any cline-neutral"> </span>
|
|
540
|
-
<span class="cline-any cline-neutral"> </span>
|
|
541
|
-
<span class="cline-any cline-no"> </span>
|
|
542
|
-
<span class="cline-any cline-neutral"> </span>
|
|
543
|
-
<span class="cline-any cline-neutral"> </span>
|
|
544
|
-
<span class="cline-any cline-no"> </span>
|
|
545
|
-
<span class="cline-any cline-neutral"> </span>
|
|
546
|
-
<span class="cline-any cline-neutral"> </span>
|
|
547
|
-
<span class="cline-any cline-neutral"> </span>
|
|
548
|
-
<span class="cline-any cline-neutral"> </span>
|
|
549
|
-
<span class="cline-any cline-neutral"> </span>
|
|
550
|
-
<span class="cline-any cline-neutral"> </span>
|
|
551
|
-
<span class="cline-any cline-neutral"> </span>
|
|
552
|
-
<span class="cline-any cline-neutral"> </span>
|
|
553
|
-
<span class="cline-any cline-neutral"> </span>
|
|
554
|
-
<span class="cline-any cline-neutral"> </span>
|
|
555
|
-
<span class="cline-any cline-neutral"> </span>
|
|
556
|
-
<span class="cline-any cline-neutral"> </span>
|
|
557
|
-
<span class="cline-any cline-no"> </span>
|
|
558
|
-
<span class="cline-any cline-neutral"> </span>
|
|
559
|
-
<span class="cline-any cline-neutral"> </span>
|
|
560
|
-
<span class="cline-any cline-neutral"> </span>
|
|
561
|
-
<span class="cline-any cline-no"> </span>
|
|
562
|
-
<span class="cline-any cline-neutral"> </span>
|
|
563
|
-
<span class="cline-any cline-neutral"> </span>
|
|
564
|
-
<span class="cline-any cline-neutral"> </span>
|
|
565
|
-
<span class="cline-any cline-neutral"> </span>
|
|
566
|
-
<span class="cline-any cline-neutral"> </span>
|
|
567
|
-
<span class="cline-any cline-neutral"> </span>
|
|
568
|
-
<span class="cline-any cline-neutral"> </span>
|
|
569
|
-
<span class="cline-any cline-neutral"> </span>
|
|
570
|
-
<span class="cline-any cline-neutral"> </span>
|
|
571
|
-
<span class="cline-any cline-neutral"> </span>
|
|
572
|
-
<span class="cline-any cline-neutral"> </span>
|
|
573
|
-
<span class="cline-any cline-yes">2x</span>
|
|
574
|
-
<span class="cline-any cline-neutral"> </span>
|
|
575
|
-
<span class="cline-any cline-neutral"> </span>
|
|
576
|
-
<span class="cline-any cline-neutral"> </span>
|
|
577
|
-
<span class="cline-any cline-neutral"> </span>
|
|
578
|
-
<span class="cline-any cline-no"> </span>
|
|
579
|
-
<span class="cline-any cline-neutral"> </span>
|
|
580
|
-
<span class="cline-any cline-no"> </span>
|
|
581
|
-
<span class="cline-any cline-no"> </span>
|
|
582
|
-
<span class="cline-any cline-no"> </span>
|
|
583
|
-
<span class="cline-any cline-neutral"> </span>
|
|
584
|
-
<span class="cline-any cline-no"> </span>
|
|
585
|
-
<span class="cline-any cline-neutral"> </span>
|
|
586
|
-
<span class="cline-any cline-neutral"> </span>
|
|
587
|
-
<span class="cline-any cline-no"> </span>
|
|
588
|
-
<span class="cline-any cline-no"> </span>
|
|
589
|
-
<span class="cline-any cline-no"> </span>
|
|
590
|
-
<span class="cline-any cline-neutral"> </span>
|
|
591
|
-
<span class="cline-any cline-neutral"> </span>
|
|
592
|
-
<span class="cline-any cline-neutral"> </span>
|
|
593
|
-
<span class="cline-any cline-neutral"> </span>
|
|
594
|
-
<span class="cline-any cline-neutral"> </span>
|
|
595
|
-
<span class="cline-any cline-neutral"> </span>
|
|
596
|
-
<span class="cline-any cline-neutral"> </span>
|
|
597
|
-
<span class="cline-any cline-neutral"> </span>
|
|
598
|
-
<span class="cline-any cline-neutral"> </span>
|
|
599
|
-
<span class="cline-any cline-neutral"> </span>
|
|
600
|
-
<span class="cline-any cline-neutral"> </span>
|
|
601
|
-
<span class="cline-any cline-neutral"> </span>
|
|
602
|
-
<span class="cline-any cline-neutral"> </span>
|
|
603
|
-
<span class="cline-any cline-neutral"> </span>
|
|
604
|
-
<span class="cline-any cline-neutral"> </span>
|
|
605
|
-
<span class="cline-any cline-neutral"> </span>
|
|
606
|
-
<span class="cline-any cline-neutral"> </span>
|
|
607
|
-
<span class="cline-any cline-neutral"> </span>
|
|
608
|
-
<span class="cline-any cline-neutral"> </span>
|
|
609
|
-
<span class="cline-any cline-no"> </span>
|
|
610
|
-
<span class="cline-any cline-no"> </span>
|
|
611
|
-
<span class="cline-any cline-neutral"> </span>
|
|
612
|
-
<span class="cline-any cline-neutral"> </span>
|
|
613
|
-
<span class="cline-any cline-neutral"> </span>
|
|
614
|
-
<span class="cline-any cline-neutral"> </span>
|
|
615
|
-
<span class="cline-any cline-no"> </span>
|
|
616
|
-
<span class="cline-any cline-neutral"> </span>
|
|
617
|
-
<span class="cline-any cline-no"> </span>
|
|
618
|
-
<span class="cline-any cline-no"> </span>
|
|
619
|
-
<span class="cline-any cline-no"> </span>
|
|
620
|
-
<span class="cline-any cline-no"> </span>
|
|
621
|
-
<span class="cline-any cline-no"> </span>
|
|
622
|
-
<span class="cline-any cline-neutral"> </span>
|
|
623
|
-
<span class="cline-any cline-no"> </span>
|
|
624
|
-
<span class="cline-any cline-neutral"> </span>
|
|
625
|
-
<span class="cline-any cline-no"> </span>
|
|
626
|
-
<span class="cline-any cline-neutral"> </span>
|
|
627
|
-
<span class="cline-any cline-neutral"> </span>
|
|
628
|
-
<span class="cline-any cline-neutral"> </span>
|
|
629
|
-
<span class="cline-any cline-neutral"> </span>
|
|
630
|
-
<span class="cline-any cline-neutral"> </span>
|
|
631
|
-
<span class="cline-any cline-neutral"> </span>
|
|
632
|
-
<span class="cline-any cline-neutral"> </span>
|
|
633
|
-
<span class="cline-any cline-neutral"> </span>
|
|
634
|
-
<span class="cline-any cline-neutral"> </span>
|
|
635
|
-
<span class="cline-any cline-neutral"> </span>
|
|
636
|
-
<span class="cline-any cline-neutral"> </span>
|
|
637
|
-
<span class="cline-any cline-neutral"> </span>
|
|
638
|
-
<span class="cline-any cline-no"> </span>
|
|
639
|
-
<span class="cline-any cline-no"> </span>
|
|
640
|
-
<span class="cline-any cline-no"> </span>
|
|
641
|
-
<span class="cline-any cline-neutral"> </span>
|
|
642
|
-
<span class="cline-any cline-neutral"> </span>
|
|
643
|
-
<span class="cline-any cline-neutral"> </span>
|
|
644
|
-
<span class="cline-any cline-neutral"> </span>
|
|
645
|
-
<span class="cline-any cline-neutral"> </span>
|
|
646
|
-
<span class="cline-any cline-neutral"> </span>
|
|
647
|
-
<span class="cline-any cline-no"> </span>
|
|
648
|
-
<span class="cline-any cline-neutral"> </span>
|
|
649
|
-
<span class="cline-any cline-no"> </span>
|
|
650
|
-
<span class="cline-any cline-neutral"> </span>
|
|
651
|
-
<span class="cline-any cline-no"> </span>
|
|
652
|
-
<span class="cline-any cline-neutral"> </span>
|
|
653
|
-
<span class="cline-any cline-neutral"> </span>
|
|
654
|
-
<span class="cline-any cline-neutral"> </span>
|
|
655
|
-
<span class="cline-any cline-no"> </span>
|
|
656
|
-
<span class="cline-any cline-no"> </span>
|
|
657
|
-
<span class="cline-any cline-neutral"> </span>
|
|
658
|
-
<span class="cline-any cline-neutral"> </span>
|
|
659
|
-
<span class="cline-any cline-neutral"> </span>
|
|
660
|
-
<span class="cline-any cline-neutral"> </span>
|
|
661
|
-
<span class="cline-any cline-neutral"> </span>
|
|
662
|
-
<span class="cline-any cline-neutral"> </span>
|
|
663
|
-
<span class="cline-any cline-no"> </span>
|
|
664
|
-
<span class="cline-any cline-neutral"> </span>
|
|
665
|
-
<span class="cline-any cline-neutral"> </span>
|
|
666
|
-
<span class="cline-any cline-no"> </span>
|
|
667
|
-
<span class="cline-any cline-neutral"> </span>
|
|
668
|
-
<span class="cline-any cline-neutral"> </span>
|
|
669
|
-
<span class="cline-any cline-neutral"> </span>
|
|
670
|
-
<span class="cline-any cline-neutral"> </span>
|
|
671
|
-
<span class="cline-any cline-neutral"> </span>
|
|
672
|
-
<span class="cline-any cline-neutral"> </span>
|
|
673
|
-
<span class="cline-any cline-neutral"> </span>
|
|
674
|
-
<span class="cline-any cline-neutral"> </span>
|
|
675
|
-
<span class="cline-any cline-neutral"> </span>
|
|
676
|
-
<span class="cline-any cline-neutral"> </span>
|
|
677
|
-
<span class="cline-any cline-neutral"> </span>
|
|
678
|
-
<span class="cline-any cline-no"> </span>
|
|
679
|
-
<span class="cline-any cline-neutral"> </span>
|
|
680
|
-
<span class="cline-any cline-neutral"> </span>
|
|
681
|
-
<span class="cline-any cline-no"> </span>
|
|
682
|
-
<span class="cline-any cline-neutral"> </span>
|
|
683
|
-
<span class="cline-any cline-no"> </span>
|
|
684
|
-
<span class="cline-any cline-no"> </span>
|
|
685
|
-
<span class="cline-any cline-neutral"> </span>
|
|
686
|
-
<span class="cline-any cline-no"> </span>
|
|
687
|
-
<span class="cline-any cline-neutral"> </span>
|
|
688
|
-
<span class="cline-any cline-neutral"> </span>
|
|
689
|
-
<span class="cline-any cline-no"> </span>
|
|
690
|
-
<span class="cline-any cline-neutral"> </span>
|
|
691
|
-
<span class="cline-any cline-neutral"> </span>
|
|
692
|
-
<span class="cline-any cline-neutral"> </span>
|
|
693
|
-
<span class="cline-any cline-neutral"> </span>
|
|
694
|
-
<span class="cline-any cline-neutral"> </span>
|
|
695
|
-
<span class="cline-any cline-no"> </span>
|
|
696
|
-
<span class="cline-any cline-neutral"> </span>
|
|
697
|
-
<span class="cline-any cline-neutral"> </span>
|
|
698
|
-
<span class="cline-any cline-neutral"> </span>
|
|
699
|
-
<span class="cline-any cline-neutral"> </span>
|
|
700
|
-
<span class="cline-any cline-neutral"> </span>
|
|
701
|
-
<span class="cline-any cline-neutral"> </span>
|
|
702
|
-
<span class="cline-any cline-neutral"> </span>
|
|
703
|
-
<span class="cline-any cline-neutral"> </span>
|
|
704
|
-
<span class="cline-any cline-neutral"> </span>
|
|
705
|
-
<span class="cline-any cline-neutral"> </span>
|
|
706
|
-
<span class="cline-any cline-neutral"> </span>
|
|
707
|
-
<span class="cline-any cline-neutral"> </span>
|
|
708
|
-
<span class="cline-any cline-no"> </span>
|
|
709
|
-
<span class="cline-any cline-neutral"> </span>
|
|
710
|
-
<span class="cline-any cline-neutral"> </span>
|
|
711
|
-
<span class="cline-any cline-no"> </span>
|
|
712
|
-
<span class="cline-any cline-neutral"> </span>
|
|
713
|
-
<span class="cline-any cline-neutral"> </span>
|
|
714
|
-
<span class="cline-any cline-no"> </span>
|
|
715
|
-
<span class="cline-any cline-no"> </span>
|
|
716
|
-
<span class="cline-any cline-no"> </span>
|
|
717
|
-
<span class="cline-any cline-neutral"> </span>
|
|
718
|
-
<span class="cline-any cline-neutral"> </span>
|
|
719
|
-
<span class="cline-any cline-no"> </span>
|
|
720
|
-
<span class="cline-any cline-no"> </span>
|
|
721
|
-
<span class="cline-any cline-neutral"> </span>
|
|
722
|
-
<span class="cline-any cline-neutral"> </span>
|
|
723
|
-
<span class="cline-any cline-neutral"> </span>
|
|
724
|
-
<span class="cline-any cline-no"> </span>
|
|
725
|
-
<span class="cline-any cline-neutral"> </span>
|
|
726
|
-
<span class="cline-any cline-neutral"> </span>
|
|
727
|
-
<span class="cline-any cline-no"> </span>
|
|
728
|
-
<span class="cline-any cline-neutral"> </span>
|
|
729
|
-
<span class="cline-any cline-neutral"> </span>
|
|
730
|
-
<span class="cline-any cline-no"> </span>
|
|
731
|
-
<span class="cline-any cline-neutral"> </span>
|
|
732
|
-
<span class="cline-any cline-neutral"> </span>
|
|
733
|
-
<span class="cline-any cline-neutral"> </span>
|
|
734
|
-
<span class="cline-any cline-neutral"> </span>
|
|
735
|
-
<span class="cline-any cline-neutral"> </span>
|
|
736
|
-
<span class="cline-any cline-neutral"> </span>
|
|
737
|
-
<span class="cline-any cline-neutral"> </span>
|
|
738
|
-
<span class="cline-any cline-no"> </span>
|
|
739
|
-
<span class="cline-any cline-neutral"> </span>
|
|
740
|
-
<span class="cline-any cline-neutral"> </span>
|
|
741
|
-
<span class="cline-any cline-neutral"> </span>
|
|
742
|
-
<span class="cline-any cline-no"> </span>
|
|
743
|
-
<span class="cline-any cline-no"> </span>
|
|
744
|
-
<span class="cline-any cline-no"> </span>
|
|
745
|
-
<span class="cline-any cline-neutral"> </span>
|
|
746
|
-
<span class="cline-any cline-neutral"> </span>
|
|
747
|
-
<span class="cline-any cline-neutral"> </span>
|
|
748
|
-
<span class="cline-any cline-neutral"> </span>
|
|
749
|
-
<span class="cline-any cline-neutral"> </span>
|
|
750
|
-
<span class="cline-any cline-neutral"> </span>
|
|
751
|
-
<span class="cline-any cline-neutral"> </span>
|
|
752
|
-
<span class="cline-any cline-no"> </span>
|
|
753
|
-
<span class="cline-any cline-neutral"> </span>
|
|
754
|
-
<span class="cline-any cline-neutral"> </span>
|
|
755
|
-
<span class="cline-any cline-neutral"> </span>
|
|
756
|
-
<span class="cline-any cline-no"> </span>
|
|
757
|
-
<span class="cline-any cline-no"> </span>
|
|
758
|
-
<span class="cline-any cline-neutral"> </span>
|
|
759
|
-
<span class="cline-any cline-neutral"> </span>
|
|
760
|
-
<span class="cline-any cline-neutral"> </span>
|
|
761
|
-
<span class="cline-any cline-neutral"> </span>
|
|
762
|
-
<span class="cline-any cline-neutral"> </span>
|
|
763
|
-
<span class="cline-any cline-neutral"> </span>
|
|
764
|
-
<span class="cline-any cline-no"> </span>
|
|
765
|
-
<span class="cline-any cline-neutral"> </span>
|
|
766
|
-
<span class="cline-any cline-neutral"> </span>
|
|
767
|
-
<span class="cline-any cline-no"> </span>
|
|
768
|
-
<span class="cline-any cline-neutral"> </span>
|
|
769
|
-
<span class="cline-any cline-neutral"> </span>
|
|
770
|
-
<span class="cline-any cline-neutral"> </span>
|
|
771
|
-
<span class="cline-any cline-neutral"> </span>
|
|
772
|
-
<span class="cline-any cline-neutral"> </span>
|
|
773
|
-
<span class="cline-any cline-neutral"> </span>
|
|
774
|
-
<span class="cline-any cline-neutral"> </span>
|
|
775
|
-
<span class="cline-any cline-yes">2x</span>
|
|
776
|
-
<span class="cline-any cline-no"> </span>
|
|
777
|
-
<span class="cline-any cline-no"> </span>
|
|
778
|
-
<span class="cline-any cline-neutral"> </span>
|
|
779
|
-
<span class="cline-any cline-neutral"> </span>
|
|
780
|
-
<span class="cline-any cline-no"> </span>
|
|
781
|
-
<span class="cline-any cline-neutral"> </span>
|
|
782
|
-
<span class="cline-any cline-no"> </span>
|
|
783
|
-
<span class="cline-any cline-no"> </span>
|
|
784
|
-
<span class="cline-any cline-no"> </span>
|
|
785
|
-
<span class="cline-any cline-neutral"> </span>
|
|
786
|
-
<span class="cline-any cline-neutral"> </span>
|
|
787
|
-
<span class="cline-any cline-no"> </span>
|
|
788
|
-
<span class="cline-any cline-no"> </span>
|
|
789
|
-
<span class="cline-any cline-no"> </span>
|
|
790
|
-
<span class="cline-any cline-neutral"> </span>
|
|
791
|
-
<span class="cline-any cline-neutral"> </span>
|
|
792
|
-
<span class="cline-any cline-neutral"> </span>
|
|
793
|
-
<span class="cline-any cline-neutral"> </span>
|
|
794
|
-
<span class="cline-any cline-neutral"> </span>
|
|
795
|
-
<span class="cline-any cline-neutral"> </span>
|
|
796
|
-
<span class="cline-any cline-neutral"> </span>
|
|
797
|
-
<span class="cline-any cline-yes">2x</span>
|
|
798
|
-
<span class="cline-any cline-no"> </span>
|
|
799
|
-
<span class="cline-any cline-neutral"> </span>
|
|
800
|
-
<span class="cline-any cline-no"> </span>
|
|
801
|
-
<span class="cline-any cline-no"> </span>
|
|
802
|
-
<span class="cline-any cline-neutral"> </span>
|
|
803
|
-
<span class="cline-any cline-neutral"> </span>
|
|
804
|
-
<span class="cline-any cline-no"> </span>
|
|
805
|
-
<span class="cline-any cline-neutral"> </span>
|
|
806
|
-
<span class="cline-any cline-no"> </span>
|
|
807
|
-
<span class="cline-any cline-no"> </span>
|
|
808
|
-
<span class="cline-any cline-no"> </span>
|
|
809
|
-
<span class="cline-any cline-neutral"> </span>
|
|
810
|
-
<span class="cline-any cline-neutral"> </span>
|
|
811
|
-
<span class="cline-any cline-no"> </span>
|
|
812
|
-
<span class="cline-any cline-no"> </span>
|
|
813
|
-
<span class="cline-any cline-no"> </span>
|
|
814
|
-
<span class="cline-any cline-no"> </span>
|
|
815
|
-
<span class="cline-any cline-neutral"> </span>
|
|
816
|
-
<span class="cline-any cline-neutral"> </span>
|
|
817
|
-
<span class="cline-any cline-neutral"> </span>
|
|
818
|
-
<span class="cline-any cline-neutral"> </span>
|
|
819
|
-
<span class="cline-any cline-no"> </span>
|
|
820
|
-
<span class="cline-any cline-no"> </span>
|
|
821
|
-
<span class="cline-any cline-neutral"> </span>
|
|
822
|
-
<span class="cline-any cline-no"> </span>
|
|
823
|
-
<span class="cline-any cline-neutral"> </span>
|
|
824
|
-
<span class="cline-any cline-neutral"> </span>
|
|
825
|
-
<span class="cline-any cline-neutral"> </span>
|
|
826
|
-
<span class="cline-any cline-neutral"> </span>
|
|
827
|
-
<span class="cline-any cline-neutral"> </span>
|
|
828
|
-
<span class="cline-any cline-no"> </span>
|
|
829
|
-
<span class="cline-any cline-neutral"> </span>
|
|
830
|
-
<span class="cline-any cline-neutral"> </span>
|
|
831
|
-
<span class="cline-any cline-neutral"> </span>
|
|
832
|
-
<span class="cline-any cline-neutral"> </span>
|
|
833
|
-
<span class="cline-any cline-neutral"> </span>
|
|
834
|
-
<span class="cline-any cline-neutral"> </span>
|
|
835
|
-
<span class="cline-any cline-neutral"> </span>
|
|
836
|
-
<span class="cline-any cline-neutral"> </span>
|
|
837
|
-
<span class="cline-any cline-neutral"> </span>
|
|
838
|
-
<span class="cline-any cline-no"> </span>
|
|
839
|
-
<span class="cline-any cline-no"> </span>
|
|
840
|
-
<span class="cline-any cline-no"> </span>
|
|
841
|
-
<span class="cline-any cline-no"> </span>
|
|
842
|
-
<span class="cline-any cline-neutral"> </span>
|
|
843
|
-
<span class="cline-any cline-neutral"> </span>
|
|
844
|
-
<span class="cline-any cline-neutral"> </span>
|
|
845
|
-
<span class="cline-any cline-neutral"> </span>
|
|
846
|
-
<span class="cline-any cline-yes">2x</span>
|
|
847
|
-
<span class="cline-any cline-neutral"> </span>
|
|
848
|
-
<span class="cline-any cline-neutral"> </span></td><td class="text"><pre class="prettyprint lang-js">import {
|
|
849
|
-
Body,
|
|
850
|
-
CanActivate,
|
|
851
|
-
Controller,
|
|
852
|
-
Delete,
|
|
853
|
-
Get,
|
|
854
|
-
Inject,
|
|
855
|
-
Logger,
|
|
856
|
-
OnModuleInit,
|
|
857
|
-
Post,
|
|
858
|
-
Req,
|
|
859
|
-
Res,
|
|
860
|
-
Type,
|
|
861
|
-
UseGuards,
|
|
862
|
-
applyDecorators,
|
|
863
|
-
} from '@nestjs/common';
|
|
864
|
-
import { ContextIdFactory, ModuleRef } from '@nestjs/core';
|
|
865
|
-
import { randomUUID } from 'crypto';
|
|
866
|
-
import type { Request, Response } from 'express';
|
|
867
|
-
|
|
868
|
-
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
869
|
-
import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js';
|
|
870
|
-
import { McpOptions } from '../interfaces';
|
|
871
|
-
import { McpExecutorService } from '../services/mcp-executor.service';
|
|
872
|
-
import { McpRegistryService } from '../services/mcp-registry.service';
|
|
873
|
-
import { JSONRPCMessage } from '@modelcontextprotocol/sdk/types.js';
|
|
874
|
-
|
|
875
|
-
/**
|
|
876
|
-
* Creates a controller for handling Streamable HTTP connections and tool executions
|
|
877
|
-
*/
|
|
878
|
-
export function createStreamableHttpController(
|
|
879
|
-
endpoint: string,
|
|
880
|
-
globalApiPrefix: string,
|
|
881
|
-
guards: Type<CanActivate>[] = [],
|
|
882
|
-
decorators: ClassDecorator[] = [],
|
|
883
|
-
) {
|
|
884
|
-
@Controller()
|
|
885
|
-
@applyDecorators(...decorators)
|
|
886
|
-
class StreamableHttpController implements OnModuleInit {
|
|
887
|
-
public readonly <span class="cstat-no" title="statement not covered" >logger = new Logger(StreamableHttpController.name);</span>
|
|
888
|
-
public <span class="cstat-no" title="statement not covered" >transports: { [sessionId: string]: StreamableHTTPServerTransport } =</span>
|
|
889
|
-
{};
|
|
890
|
-
public <span class="cstat-no" title="statement not covered" >mcpServers: { [sessionId: string]: McpServer } = {};</span>
|
|
891
|
-
|
|
892
|
-
// Singleton instances for stateless mode
|
|
893
|
-
public <span class="cstat-no" title="statement not covered" >statelessTransport: StreamableHTTPServerTransport | null = null;</span>
|
|
894
|
-
public <span class="cstat-no" title="statement not covered" >statelessMcpServer: McpServer | null = null;</span>
|
|
895
|
-
public <span class="cstat-no" title="statement not covered" >isStatelessMode: boolean = false;</span>
|
|
896
|
-
|
|
897
|
-
<span class="fstat-no" title="function not covered" > constructor(</span>
|
|
898
|
-
@Inject('MCP_OPTIONS') public readonly <span class="cstat-no" title="statement not covered" >options: McpOptions,</span>
|
|
899
|
-
public readonly <span class="cstat-no" title="statement not covered" >moduleRef: M</span>oduleRef,
|
|
900
|
-
public readonly <span class="cstat-no" title="statement not covered" >toolRegistry: M</span>cpRegistryService,
|
|
901
|
-
) {
|
|
902
|
-
// Determine if we're in stateless mode
|
|
903
|
-
<span class="cstat-no" title="statement not covered" > this.isStatelessMode = !!options.streamableHttp?.statelessMode;</span>
|
|
904
|
-
|
|
905
|
-
// Initialize stateless mode if needed
|
|
906
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (this.isStatelessMode) {</span>
|
|
907
|
-
<span class="cstat-no" title="statement not covered" > this.initializeStatelessMode()</span>
|
|
908
|
-
.then(<span class="fstat-no" title="function not covered" >() =</span>> {
|
|
909
|
-
<span class="cstat-no" title="statement not covered" > this.logger.debug('Stateless mode initialized');</span>
|
|
910
|
-
})
|
|
911
|
-
.catch(<span class="fstat-no" title="function not covered" >(e</span>rror) => {
|
|
912
|
-
<span class="cstat-no" title="statement not covered" > this.logger.error('Error initializing stateless mode:', error);</span>
|
|
913
|
-
});
|
|
914
|
-
}
|
|
915
|
-
}
|
|
916
|
-
|
|
917
|
-
/**
|
|
918
|
-
* Initialize the stateless mode with singleton transport and server
|
|
919
|
-
*/
|
|
920
|
-
public <span class="fstat-no" title="function not covered" >async </span>initializeStatelessMode(): Promise<void> {
|
|
921
|
-
<span class="cstat-no" title="statement not covered" > this.logger.log('Initializing MCP Streamable HTTP in stateless mode');</span>
|
|
922
|
-
|
|
923
|
-
// Create a singleton transport for all requests
|
|
924
|
-
<span class="cstat-no" title="statement not covered" > this.statelessTransport = new StreamableHTTPServerTransport({</span>
|
|
925
|
-
// statelessMode: true, // TODO: Uncomment when this PR is merged and released: https://github.com/modelcontextprotocol/typescript-sdk/pull/362
|
|
926
|
-
sessionIdGenerator: <span class="fstat-no" title="function not covered" >() =</span>> <span class="cstat-no" title="statement not covered" >undefined,</span>
|
|
927
|
-
enableJsonResponse:
|
|
928
|
-
this.options.streamableHttp?.enableJsonResponse || false,
|
|
929
|
-
});
|
|
930
|
-
|
|
931
|
-
// TODO: Remove when this PR is merged and released: https://github.com/modelcontextprotocol/typescript-sdk/pull/362
|
|
932
|
-
(<span class="cstat-no" title="statement not covered" >this.statelessTransport as any)._initialized = true;</span>
|
|
933
|
-
|
|
934
|
-
// Create a singleton MCP server instance
|
|
935
|
-
<span class="cstat-no" title="statement not covered" > this.statelessMcpServer = new McpServer(</span>
|
|
936
|
-
{ name: this.options.name, version: this.options.version },
|
|
937
|
-
{
|
|
938
|
-
capabilities: this.options.capabilities || {
|
|
939
|
-
tools: {},
|
|
940
|
-
resources: {},
|
|
941
|
-
resourceTemplates: {},
|
|
942
|
-
prompts: {},
|
|
943
|
-
},
|
|
944
|
-
},
|
|
945
|
-
);
|
|
946
|
-
|
|
947
|
-
// Connect the transport to the MCP server
|
|
948
|
-
<span class="cstat-no" title="statement not covered" > await this.statelessMcpServer.connect(this.statelessTransport);</span>
|
|
949
|
-
}
|
|
950
|
-
|
|
951
|
-
<span class="fstat-no" title="function not covered" > onModuleInit(</span>) {
|
|
952
|
-
<span class="cstat-no" title="statement not covered" > this.logger.log(</span>
|
|
953
|
-
`Initialized MCP Streamable HTTP controller at ${endpoint} in ${
|
|
954
|
-
this.isStatelessMode ? 'stateless' : 'stateful'
|
|
955
|
-
} mode`,
|
|
956
|
-
);
|
|
957
|
-
}
|
|
958
|
-
|
|
959
|
-
/**
|
|
960
|
-
* Main HTTP endpoint for both initialization and subsequent requests
|
|
961
|
-
*/
|
|
962
|
-
@Post(endpoint)
|
|
963
|
-
@UseGuards(...guards)
|
|
964
|
-
<span class="fstat-no" title="function not covered" > async </span>handlePostRequest(
|
|
965
|
-
@Req() req: Request,
|
|
966
|
-
@Res() res: Response,
|
|
967
|
-
@Body() body: unknown,
|
|
968
|
-
) {
|
|
969
|
-
<span class="cstat-no" title="statement not covered" > this.logger.debug('Received MCP request:', body);</span>
|
|
970
|
-
|
|
971
|
-
<span class="cstat-no" title="statement not covered" > try {</span>
|
|
972
|
-
<span class="cstat-no" title="statement not covered" > if (this.isStatelessMode) {</span>
|
|
973
|
-
<span class="cstat-no" title="statement not covered" > return this.handleStatelessRequest(req, res, body);</span>
|
|
974
|
-
} else {
|
|
975
|
-
<span class="cstat-no" title="statement not covered" > return this.handleStatefulRequest(req, res, body);</span>
|
|
976
|
-
}
|
|
977
|
-
} catch (error) {
|
|
978
|
-
<span class="cstat-no" title="statement not covered" > this.logger.error('Error handling MCP request:', error);</span>
|
|
979
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (!res.headersSent) {</span>
|
|
980
|
-
<span class="cstat-no" title="statement not covered" > res.status(500).json({</span>
|
|
981
|
-
jsonrpc: '2.0',
|
|
982
|
-
error: {
|
|
983
|
-
code: -32603,
|
|
984
|
-
message: 'Internal server error',
|
|
985
|
-
},
|
|
986
|
-
id: null,
|
|
987
|
-
});
|
|
988
|
-
}
|
|
989
|
-
}
|
|
990
|
-
}
|
|
991
|
-
|
|
992
|
-
/**
|
|
993
|
-
* Handle requests in stateless mode
|
|
994
|
-
*/
|
|
995
|
-
public <span class="fstat-no" title="function not covered" >async </span>handleStatelessRequest(
|
|
996
|
-
req: Request,
|
|
997
|
-
res: Response,
|
|
998
|
-
body: unknown,
|
|
999
|
-
): Promise<void> {
|
|
1000
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (!this.statelessTransport || !this.statelessMcpServer) {</span>
|
|
1001
|
-
<span class="cstat-no" title="statement not covered" > await this.initializeStatelessMode();</span>
|
|
1002
|
-
}
|
|
1003
|
-
|
|
1004
|
-
// ToDo: This will likely change.
|
|
1005
|
-
// Handle initialize requests directly
|
|
1006
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (this.isInitializeRequest(body)) {</span>
|
|
1007
|
-
// Check and respond here
|
|
1008
|
-
const acceptHeader = (<span class="cstat-no" title="statement not covered" >req.headers['accept'] as string) || '';</span>
|
|
1009
|
-
const isEventStream = <span class="cstat-no" title="statement not covered" >acceptHeader.includes('text/event-stream');</span>
|
|
1010
|
-
<span class="cstat-no" title="statement not covered" > if (isEventStream) {</span>
|
|
1011
|
-
<span class="cstat-no" title="statement not covered" > res.setHeader('Content-Type', 'text/event-stream');</span>
|
|
1012
|
-
<span class="cstat-no" title="statement not covered" > res.flushHeaders?.();</span>
|
|
1013
|
-
} else {
|
|
1014
|
-
<span class="cstat-no" title="statement not covered" > res.setHeader('Content-Type', 'application/json');</span>
|
|
1015
|
-
}
|
|
1016
|
-
const payload: JSONRPCMessage = <span class="cstat-no" title="statement not covered" >{</span>
|
|
1017
|
-
jsonrpc: '2.0',
|
|
1018
|
-
id: (body as any).id,
|
|
1019
|
-
result: {
|
|
1020
|
-
protocolVersion: '2024-11-05',
|
|
1021
|
-
capabilities: this.options.capabilities || {},
|
|
1022
|
-
instructions: this.options.instructions || '',
|
|
1023
|
-
serverInfo: {
|
|
1024
|
-
name: this.options.name,
|
|
1025
|
-
version: this.options.version,
|
|
1026
|
-
},
|
|
1027
|
-
},
|
|
1028
|
-
};
|
|
1029
|
-
<span class="cstat-no" title="statement not covered" > if (isEventStream) {</span>
|
|
1030
|
-
const messageId = <span class="cstat-no" title="statement not covered" >randomUUID() + '_' + Date.now();</span>
|
|
1031
|
-
<span class="cstat-no" title="statement not covered" > res.write(</span>
|
|
1032
|
-
'event: message\nid: ' +
|
|
1033
|
-
messageId +
|
|
1034
|
-
'\ndata: ' +
|
|
1035
|
-
JSON.stringify(payload) +
|
|
1036
|
-
'\n\n',
|
|
1037
|
-
);
|
|
1038
|
-
<span class="cstat-no" title="statement not covered" > res.end();</span>
|
|
1039
|
-
} else {
|
|
1040
|
-
<span class="cstat-no" title="statement not covered" > res.json(payload);</span>
|
|
1041
|
-
}
|
|
1042
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1043
|
-
}
|
|
1044
|
-
|
|
1045
|
-
// Resolve the request-scoped tool executor service
|
|
1046
|
-
const contextId = <span class="cstat-no" title="statement not covered" >ContextIdFactory.getByRequest(req);</span>
|
|
1047
|
-
const executor = <span class="cstat-no" title="statement not covered" >await this.moduleRef.resolve(</span>
|
|
1048
|
-
McpExecutorService,
|
|
1049
|
-
contextId,
|
|
1050
|
-
{ strict: false },
|
|
1051
|
-
);
|
|
1052
|
-
|
|
1053
|
-
// Register request handlers with the user context from this specific request
|
|
1054
|
-
<span class="cstat-no" title="statement not covered" > executor.registerRequestHandlers(this.statelessMcpServer!, req);</span>
|
|
1055
|
-
|
|
1056
|
-
// Handle the request with the singleton transport
|
|
1057
|
-
<span class="cstat-no" title="statement not covered" > await this.statelessTransport!.handleRequest(req, res, body);</span>
|
|
1058
|
-
}
|
|
1059
|
-
|
|
1060
|
-
/**
|
|
1061
|
-
* Handle requests in stateful mode
|
|
1062
|
-
*/
|
|
1063
|
-
public <span class="fstat-no" title="function not covered" >async </span>handleStatefulRequest(
|
|
1064
|
-
req: Request,
|
|
1065
|
-
res: Response,
|
|
1066
|
-
body: unknown,
|
|
1067
|
-
): Promise<void> {
|
|
1068
|
-
// Check for existing session ID
|
|
1069
|
-
const sessionId = <span class="cstat-no" title="statement not covered" >req.headers['mcp-session-id'] as string | undefined;</span>
|
|
1070
|
-
let transport: StreamableHTTPServerTransport;
|
|
1071
|
-
|
|
1072
|
-
<span class="cstat-no" title="statement not covered" > if (sessionId && this.transports[sessionId]) {</span>
|
|
1073
|
-
// Reuse existing transport
|
|
1074
|
-
<span class="cstat-no" title="statement not covered" > transport = this.transports[sessionId];</span>
|
|
1075
|
-
} else <span class="cstat-no" title="statement not covered" >if (!sessionId && this.isInitializeRequest(body)) {</span>
|
|
1076
|
-
// New initialization request
|
|
1077
|
-
<span class="cstat-no" title="statement not covered" > transport = new StreamableHTTPServerTransport({</span>
|
|
1078
|
-
sessionIdGenerator:
|
|
1079
|
-
this.options.streamableHttp?.sessionIdGenerator ||
|
|
1080
|
-
(<span class="fstat-no" title="function not covered" >() =</span>> <span class="cstat-no" title="statement not covered" >randomUUID())</span>,
|
|
1081
|
-
enableJsonResponse:
|
|
1082
|
-
this.options.streamableHttp?.enableJsonResponse || false,
|
|
1083
|
-
});
|
|
1084
|
-
|
|
1085
|
-
// Create a new MCP server for this session
|
|
1086
|
-
const mcpServer = <span class="cstat-no" title="statement not covered" >new McpServer(</span>
|
|
1087
|
-
{ name: this.options.name, version: this.options.version },
|
|
1088
|
-
{
|
|
1089
|
-
capabilities: this.options.capabilities || {
|
|
1090
|
-
tools: {},
|
|
1091
|
-
resources: {},
|
|
1092
|
-
resourceTemplates: {},
|
|
1093
|
-
prompts: {},
|
|
1094
|
-
},
|
|
1095
|
-
},
|
|
1096
|
-
);
|
|
1097
|
-
|
|
1098
|
-
// Connect the transport to the MCP server BEFORE handling the request
|
|
1099
|
-
<span class="cstat-no" title="statement not covered" > await mcpServer.connect(transport);</span>
|
|
1100
|
-
|
|
1101
|
-
// Handle the initialization request
|
|
1102
|
-
<span class="cstat-no" title="statement not covered" > await transport.handleRequest(req, res, body);</span>
|
|
1103
|
-
|
|
1104
|
-
// Store the transport and server by session ID for future requests
|
|
1105
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (transport.sessionId) {</span>
|
|
1106
|
-
<span class="cstat-no" title="statement not covered" > this.transports[transport.sessionId] = transport;</span>
|
|
1107
|
-
<span class="cstat-no" title="statement not covered" > this.mcpServers[transport.sessionId] = mcpServer;</span>
|
|
1108
|
-
|
|
1109
|
-
// Set up cleanup when connection closes
|
|
1110
|
-
<span class="cstat-no" title="statement not covered" > transport.onclose = <span class="fstat-no" title="function not covered" >() =</span>> {</span>
|
|
1111
|
-
<span class="cstat-no" title="statement not covered" > this.cleanupSession(transport.sessionId!);</span>
|
|
1112
|
-
};
|
|
1113
|
-
}
|
|
1114
|
-
|
|
1115
|
-
<span class="cstat-no" title="statement not covered" > this.logger.log(</span>
|
|
1116
|
-
`Initialized new session with ID: ${transport.sessionId}`,
|
|
1117
|
-
);
|
|
1118
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1119
|
-
} else {
|
|
1120
|
-
// Invalid request - no session ID or not initialization request
|
|
1121
|
-
<span class="cstat-no" title="statement not covered" > res.status(400).json({</span>
|
|
1122
|
-
jsonrpc: '2.0',
|
|
1123
|
-
error: {
|
|
1124
|
-
code: -32000,
|
|
1125
|
-
message: 'Bad Request: No valid session ID provided',
|
|
1126
|
-
},
|
|
1127
|
-
id: null,
|
|
1128
|
-
});
|
|
1129
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1130
|
-
}
|
|
1131
|
-
|
|
1132
|
-
// For subsequent requests to an existing session
|
|
1133
|
-
const mcpServer = <span class="cstat-no" title="statement not covered" >this.mcpServers[sessionId];</span>
|
|
1134
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (!mcpServer) {</span>
|
|
1135
|
-
<span class="cstat-no" title="statement not covered" > res.status(404).json({</span>
|
|
1136
|
-
jsonrpc: '2.0',
|
|
1137
|
-
error: {
|
|
1138
|
-
code: -32000,
|
|
1139
|
-
message: 'Session not found',
|
|
1140
|
-
},
|
|
1141
|
-
id: null,
|
|
1142
|
-
});
|
|
1143
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1144
|
-
}
|
|
1145
|
-
|
|
1146
|
-
// Resolve the request-scoped tool executor service
|
|
1147
|
-
const contextId = <span class="cstat-no" title="statement not covered" >ContextIdFactory.getByRequest(req);</span>
|
|
1148
|
-
const executor = <span class="cstat-no" title="statement not covered" >await this.moduleRef.resolve(</span>
|
|
1149
|
-
McpExecutorService,
|
|
1150
|
-
contextId,
|
|
1151
|
-
{ strict: false },
|
|
1152
|
-
);
|
|
1153
|
-
|
|
1154
|
-
// Register request handlers with the user context from this specific request
|
|
1155
|
-
<span class="cstat-no" title="statement not covered" > executor.registerRequestHandlers(mcpServer, req);</span>
|
|
1156
|
-
|
|
1157
|
-
// Handle the request with existing transport
|
|
1158
|
-
<span class="cstat-no" title="statement not covered" > await transport.handleRequest(req, res, body);</span>
|
|
1159
|
-
}
|
|
1160
|
-
|
|
1161
|
-
/**
|
|
1162
|
-
* GET endpoint for SSE streams
|
|
1163
|
-
*/
|
|
1164
|
-
@Get(endpoint)
|
|
1165
|
-
@UseGuards(...guards)
|
|
1166
|
-
<span class="fstat-no" title="function not covered" > async </span>handleGetRequest(@Req() req: Request, @Res() res: Response) {
|
|
1167
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (this.isStatelessMode) {</span>
|
|
1168
|
-
<span class="cstat-no" title="statement not covered" > return this.handleStatelessRequest(req, res, req.body);</span>
|
|
1169
|
-
}
|
|
1170
|
-
|
|
1171
|
-
const sessionId = <span class="cstat-no" title="statement not covered" >req.headers['mcp-session-id'] as string | undefined;</span>
|
|
1172
|
-
|
|
1173
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (!sessionId || !this.transports[sessionId]) {</span>
|
|
1174
|
-
<span class="cstat-no" title="statement not covered" > res.status(400).send('Invalid or missing session ID');</span>
|
|
1175
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1176
|
-
}
|
|
1177
|
-
|
|
1178
|
-
<span class="cstat-no" title="statement not covered" > this.logger.debug(`Establishing SSE stream for session ${sessionId}`);</span>
|
|
1179
|
-
const transport = <span class="cstat-no" title="statement not covered" >this.transports[sessionId];</span>
|
|
1180
|
-
<span class="cstat-no" title="statement not covered" > await transport.handleRequest(req, res);</span>
|
|
1181
|
-
}
|
|
1182
|
-
|
|
1183
|
-
/**
|
|
1184
|
-
* DELETE endpoint for terminating sessions
|
|
1185
|
-
*/
|
|
1186
|
-
@Delete(endpoint)
|
|
1187
|
-
@UseGuards(...guards)
|
|
1188
|
-
<span class="fstat-no" title="function not covered" > async </span>handleDeleteRequest(@Req() req: Request, @Res() res: Response) {
|
|
1189
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (this.isStatelessMode) {</span>
|
|
1190
|
-
// In stateless mode, we don't have sessions to delete
|
|
1191
|
-
<span class="cstat-no" title="statement not covered" > res.status(200).end();</span>
|
|
1192
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1193
|
-
}
|
|
1194
|
-
|
|
1195
|
-
const sessionId = <span class="cstat-no" title="statement not covered" >req.headers['mcp-session-id'] as string | undefined;</span>
|
|
1196
|
-
|
|
1197
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (!sessionId || !this.transports[sessionId]) {</span>
|
|
1198
|
-
<span class="cstat-no" title="statement not covered" > res.status(400).send('Invalid or missing session ID');</span>
|
|
1199
|
-
<span class="cstat-no" title="statement not covered" > return;</span>
|
|
1200
|
-
}
|
|
1201
|
-
|
|
1202
|
-
<span class="cstat-no" title="statement not covered" > this.logger.debug(`Terminating session ${sessionId}`);</span>
|
|
1203
|
-
const transport = <span class="cstat-no" title="statement not covered" >this.transports[sessionId];</span>
|
|
1204
|
-
<span class="cstat-no" title="statement not covered" > await transport.handleRequest(req, res);</span>
|
|
1205
|
-
<span class="cstat-no" title="statement not covered" > this.cleanupSession(sessionId);</span>
|
|
1206
|
-
}
|
|
1207
|
-
|
|
1208
|
-
// Helper function to detect initialize requests
|
|
1209
|
-
public <span class="fstat-no" title="function not covered" >isInitializeRequest(</span>body: unknown): boolean {
|
|
1210
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (Array.isArray(body)) {</span>
|
|
1211
|
-
<span class="cstat-no" title="statement not covered" > return body.some(</span>
|
|
1212
|
-
<span class="fstat-no" title="function not covered" > (m</span>sg) =>
|
|
1213
|
-
<span class="cstat-no" title="statement not covered" > typeof msg === 'object' &&</span>
|
|
1214
|
-
msg !== null &&
|
|
1215
|
-
'method' in msg &&
|
|
1216
|
-
msg.method === 'initialize',
|
|
1217
|
-
);
|
|
1218
|
-
}
|
|
1219
|
-
<span class="cstat-no" title="statement not covered" > return (</span>
|
|
1220
|
-
typeof body === 'object' &&
|
|
1221
|
-
body !== null &&
|
|
1222
|
-
'method' in body &&
|
|
1223
|
-
body.method === 'initialize'
|
|
1224
|
-
);
|
|
1225
|
-
}
|
|
1226
|
-
|
|
1227
|
-
// Clean up session resources
|
|
1228
|
-
public <span class="fstat-no" title="function not covered" >cleanupSession(</span>sessionId: string): void {
|
|
1229
|
-
<span class="cstat-no" title="statement not covered" > <span class="missing-if-branch" title="if path not taken" >I</span>if (sessionId) {</span>
|
|
1230
|
-
<span class="cstat-no" title="statement not covered" > this.logger.debug(`Cleaning up session: ${sessionId}`);</span>
|
|
1231
|
-
<span class="cstat-no" title="statement not covered" > delete this.transports[sessionId];</span>
|
|
1232
|
-
<span class="cstat-no" title="statement not covered" > delete this.mcpServers[sessionId];</span>
|
|
1233
|
-
}
|
|
1234
|
-
}
|
|
1235
|
-
}
|
|
1236
|
-
|
|
1237
|
-
return StreamableHttpController;
|
|
1238
|
-
}
|
|
1239
|
-
</pre></td></tr></table></pre>
|
|
1240
|
-
|
|
1241
|
-
<div class='push'></div><!-- for sticky footer -->
|
|
1242
|
-
</div><!-- /wrapper -->
|
|
1243
|
-
<div class='footer quiet pad2 space-top1 center small'>
|
|
1244
|
-
Code coverage generated by
|
|
1245
|
-
<a href="https://istanbul.js.org/" target="_blank" rel="noopener noreferrer">istanbul</a>
|
|
1246
|
-
at 2025-04-26T05:28:42.460Z
|
|
1247
|
-
</div>
|
|
1248
|
-
<script src="../prettify.js"></script>
|
|
1249
|
-
<script>
|
|
1250
|
-
window.onload = function () {
|
|
1251
|
-
prettyPrint();
|
|
1252
|
-
};
|
|
1253
|
-
</script>
|
|
1254
|
-
<script src="../sorter.js"></script>
|
|
1255
|
-
<script src="../block-navigation.js"></script>
|
|
1256
|
-
</body>
|
|
1257
|
-
</html>
|
|
1258
|
-
|