Commit graph

17 commits

Author SHA1 Message Date
Mario Zechner
3932c5e04c Add lifecycle callbacks to SandboxRuntimeProvider for abort signal support
- Added onExecutionStart(sandboxId, signal) - called when sandbox execution begins
- Added onExecutionEnd(sandboxId) - called when sandbox execution ends
- Integrated callbacks in SandboxedIframe.execute()
- Enables providers to track and cancel async operations (e.g., userScript executions)
2025-11-16 00:56:20 +01:00
Mario Zechner
26b774bb04 Add standalone mode for HTML artifact downloads
When downloading HTML artifacts, the generated HTML now works standalone
without requiring the extension runtime.

Changes:
- Add PrepareHtmlOptions config object to SandboxedIframe.prepareHtmlDocument()
- Add isStandalone flag to skip runtime bridge and navigation interceptor
- When isStandalone=true:
  - window.sendRuntimeMessage is NOT defined
  - Navigation interceptor is NOT injected
  - Artifact runtime providers fall back to embedded data
- HtmlArtifact download button now uses isStandalone: true

This fixes the issue where downloaded HTML artifacts would:
- Try to call window.sendRuntimeMessage (which would fail silently)
- Try to postMessage to non-existent parent window
- Not work when opened via file:// protocol

Now downloaded artifacts work completely standalone with embedded data.
2025-10-12 00:39:26 +02:00
Mario Zechner
63bfe95c18 Fix up context check 2025-10-11 21:41:24 +02:00
Mario Zechner
98ea763d64 Intercept iframe navigation and open links externally
- Add navigation interceptor script that prevents all iframe navigation
- Intercept link clicks, form submissions, and window.location changes
- Send open-external-url messages to parent window
- Use chrome.tabs.create() in extension context, window.open() fallback
- Fix font-size workaround to use 'initial' instead of hardcoded 16px
- Document Chrome extension font-size bug with Stack Overflow reference

This prevents HTML artifacts from navigating away when users click links,
which would break the sandbox message system. All links now open in new
Chrome tabs instead.
2025-10-11 19:13:04 +02:00
Mario Zechner
2a67556e5d Fix font-size inheritance in HTML artifact iframes
Set explicit font-size: 16px on the <html> element in sandboxed iframes
to prevent browser default inheritance quirks that can cause unexpected
font sizes (e.g., 75% shown in devtools).

This establishes a consistent base font size while still allowing user
HTML content to override it on body or specific elements as needed.

Fixes the issue where HTML artifacts displayed with inconsistent font
sizes due to iframe inheritance behavior.
2025-10-11 18:46:55 +02:00
Mario Zechner
b129154cc8 Add ToolRenderResult interface for custom tool rendering
- Changed ToolRenderer return type from TemplateResult to ToolRenderResult
- ToolRenderResult = { content: TemplateResult, isCustom: boolean }
- isCustom: true = no card wrapper, false = wrap in card
- Updated all existing tool renderers to return new format
- Updated Messages.ts to handle custom rendering

This enables tools to render without default card chrome when needed.
2025-10-11 04:40:42 +02:00
Mario Zechner
4ac774cbbb Fix console logging and message routing
Console Logging Improvements:
- Changed ConsoleRuntimeProvider to send logs immediately instead of batching
- Track pending send promises and await them in onCompleted callback
- Ensures REPL gets all logs before execution-complete
- Enables real-time console logging for HTML artifacts

