FTPair
Bring FTP/SFTP/FTPS remote file management directly into VS Code.
Table of Contents
Highlights
- FTP, SFTP, and FTPS (implicit/explicit) connection support
- Remote Explorer panel (list, open, rename, delete, create file/folder)
Upload To... supports:
- single file upload
- recursive folder upload
- multi-selection upload from Explorer
- Batch upload summary:
total / succeeded / skipped / failed
Upload on Save (global setting + profile-level setting)
Download From... downloads the remote counterpart of the selected/active local file
- Download files/folders directly from Remote Explorer (recursive for folders)
- Local ↔ Remote diff
- Reveal the active file in Remote Explorer
- JSON export/import for profiles
.ftpignore + excludedPaths + path mapping support
- Passwords stored securely in OS keychain (
SecretStorage)
Installation
Install FTPair from the VS Code Marketplace.
Quick Start
- Open
Cmd/Ctrl + Shift + P
- Run
FTPair: Add Connection Profile
- Fill in profile details and save
- Connect with
FTPair: Connect
- Open the
FTPair panel from the Activity Bar
- Use
Upload To... / Download From... from Explorer or editor
For commands that use profile selection (Upload To..., Download From..., Diff with Remote):
- If there is only one profile, it is selected automatically.
- If there are multiple profiles, a selection list is shown.
Upload Flows
1) Upload File
- Uploads the active file to the selected profile.
- No default keybinding (available via Command Palette).
2) Upload To... (recommended main flow)
This command is available in Explorer, Editor, and SCM context menus.
- If a file is selected in Explorer: uploads that file.
- If a folder is selected in Explorer: uploads recursively.
- If multiple items are selected in Explorer: uploads all selected files/folders in one flow.
- If no item is selected: uses active editor/tab file.
- If none is available: opens a file picker.
Batch operations show a summary:
Upload completed: total X, succeeded Y, skipped Z, failed N.
Default shortcut:
- macOS:
Cmd+Option+Shift+X
- Windows/Linux:
Ctrl+Alt+Shift+X
Note: Single-file and multi/folder uploads use the same shortcut (Upload To...).
3) Upload Folder and Upload Entire Project
Upload Folder: recursively uploads the selected folder (requires active connection).
Upload Entire Project: recursively uploads workspace root (asks for confirmation).
- Shows batch summary after completion.
4) Upload filtering and mapping
.ftpignore and profile excludedPaths are applied together.
- Local → remote path resolution:
- profile
mappings first
- workspace fallback when needed
- temp path resolution for remote temp files
5) Upload on Save
Upload is triggered when any of these is true:
- Global setting:
ftpair.uploadOnSave
- Profile setting:
uploadOnSave
- Remote temp file scenario
Download and Diff
Download From...
- Selects a local file from Explorer/Editor/SCM and downloads its remote counterpart based on the selected profile.
- Uses profile selection.
Open Remote File...
- Selects a local file from Explorer/Editor/SCM and downloads its remote counterpart into a temporary folder.
- Opens the downloaded remote version with an appropriate viewer (does not overwrite local file).
Remote Explorer Download
- Direct download for files.
- Recursive download for folders.
- Tries to open binary files with an appropriate viewer.
Diff with Remote
- Opens VS Code diff view for active file or selected remote file.
- In local-file diff flow, profile selection opens each time; comparison is done after connecting to the selected profile.
Remote Explorer Features
Toolbar:
Reveal Active File In Remote Explorer
Collapse All
Refresh
Disconnect
Switch Connection
Add Connection Profile
Export Settings / Import Settings buttons in Switch Connection profile list
Import Settings icon is visible when disconnected and hidden when connected
Switch Connection profile list is numbered; order can be changed permanently with Move Up / Move Down
Row/context actions:
Open Remote File
Download
Diff with Remote
Rename
Delete
New File
New Folder
Copy Remote Path
Additional:
- Active profile name shown in title
- Symlink target display and symlink visibility
- Change profile from status bar (
ftpair.statusBarClicked)
Profile Configuration (.vscode/ftpair.json)
File path: .vscode/ftpair.json inside workspace
Example:
{
"profiles": [
{
"id": "prod",
"label": "Prod Server",
"protocol": "sftp",
"host": "example.com",
"port": 22,
"username": "deploy",
"authType": "key",
"privateKeyPath": "~/.ssh/id_rsa",
"remotePath": "/var/www/current",
"webUrl": "https://example.com",
"mappings": [
{
"local": "/Users/me/Projects/site",
"remote": "/"
}
],
"excludedPaths": ["node_modules", ".git", "*.log"],
"uploadOnSave": true,
"showInUploadMenu": true,
"ftpsMode": "explicit"
}
],
"activeProfileId": "prod"
}
Field notes:
authType: password | key | agent
showInUploadMenu=false: hides profile from upload selection list
mappings: maps local paths to remote paths (most specific match wins)
activeProfileId: active profile
Settings Export / Import
Commands:
Export Settings
Import Settings
Behavior:
- Export writes profile configuration to JSON file (
ftpair-settings.json recommended).
- Import replaces current profile set with file content.
- During import, active connections are closed and extension context is refreshed.
- Passwords are not imported/exported for security reasons.
Supported import formats:
- Direct config format (
profiles, activeProfileId)
- Export envelope format (
source, version, exportedAt, config)
Settings (settings.json)
| Setting |
Type |
Default |
Description |
ftpair.uploadOnSave |
boolean |
false |
Auto-upload on save |
ftpair.showStatusBar |
boolean |
true |
Show active profile indicator in status bar |
ftpair.confirmDelete |
boolean |
true |
Confirm before remote delete |
Shortcuts
| Command |
macOS |
Windows/Linux |
Upload To... |
Cmd+Option+Shift+X |
Ctrl+Alt+Shift+X |
Diff with Remote |
Cmd+Shift+D |
Ctrl+Shift+D |
Commands
| Command ID |
Title |
ftpair.connect |
FTPair: Connect |
ftpair.disconnect |
Disconnect |
ftpair.uploadFile |
Upload File |
ftpair.uploadFolder |
Upload Folder |
ftpair.uploadFileChooseServer |
Upload to Server... |
ftpair.uploadGitChanges |
Upload To... |
ftpair.downloadFromChooseServer |
Download From... |
ftpair.openRemoteFromChooseServer |
Open Remote File... |
ftpair.uploadProject |
Upload Entire Project |
ftpair.downloadFile |
Download |
ftpair.diffFile |
Diff with Remote |
ftpair.addProfile |
Add Connection Profile |
ftpair.editProfile |
FTPair: Edit Connection Profile |
ftpair.deleteProfile |
FTPair: Delete Connection Profile |
ftpair.exportSettings |
Export Settings |
ftpair.importSettings |
Import Settings |
ftpair.refreshExplorer |
Refresh |
ftpair.revealActiveFileRemote |
Reveal Active File In Remote Explorer |
ftpair.collapseAll |
Collapse All |
ftpair.openLog |
FTPair: Open Log |
ftpair.switchConnection |
Switch Connection |
ftpair.statusBarClicked |
FTPair: Change Profile |
ftpair.openRemoteFile |
Open Remote File |
ftpair.renameRemote |
Rename |
ftpair.deleteRemote |
Delete |
ftpair.newRemoteFile |
New File |
ftpair.newRemoteFolder |
New Folder |
ftpair.copyRemotePath |
Copy Remote Path |
ftpair.createIgnoreFile |
Create .ftpignore |
Compatibility alias:
sftp.upload.activeFile → routed to FTPair upload flow.
Security Notes
- Passwords/proxy credentials are stored in
SecretStorage (OS keychain).
- Passwords are never written to
.vscode/ftpair.json.
- Do not keep SSH private keys inside the project (
~/.ssh is recommended).
License
Commercial License. See the Marketplace License page for full terms.