Skip to content

feat: bot file transfer, mobile file download, and relay server improvements#100

Merged
GCWing merged 2 commits intoGCWing:mainfrom
bobleer:pr/bot-file-transfer-mobile-file-download-20250309
Mar 9, 2026
Merged

feat: bot file transfer, mobile file download, and relay server improvements#100
GCWing merged 2 commits intoGCWing:mainfrom
bobleer:pr/bot-file-transfer-mobile-file-download-20250309

Conversation

@bobleer
Copy link
Contributor

@bobleer bobleer commented Mar 9, 2026

Summary

  • Bot file transfer: Feishu and Telegram bots can now detect computer:// links in AI responses, present download buttons, and transfer workspace files to users (Feishu IM file API / Telegram sendDocument, ≤30MB).
  • Mobile file download: computer:// links in chat messages render as interactive FileCard components with file metadata, progress bar, and browser save-as download via chunked transfer (3MB chunks).
  • Relay server deployment: Standalone Dockerfile (no workspace deps), remote-deploy.sh for SSH-based deployment, WebSocket 64MB limits across relay server and client.
  • Terminal & input fixes: Fix pty_to_session mapping race, IME composition handling for Safari, smart auto-scroll (only when near bottom), theme flash elimination.

Changes

Bot File Transfer

  • bot/mod.rs: Shared utilities — resolve_workspace_path, read_workspace_file, detect_mime_type, extract_computer_file_paths, format_file_size, WorkspaceFileContent
  • bot/feishu.rs: upload_file_to_feishu, send_file_to_feishu_chat, notify_files_ready, handle_download_request; graceful stop signal for pairing loop
  • bot/telegram.rs: send_message_with_keyboard, send_file_as_document, notify_files_ready, handle_download_request, download_photo (image support); inline keyboard buttons; send_handle_result with clean_reply_text
  • bot/command_router.rs: ForwardedTurnResult struct; auto-inherit workspace; updated execute_forwarded_turn to return full_text for link extraction

Remote Server

  • remote_server.rs: ReadFile, ReadFileChunk, GetFileInfo commands; terminal pre-warming; broadcast buffer 256→1024; accumulated_text() accessor
  • relay_client.rs: WebSocket config with 64MB limits
  • mod.rs: Graceful stop signal for bot pairing; race guard on bot_connected_info

Mobile Web

  • ChatPage.tsx: FileCard component with chunked download + progress; MarkdownContent custom a renderer; IME composition guards; useLayoutEffect initial scroll; near-bottom auto-scroll logic
  • RemoteSessionManager.ts: readFile() chunked transfer, getFileInfo()
  • ThemeProvider.tsx: CSS transition class approach; commitThemeDOM; pre-cached CSS
  • index.html: Inline theme script before first paint
  • global.scss: iOS-style navigation animations with z-index layering; theme-switching class

Relay Server Deployment

  • Simplified standalone Dockerfile (Rust 1.85, no workspace)
  • docker-compose.yml: Caddy commented out, room-web volume
  • remote-deploy.sh: SSH-based deployment script
  • deploy.sh: Stop old containers before rebuild
  • README.md: Local vs remote deploy docs

Fixes

  • terminal/session/manager.rs: Retry pty_to_session lookup for non-Data events; accept Starting session status
  • RichTextInput.tsx: Safari IME fix (delayed isComposingRef clear)
  • WebSocket max_frame_size / max_write_buffer_size 64MB

Test Plan

  • Feishu bot: AI creates a file → response contains computer:// link → user taps download button → file delivered to chat
  • Telegram bot: Same flow with inline keyboard download buttons
  • Mobile web: AI response with computer:// link → FileCard renders with name/size → tap to download → progress bar → browser save dialog
  • Mobile web: Chunked download for files >3MB works correctly
  • Mobile web: IME input (Chinese/Japanese) on Safari → Enter commits without double-send
  • Mobile web: Theme switch → no flash, smooth CSS transition
  • Mobile web: Scroll to bottom only when user is near bottom; scrolling up stays stable
  • Relay server: bash deploy.sh local deploy works; bash remote-deploy.sh <host> SSH deploy works
  • Terminal: Remote session BashTool execution starts without 30s delay (pre-warm)

Made with Cursor

bowen628 added 2 commits March 9, 2026 20:59
…vements

## Bot file transfer (Feishu + Telegram)
- Extract `computer://` links from AI responses and offer download buttons
- Feishu: upload files via IM file API (≤30MB), send as file messages
- Telegram: send files via sendDocument API (≤30MB), inline keyboard buttons
- Shared utilities in bot/mod.rs: resolve_workspace_path, read_workspace_file,
  detect_mime_type, extract_computer_file_paths, format_file_size
- ForwardedTurnResult replaces plain String to carry both display_text and
  full_text for link extraction
- pending_files map on BotChatState for download token management
- Auto-inherit desktop workspace when bot session has none
- Graceful stop signal (watch channel) for bot pairing loops

## Remote server file commands
- Add ReadFile, ReadFileChunk, GetFileInfo commands
- Chunked transfer with 3MB raw chunks (4MB base64) for large files
- Terminal pre-warming for remote sessions (avoids 30s shell readiness wait)
- Increase broadcast channel buffer from 256 to 1024
- accumulated_text() accessor on RemoteSessionStateTracker

## Mobile web file download
- FileCard component renders `computer://` links as interactive cards with
  name, size, and download progress indicator
- MarkdownContent: custom `a` renderer for computer:// links + urlTransform
  to preserve the protocol
- RemoteSessionManager: readFile() with chunked transfer + progress callback,
  getFileInfo() for metadata-only queries
- Download triggers browser save dialog via blob URL

## Relay server deployment
- Standalone Dockerfile (no workspace dependency, Rust 1.85)
- Simplified docker-compose.yml (Caddy commented out)
- Add remote-deploy.sh for SSH-based deployment from dev machine
- Updated README with local vs remote deploy instructions
- WS max_frame_size and max_write_buffer_size set to 64MB
- Relay client WebSocket config with matching 64MB limits

## Terminal & input fixes
- Fix pty_to_session mapping race: retry lookup for non-Data events
- Accept Starting session status when shell integration reaches Prompt
- RichTextInput: fix IME composition handling for Safari (delayed clear)
- Mobile ChatPage: IME compositionStart/End guards on textarea
- Improved scroll behavior: only auto-scroll when near bottom
- useLayoutEffect for initial scroll to prevent flash
- Theme switching: CSS transition class instead of opacity crossfade
- index.html: inline script reads saved theme before first paint
- Navigation animations: iOS-style full-width slide with z-index layering

Made-with: Cursor
- Keep our delayed isComposingRef clear (Safari fix) while preserving
  upstream's onCompositionEnd callback propagation

Made-with: Cursor
@GCWing GCWing merged commit 2c617c3 into GCWing:main Mar 9, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants