- Add try-catch wrapper around uploadFoldersCompressed to handle compression failures gracefully
- Implement fallback to regular upload when compressed upload is not supported
- Check for failed folders in compressed results and trigger full fallback if needed
- Return error indicator from uploadFoldersCompressed instead of attempting inline fallback
- Improve error logging to distinguish between compression support issues and other failures
- Ensure all entries are uploaded via regular upload path when compression is unavailable
- This prevents upload failures when the server doesn't support compressed folder uploads
- Add CompressedUploadDialog component to let users choose between compressed and regular transfer methods
- Implement compressUploadService for handling folder compression and extraction on the server
- Add compressUploadBridge to expose compression functionality to the renderer process
- Add sftpUseCompressedUpload setting with three modes: ask, enabled, disabled
- Add new upload progress states: compressing, extracting, scanning, completed
- Add i18n translations for upload dialog and settings in English and Chinese
- Update SFTP modal to support compressed upload workflow with progress tracking
- Add storage key for persisting compressed upload preference across sessions
- Significantly reduces transfer time for folders by using tar compression when available on server
- Add i18n translations for "Upload folder" in English and Chinese locales
- Add folderInputRef to track folder input element in SFTPModal component
- Implement handleFolderSelect handler for processing folder uploads
- Add "Upload folder" button to SftpModalHeader with FolderUp icon
- Add hidden file input with webkitdirectory attribute for folder selection
- Update SftpModalFileList context menu to include folder upload option
- Pass folderInputRef and folder handlers through component hierarchy
- Enable users to upload entire folder structures via SFTP modal
The previous approach tried to reconstruct paths for nested files using
filePathMap keyed by f.name (base file names), but for folder drops
rootName is the folder name which doesn't exist in the map.
Now we call getPathForFile directly on each result.file, which should
work for all files in Electron. The filePathMap reconstruction is kept
as a fallback.
This ensures large files inside dropped folders use stream transfers
instead of falling back to arrayBuffer() which causes OOM.
Co-Authored-By: Claude <noreply@anthropic.com>
- Replace memory-based file uploads with stream transfers for large files
- Add uploadWithStreams and downloadWithStreams functions in transferBridge
- Fix cancel transfer by properly destroying streams instead of throwing
errors in callbacks (which corrupted SSH connection)
- Fix upload button not triggering upload by copying FileList before
clearing input (clearing input also clears FileList reference)
- Export getPathForFile utility for obtaining local file paths
- Add startStreamTransfer and cancelTransfer bridge methods
Co-Authored-By: Claude <noreply@anthropic.com>
- uploadService.ts: Mark all bundle tasks as cancelled on early loop exit
- uploadService.ts: Don't set wasCancelled for actual errors, preserving
the error result for proper UI feedback
- useSftpModalTransfers.ts: Re-throw real errors instead of masking them
as cancellations, only return cancelled:true for user-initiated cancels
This ensures genuine failures (permission denied, disk full, connection
loss) are reported as errors with proper toast messages, while user
cancellations are correctly identified and handled.
Co-Authored-By: Claude <noreply@anthropic.com>
Disables render tracking by default, making it an opt-in debugging feature. This change significantly reduces development log noise by only logging render information when explicitly enabled via a debug flag.
Also, explicitly sets `aria-describedby={undefined}` on dialog content. This ensures proper accessibility semantics when a description is not provided, preventing potential issues or warnings.
Adopts a "fail-fast" strategy for SFTP uploads, stopping the entire transfer process upon encountering any error during file or directory operations.
Introduces a new `isFatalUploadError` helper to consolidate and expand the definition of errors that should halt an upload, now explicitly including cases where the target directory is deleted or inaccessible during the transfer.
Removes specific fatal error checks from various components, streamlining error propagation and simplifying the overall error handling logic.
Ensures "Scanning files..." placeholder tasks are consistently removed when actual upload tasks are added, preventing potential state inconsistencies.
Refactors the SFTP upload mechanism to provide a more unified and robust experience.
- **Bundles folder uploads**: When uploading a folder from the local machine, it now appears as a single, aggregated task in the UI, showing overall progress instead of individual files.
- **Enhances cancellation**: Implements a new upload service and controller to manage transfers, allowing for more immediate and reliable cancellation of both individual files and bundled folder uploads.
- **Improves UI feedback**: Adds dedicated buttons for cancelling active uploads and dismissing completed, failed, or cancelled tasks.
- **Faster folder deletion**: Utilizes SSH `rm -rf` command for rapid remote folder deletion, falling back to SFTP rmdir if SSH exec is unavailable.
- Updates internationalization keys for single item deletion confirmation.
- Bundle folder uploads as single tasks showing aggregate progress
- Add unique file transfer IDs for proper cancellation tracking
- Fix cancel button to call cancelExternalUpload for external uploads
- Improve backend cancel detection using cancelled flag instead of error message
- Use SSH exec with rm -rf for fast folder deletion on remote servers
- Add FolderUp icon for folder upload tasks in transfer queue
- Add i18n key for upload cancelled message
Co-Authored-By: Claude <noreply@anthropic.com>
Enhances SFTP file upload performance and responsiveness by:
- Throttling UI progress updates with `requestAnimationFrame` to reduce re-renders.
- Optimizing Electron-side binary writes with larger chunk sizes, `subarray` for buffers, and efficient buffer handling.
- Implementing IPC progress event throttling to reduce communication overhead between main and renderer processes.
- Speeding up folder processing by traversing directory entries in parallel batches, with yielding to maintain UI responsiveness.
Improves robustness by:
- Ensuring folder uploads stop immediately upon user cancellation.
- Preventing division-by-zero errors in the progress bar calculation.
Also updates Claude settings to allow `npm run build:*` commands.
Extracts the logic for normalizing line endings (CRLF to LF) during clipboard paste operations into a shared utility function.
This improves code reusability and consistency across different paste mechanisms, ensuring that pasted content always uses Unix-style line endings and prevents issues like extra blank lines in the terminal.
Implements periodic yielding to the main thread during large folder uploads and local folder parsing. This prevents the UI from freezing, improving responsiveness during these intensive operations.
Integrates folder upload progress directly into the transfer status panel, replacing the previous full-screen overlay. This provides a less intrusive and more consistent user experience for monitoring folder uploads.
Refines the drag-and-drop handler to correctly prioritize internal pane-to-pane transfers over external file/folder drops from the operating system.
- Improve font filtering logic with word boundary matching to avoid false positives
- Rename snake_case variable to camelCase (mono_fonts -> monoFonts)
- Translate Chinese comments to English
- Add TypeScript type definitions for Font Access API
- Check API availability before calling queryLocalFonts
- Apply CJK fallback fonts to local fonts
- Add 'local-' prefix for local font IDs to avoid collisions
- Handle permission denied gracefully
- Use TERMINAL_FONTS as default for availableFonts
- Add safer fallbacks for empty availableFonts in all components
- Export withCjkFallback function for reuse
Drops support for the built-in image viewer, including related UI, state, and file association logic. Simplifies file opener options and context menus to support only text editing and external system applications.
Streamlines codebase by eliminating redundant image preview code and reduces maintenance overhead for this feature.
Enables users to open SFTP files using any system application via a new "Open With" dialog. Remembers associations per file extension, supports editing/removing these in settings, and synchronizes changes across components. Updates backend and Electron bridge to handle selecting and launching external applications on all platforms. Improves localization and user feedback for the new feature.
Enables text and image file viewing and editing directly from the SFTP interface with context menu actions and modals. Improves file type detection to distinguish between text, image, and known binary files, preventing inappropriate editing options. Updates editor modal with find support and refines build config to reduce dev warnings.
Enhances user workflow by reducing friction in managing remote files.
Integrates Monaco Editor for enhanced syntax highlighting in the text editor modal, improving editing experience for code and config files.
Tracks and synchronizes the terminal's current working directory via OSC 7 escape sequences, enabling SFTP dialogs to open at the detected shell path even after user or directory changes.
Introduces IPC and backend support for querying the current shell directory from active SSH sessions, with fallback and path validation logic for remote SFTP browsing.
Improves file type detection by analyzing file content in addition to extensions.
Updates i18n strings and UI elements for clarity and future system application integration.
Adds necessary dependencies for Monaco Editor and updates content security policy for web workers.
Optimizes SFTP view rendering by isolating tab activation state, using context stores and memoization to prevent unnecessary re-renders on tab switch. Introduces cross-pane tab drag-and-drop, allowing users to move tabs between panes via the tab bar, and ensures stable callback references throughout. Refactors UI components for memoization and efficient prop updates, and wraps key dialogs with React.memo for better performance.
Enhances overall responsiveness, especially when switching or managing tabs in complex SFTP sessions.
Replaces all direct usage of browser globals and infrastructure service imports in UI components with dedicated application/state backend hooks. Introduces lint rules to prevent direct access to backend bridges and localStorage from components, promoting a cleaner separation of concerns and improved maintainability.
Moves user preferences (e.g., port forwarding form mode) to persistent state hooks, updates port forwarding and SFTP logic to rely on backend hooks, and centralizes logging through a logger utility. Cleans up debug code and removes obsolete scripts from HTML.
Improves testability, prepares for alternative backend implementations, and enforces architectural boundaries.
Reorder and normalize import statements, group icon imports, and add
missing utility imports (cn). Fix export/newline formatting and minor
type import tweaks. Add ESLint scripts to package.json and update the
lockfile.
- Added agents overview documentation outlining the project structure and roles.
- Implemented `useSessionState` for managing terminal sessions and workspaces.
- Developed `useSettingsState` for handling user settings and theme management.
- Created `useVaultState` for managing hosts, SSH keys, snippets, and custom groups.
- Introduced domain logic for host normalization and sanitization.
- Defined models for Host, SSHKey, Snippet, TerminalSession, and Workspace.
- Implemented workspace management functions including creation, insertion, and pruning.
- Established local storage adapter for persistent data management.
- Integrated Gemini AI service for terminal simulation and command generation.
- Developed sync service for backing up and restoring configuration to/from GitHub Gists.
- Added TopTabs component for managing terminal sessions and workspaces.
- Integrated drag-and-drop functionality for session organization.
- Created VaultView component for managing hosts, SSH keys, snippets, and port forwarding.
- Implemented group management for hosts with the ability to create, delete, and move groups.
- Added initial data for hosts and snippets in defaultData.ts.
- Defined storage keys for persistent data management in storageKeys.ts.