1
1
package cc.unitmesh.devti.mcp.ui
2
2
3
+ import cc.unitmesh.devti.AutoDevNotifications
4
+ import cc.unitmesh.devti.mcp.client.CustomMcpServerManager
5
+ import cc.unitmesh.devti.mcp.ui.model.McpLlmConfig
3
6
import cc.unitmesh.devti.util.parser.CodeFence
7
+ import com.intellij.openapi.project.Project
4
8
import com.intellij.ui.JBColor
5
9
import com.intellij.ui.components.JBLabel
6
10
import com.intellij.ui.components.JBScrollPane
7
11
import com.intellij.ui.components.JBTabbedPane
8
12
import com.intellij.util.ui.JBUI
9
13
import com.intellij.util.ui.UIUtil
14
+ import io.modelcontextprotocol.kotlin.sdk.Tool
15
+ import kotlinx.serialization.encodeToString
16
+ import kotlinx.serialization.json.Json
10
17
import java.awt.BorderLayout
18
+ import java.awt.FlowLayout
11
19
import java.awt.GridBagConstraints
12
20
import java.awt.GridBagLayout
13
21
import java.io.StringReader
@@ -16,7 +24,10 @@ import javax.swing.border.CompoundBorder
16
24
import javax.swing.border.EmptyBorder
17
25
import javax.swing.border.MatteBorder
18
26
19
- class McpResultPanel : JPanel (BorderLayout ()) {
27
+ class McpResultPanel (private val project : Project , val config : McpLlmConfig ) : JPanel(BorderLayout ()) {
28
+ private val mcpServerManager = CustomMcpServerManager .instance(project)
29
+ private val json = Json { prettyPrint = true }
30
+
20
31
private val rawResultTextArea = JTextArea ().apply {
21
32
isEditable = false
22
33
wrapStyleWord = true
@@ -162,12 +173,106 @@ class McpResultPanel : JPanel(BorderLayout()) {
162
173
paramsPanel.add(valueLabel, valueGbc)
163
174
}
164
175
176
+ // Add execute button and result panel
177
+ val executeButton = JButton (" Execute" ).apply {
178
+ font = JBUI .Fonts .label(12f )
179
+ addActionListener {
180
+ executeToolCall(toolCall, panel)
181
+ }
182
+ }
183
+
184
+ val buttonsPanel = JPanel (FlowLayout (FlowLayout .LEFT )).apply {
185
+ isOpaque = false
186
+ add(executeButton)
187
+ }
188
+
189
+ val resultPanel = JPanel (BorderLayout ()).apply {
190
+ isOpaque = false
191
+ border = JBUI .Borders .emptyTop(8 )
192
+ isVisible = false
193
+ }
194
+
195
+ val contentPanel = JPanel (BorderLayout ()).apply {
196
+ isOpaque = false
197
+ add(paramsPanel, BorderLayout .CENTER )
198
+ add(buttonsPanel, BorderLayout .SOUTH )
199
+ }
200
+
165
201
panel.add(titleLabel, BorderLayout .NORTH )
166
- panel.add(paramsPanel, BorderLayout .CENTER )
202
+ panel.add(contentPanel, BorderLayout .CENTER )
203
+ panel.add(resultPanel, BorderLayout .SOUTH )
167
204
168
205
return panel
169
206
}
170
207
208
+ private fun executeToolCall (toolCall : ToolCall , parentPanel : JPanel ) {
209
+ val panel = parentPanel.components
210
+ .filterIsInstance<JPanel >()
211
+ .find { it.border != null && it.border.toString().contains(" empty" ) }
212
+
213
+ if (panel == null ) {
214
+ AutoDevNotifications .error(project, " Cannot find result panel" )
215
+ return
216
+ }
217
+
218
+ panel.removeAll()
219
+ panel.layout = BorderLayout ()
220
+
221
+ // Create loading indicator
222
+ val loadingLabel = JBLabel (" Executing tool ${toolCall.name} ..." ).apply {
223
+ horizontalAlignment = SwingConstants .CENTER
224
+ }
225
+ panel.add(loadingLabel, BorderLayout .CENTER )
226
+ panel.isVisible = true
227
+ panel.revalidate()
228
+ panel.repaint()
229
+
230
+ // Run execution in background
231
+ SwingUtilities .invokeLater {
232
+ // Convert parameters to JSON
233
+ val params = try {
234
+ val jsonParams = json.encodeToString(toolCall.parameters)
235
+ jsonParams
236
+ } catch (e: Exception ) {
237
+ " {}"
238
+ }
239
+
240
+ // Find matching tool
241
+ val matchingTool = findMatchingTool(toolCall.name)
242
+
243
+ val result = if (matchingTool != null ) {
244
+ mcpServerManager!! .execute(project, matchingTool, params)
245
+ } else {
246
+ " Error: Could not find matching tool '${toolCall.name} '"
247
+ }
248
+
249
+ // Display result
250
+ panel.removeAll()
251
+ val textArea = JTextArea (result).apply {
252
+ lineWrap = true
253
+ wrapStyleWord = true
254
+ isEditable = false
255
+ font = JBUI .Fonts .create(" Monospaced" , 12 )
256
+ border = JBUI .Borders .empty(4 )
257
+ }
258
+
259
+ panel.add(JBScrollPane (textArea), BorderLayout .CENTER )
260
+ panel.isVisible = true
261
+ panel.revalidate()
262
+ panel.repaint()
263
+ }
264
+ }
265
+
266
+ private fun findMatchingTool (toolName : String ): Tool ? {
267
+ for (tool in config.enabledTools) {
268
+ if (tool.name == toolName) {
269
+ return tool
270
+ }
271
+ }
272
+
273
+ return null
274
+ }
275
+
171
276
data class ToolCall (
172
277
val name : String ,
173
278
val parameters : Map <String , String >
0 commit comments