@@ -307,70 +307,50 @@ function ToolCallInfoPanel({ toolCallInfo, isDestroying, onRequestClose, onClose
307307 }
308308 } , [ isDestroying , isApp , onCloseComplete ] ) ;
309309
310+ const inputJson = JSON . stringify ( toolCallInfo . input , null , 2 ) ;
311+
310312 return (
311313 < div
312314 className = { styles . toolCallInfoPanel }
313315 style = { isDestroying ? { opacity : 0.5 , pointerEvents : "none" } : undefined }
314316 >
315- { /* For non-app tools, show input/output side by side */ }
316- { ! isApp && (
317- < div className = { styles . inputInfoPanel } >
318- < h2 >
319- < span > { toolCallInfo . serverInfo . name } </ span >
320- < span className = { styles . toolName } > { toolCallInfo . tool . name } </ span >
321- { onRequestClose && ! isDestroying && (
322- < button
323- className = { styles . closeButton }
324- onClick = { onRequestClose }
325- title = "Close"
326- >
327- ×
328- </ button >
329- ) }
330- </ h2 >
331- < JsonBlock value = { toolCallInfo . input } />
332- </ div >
333- ) }
334- < div className = { isApp ? styles . appOutputPanel : styles . outputInfoPanel } >
335- { /* For apps, show header above the app: ServerName:tool_name */ }
336- { isApp && (
337- < div className = { styles . appHeader } >
338- < span > { toolCallInfo . serverInfo . name } :< span className = { styles . toolName } > { toolCallInfo . tool . name } </ span > </ span >
339- { onRequestClose && ! isDestroying && (
340- < button
341- className = { styles . closeButton }
342- onClick = { onRequestClose }
343- title = "Close"
344- >
345- ×
346- </ button >
347- ) }
348- </ div >
317+ { /* Row 1: Header with server:tool name and close button */ }
318+ < div className = { styles . appHeader } >
319+ < span > { toolCallInfo . serverInfo . name } :< span className = { styles . toolName } > { toolCallInfo . tool . name } </ span > </ span >
320+ { onRequestClose && ! isDestroying && (
321+ < button
322+ className = { styles . closeButton }
323+ onClick = { onRequestClose }
324+ title = "Close"
325+ >
326+ ×
327+ </ button >
349328 ) }
329+ </ div >
330+
331+ { /* Row 2: Tool Input */ }
332+ < CollapsiblePanel icon = "📥" label = "Tool Input" content = { inputJson } />
333+
334+ { /* Row 3: App iframe (if app) */ }
335+ { isApp && (
350336 < ErrorBoundary >
351337 < Suspense fallback = "Loading..." >
352- {
353- isApp
354- ? < AppIFramePanel
355- toolCallInfo = { toolCallInfo }
356- isDestroying = { isDestroying }
357- onTeardownComplete = { onCloseComplete }
358- />
359- : < ToolResultPanel toolCallInfo = { toolCallInfo } />
360- }
338+ < AppIFramePanel
339+ toolCallInfo = { toolCallInfo }
340+ isDestroying = { isDestroying }
341+ onTeardownComplete = { onCloseComplete }
342+ />
361343 </ Suspense >
362344 </ ErrorBoundary >
363- </ div >
364- </ div >
365- ) ;
366- }
367-
345+ ) }
368346
369- function JsonBlock ( { value } : { value : object } ) {
370- return (
371- < pre className = { styles . jsonBlock } >
372- < code > { JSON . stringify ( value , null , 2 ) } </ code >
373- </ pre >
347+ { /* Row 4: Tool Result */ }
348+ < ErrorBoundary >
349+ < Suspense fallback = "Loading result..." >
350+ < ToolResultPanel toolCallInfo = { toolCallInfo } />
351+ </ Suspense >
352+ </ ErrorBoundary >
353+ </ div >
374354 ) ;
375355}
376356
@@ -421,7 +401,6 @@ function AppIFramePanel({ toolCallInfo, isDestroying, onTeardownComplete }: AppI
421401 const iframeRef = useRef < HTMLIFrameElement | null > ( null ) ;
422402 const appBridgeRef = useRef < ReturnType < typeof newAppBridge > | null > ( null ) ;
423403 const [ modelContext , setModelContext ] = useState < ModelContext | null > ( null ) ;
424- const [ toolResult , setToolResult ] = useState < object | null > ( null ) ;
425404 const [ messages , setMessages ] = useState < AppMessage [ ] > ( [ ] ) ;
426405 const [ displayMode , setDisplayMode ] = useState < "inline" | "fullscreen" > ( "inline" ) ;
427406
@@ -452,8 +431,6 @@ function AppIFramePanel({ toolCallInfo, isDestroying, onTeardownComplete }: AppI
452431 } ) ;
453432 } ) ;
454433
455- // Track tool result for display
456- toolCallInfo . resultPromise . then ( setToolResult ) . catch ( ( ) => { } ) ;
457434 } , [ toolCallInfo ] ) ;
458435
459436 // Graceful teardown: wait for guest to respond before unmounting
@@ -501,9 +478,6 @@ function AppIFramePanel({ toolCallInfo, isDestroying, onTeardownComplete }: AppI
501478 : "" ;
502479 const fullContext = [ contextText , contextJson ] . filter ( Boolean ) . join ( "\n\n" ) ;
503480
504- const inputJson = JSON . stringify ( toolCallInfo . input , null , 2 ) ;
505- const resultJson = toolResult ? JSON . stringify ( toolResult , null , 2 ) : null ;
506-
507481 // Format messages
508482 const formatMessage = ( m : AppMessage ) => {
509483 const content = m . content . map ( formatContentBlock ) . join ( "\n" ) ;
@@ -517,11 +491,7 @@ function AppIFramePanel({ toolCallInfo, isDestroying, onTeardownComplete }: AppI
517491
518492 return (
519493 < div className = { panelClassName } >
520- < CollapsiblePanel icon = "📥" label = "Tool Input" content = { inputJson } />
521494 < iframe ref = { iframeRef } />
522- { resultJson && (
523- < CollapsiblePanel icon = "📤" label = "Tool Result" content = { resultJson } />
524- ) }
525495 { messages . length > 0 && (
526496 < CollapsiblePanel
527497 icon = "💬"
@@ -543,7 +513,8 @@ interface ToolResultPanelProps {
543513}
544514function ToolResultPanel ( { toolCallInfo } : ToolResultPanelProps ) {
545515 const result = use ( toolCallInfo . resultPromise ) ;
546- return < JsonBlock value = { result } /> ;
516+ const resultJson = JSON . stringify ( result , null , 2 ) ;
517+ return < CollapsiblePanel icon = "📤" label = "Tool Result" content = { resultJson } /> ;
547518}
548519
549520
0 commit comments