Message Routing Fixes:
- Remove "handled" concept from message routing - broadcast all messages to all providers/consumers
- Change handleMessage return type from Promise<boolean> to Promise<void>
- Add debug logging to RuntimeMessageRouter to trace message flow
- Fix duplicate error logging (window error handler now only tracks errors, doesn't log them)

Output Formatting Consistency:
- Remove [LOG], [ERROR] prefixes from console output in both tools
- Show console logs before error messages
- Use "=> value" format for return values in both javascript-repl and browser-javascript
- Remove duplicate "Error:" prefix and extra formatting

Bug Fixes:
- Fix race condition where execution-complete arrived before console logs
- Fix ConsoleRuntimeProvider blocking execution-complete from reaching consumers
- Remove duplicate console log collection from SandboxedIframe
- Fix return value capture by wrapping user code in async function
2025-10-09 23:20:14 +02:00
Mario Zechner
8747e01c31 Display return values and fix duplicate error messages in REPL
- javascript-repl now displays return values with => prefix
- Objects are JSON.stringify'd with formatting
- Removed console.error from wrapper to prevent duplicate error messages
- Error is already captured and sent via execution-error message
- Fixes missing return value display and duplicate error output
2025-10-09 20:51:25 +02:00
Mario Zechner
5fc3857666 Pass return value through execution-complete message instead of logging
- Return value now passed to window.complete(error, returnValue)
- execution-complete message includes returnValue field
- SandboxResult interface updated to include returnValue
- executionConsumer passes returnValue in resolved promise
- Return values properly captured and available to callers
2025-10-09 20:47:26 +02:00
Mario Zechner
9a3f01fcb8 Fix REPL timeout with return statements by wrapping user code in function
- User code with return statement was exiting the async IIFE early
- Completion callbacks and window.complete() were never reached
- Now wrap user code in userCodeFunc to capture return value
- Return statement returns from userCodeFunc, not outer IIFE
- Completion callbacks and window.complete() always execute
- Return value is logged to console output
- Fixes 30-second timeout when using return statements in REPL
2025-10-09 20:43:39 +02:00
Mario Zechner
5dcb5ecc89 Fix race condition by making window.complete() async and awaiting it
- window.complete() was fire-and-forget, causing execution-complete to arrive before console messages
- This caused sandbox to unregister before console message responses arrived
- Made complete() async and await sendRuntimeMessage()
- SandboxedIframe wrapper now awaits window.complete()
- Ensures all messages are processed before cleanup/unregister
- Fixes 30-second timeout on javascript_repl
2025-10-09 20:31:48 +02:00
Mario Zechner
33418d9dea Unify completion callback pattern across browser-javascript and javascript-repl
- Remove fallback timeout from ConsoleRuntimeProvider (was causing 2s delays)
- Add completion callback support to SandboxedIframe REPL wrapper
- Call completion callbacks before window.complete() in both success/error paths
- Both browser-javascript and javascript-repl now use identical completion pattern
- Ensures console logs are batched and sent before execution completes
2025-10-09 20:24:20 +02:00
Mario Zechner
c2793d8017 Add runtime bridge architecture and fix HTML escaping
Major refactoring to unify runtime providers across sandbox and user script contexts:

1. Runtime Bridge & Router
   - Add RuntimeMessageBridge for unified messaging abstraction
   - Rename SandboxMessageRouter → RuntimeMessageRouter
   - Router now handles both iframe and user script messages
   - Guard for non-extension environments

2. Provider Refactoring
   - ArtifactsRuntimeProvider: Add offline mode with snapshot fallback
   - AttachmentsRuntimeProvider: Remove returnDownloadableFile (moved to dedicated provider)
   - ConsoleRuntimeProvider: Add message collection, remove lifecycle logic
   - FileDownloadRuntimeProvider: New provider for file downloads

3. HTML Escaping Fix
   - Escape </script> in JSON.stringify output to prevent premature tag closure
   - Applies when injecting provider data into <script> tags
   - JavaScript engine automatically unescapes, no runtime changes needed

4. Function Renaming
   - listFiles → listAttachments
   - readTextFile → readTextAttachment
   - readBinaryFile → readBinaryAttachment
   - returnFile → returnDownloadableFile

5. Updated Exports
   - Export new RuntimeMessageBridge and RuntimeMessageRouter
   - Export FileDownloadRuntimeProvider
   - Update all cross-references

This sets the foundation for reusing providers in browser-javascript tool.
2025-10-09 17:32:45 +02:00
Mario Zechner
4d2ca6ab2a Add artifact message persistence for session reconstruction
- Add ArtifactMessage type as core part of AppMessage union (not CustomMessages)
- ArtifactsRuntimeProvider appends artifact messages on create/update/delete
- MessageList filters out artifact messages (UI display only)
- artifacts.ts reconstructFromMessages handles artifact messages
- Export ARTIFACTS_RUNTIME_PROVIDER_DESCRIPTION from main index
- Fix artifact creation bug: pass filename as title instead of mimeType

Changes:
- web-ui/src/components/Messages.ts: Add ArtifactMessage to BaseMessage union
- web-ui/src/components/MessageList.ts: Skip artifact messages in render
- web-ui/src/components/sandbox/ArtifactsRuntimeProvider.ts: Append messages, fix title parameter
- web-ui/src/ChatPanel.ts: Pass agent.appendMessage callback
- web-ui/src/tools/artifacts/artifacts.ts: Handle artifact messages in reconstructFromMessages
- web-ui/src/index.ts: Export ARTIFACTS_RUNTIME_PROVIDER_DESCRIPTION
- web-ui/example/src/custom-messages.ts: Update message transformer to filter artifacts
2025-10-09 04:07:59 +02:00
Mario Zechner
0eaa879d46 Fix various sandbox issues. 2025-10-08 22:51:32 +02:00
Mario Zechner
f2eecb78d2 web-ui package 2025-10-05 13:30:08 +02:00
Mario Zechner
0af33ce79a Fix race condition in web-ui SandboxedIframe
Fixed loadContent() and execute() to set srcdoc at the correct time:
- loadContent(): Now sets srcdoc after creating iframe (was missing entirely)
- execute(): Now sets srcdoc after setting up message listeners and creating iframe (was setting before iframe existed)

This prevents missing postMessage events from the sandboxed iframe.
2025-10-04 19:09:17 +02:00