SSD-Syncer is a cross-platform CLI tool that synchronizes folders between multiple computers (macOS, Windows, Ubuntu) using a physical SSD drive — no network required.
It works like a "sneakernet" sync: plug your SSD into one computer, sync, then plug it into another — all machines end up with identical folder contents.
MacOS ↔ SSD ↔ Windows
↔ Ubuntu
- The SSD acts as a hub. Each time you plug it into a computer, the CLI performs a bidirectional sync between the local folder and the SSD folder.
- Uses a three-way merge algorithm: compares the current local state and SSD state against the last-sync snapshot to determine what changed on each side.
- Optimized scanning: first compares file modification time + size (fast), then computes BLAKE3 hash only for changed files.
- Cross-platform: single Rust binary runs on macOS, Windows, and Linux
- Bidirectional sync: changes on either side are correctly merged
- Conflict detection: 5 resolution strategies (
both/local-wins/ssd-wins/newer-wins/ask) - Fast scanning: mtime+size pre-filtering, BLAKE3 hashing only when needed
- Smart ignore: common build/temp directories (
node_modules,__pycache__,target,.git,dist,build, etc.) and system files (.DS_Store,._*,Thumbs.db) ignored by default, supports glob patterns - Dry run mode: preview all changes before applying
- Sync history log: track when and what was synced
Download the binary and install script for your platform from the release directory:
Windows:
- Download
ssd-syncer-windows.exeandinstall.batto the same folder - Double-click
install.bat(or run it in CMD) - Open a new terminal and use
sync <command>
macOS:
- Download
ssd-syncer-macosandinstall.shto the same folder - Run:
chmod +x install.sh && ./install.sh - Open a new terminal (or
source ~/.zshrc) and usesync <command>
Linux:
- Download
ssd-syncer-linuxandinstall.shto the same folder - Run:
chmod +x install.sh && ./install.sh - Open a new terminal (or
source ~/.bashrc) and usesync <command>
Requires Rust toolchain.
cd cli
cargo build --releaseThe binary will be at cli/target/release/ssd-syncer.
Use cross for easy cross-compilation:
# For Linux
cross build --release --target x86_64-unknown-linux-gnu
# For Windows
cross build --release --target x86_64-pc-windows-gnu# On your Mac
ssd-syncer init --name "macbook-pro"
# On your Windows PC
ssd-syncer init --name "win-desktop"
# On your Ubuntu machine
ssd-syncer init --name "ubuntu-dev"# On Mac
ssd-syncer add --local /Users/summer/share/abc --ssd /Volumes/MySSD/abc --name WORK
# On Windows
ssd-syncer add --local D:/share/abc --ssd E:/abc --name WORK
# On Ubuntu
ssd-syncer add --local /home/summer/share/abc --ssd /mnt/ssd/abc --name WORK# By mapping name
ssd-syncer sync WORK
# If only one mapping exists, name can be omitted
ssd-syncer sync# Dry run — see what would happen, no changes applied
ssd-syncer sync WORK --dry-run
# Quick status summary
ssd-syncer status WORK
# Detailed file-by-file diff
ssd-syncer diff WORKssd-syncer init --name "macbook-pro"ssd-syncer add --local /Users/summer/Documents/work --ssd /Volumes/MySSD/work --name WORK--local— Local folder path--ssd— SSD target absolute path--name— Alias name for this mapping
ssd-syncer remove --name WORKssd-syncer listssd-syncer sync WORK # Sync by mapping name
ssd-syncer sync # Auto-select if only one mapping
ssd-syncer sync WORK --dry-run # Preview only
ssd-syncer sync WORK --verbose # Verbose output
ssd-syncer sync WORK -v # Short formssd-syncer status WORK
ssd-syncer status # Auto-select if only one mappingssd-syncer diff WORK
ssd-syncer diff # Auto-select if only one mappingssd-syncer log WORK
ssd-syncer log WORK --limit 50 # Show last 50 entriesssd-syncer ignore-resetssd-syncer ignore-list# Name pattern: ignore all directories/files named "logs" anywhere
ssd-syncer ignore-add "*.log" "logs" ".env" "coverage"
# Path pattern (contains /): ignore a specific folder only
ssd-syncer ignore-add "projects/myapp/tmp" "data/cache"Pattern rules:
All patterns are matched against relative paths within the sync folder root (the local directory you configured with
ssd-syncer add --local).
- Name pattern (no
/): matches any file/directory with that name at any level.
- Example: pattern
node_modulesignores all directories namednode_modulesno matter how deeply nested.- Path pattern (contains
/): matches only the exact relative path and everything under it.
- Example: pattern
projects/myapp/tmponly ignores the folder at that specific relative path.- Glob (
*,?): supported in both types, e.g.*.log,*.pyc.Example to clarify “relative to sync folder root”:
Suppose your sync mapping is:
local = "C:\Users\Summer\sync" ← this is the sync folder root ssd = "MY_SYNC"Then the pattern
projects/myapp/tmpmatches:
- Local:
C:\Users\Summer\sync\projects\myapp\tmp\and all files within- SSD:
<SSD_MOUNT>/MY_SYNC/projects/myapp/tmp/and all files withinIt does NOT mean a path on the SSD only — it applies equally to both sides.
ssd-syncer ignore-remove "vendor" "dist"Local config is stored at ~/.ssd-syncer/config.toml:
[machine]
name = "macbook-pro"
[[sync]]
name = "WORK"
local = "/Users/summer/share/abc"
ssd = "/Volumes/MySSD/abc"
[[sync]]
name = "PHOTOS"
local = "/Users/summer/share/xyz"
ssd = "/Volumes/MySSD/xyz"
[ignore]
patterns = [
".DS_Store", "._*", "Thumbs.db", "desktop.ini", ".ssd-syncer",
".git", ".svn", ".hg",
"__pycache__", ".venv", "venv", "node_modules",
"target", "dist", "build", ".cache",
".idea", ".vs",
# ... and more (use `ignore-reset` to see full list)
]
[conflict]
strategy = "both" # both / local-wins / ssd-wins / newer-wins / askTip: If your config was created before v0.2.0, run
ssd-syncer ignore-resetto update to the latest default ignore patterns.
| Strategy | Behavior |
|---|---|
both (default) |
Keep both versions, rename the conflicting file with .conflict.<machine>.<timestamp> suffix |
local-wins |
Local version always wins |
ssd-wins |
SSD version always wins |
newer-wins |
The file with the more recent modification time wins |
ask |
Interactive prompt (falls back to both in non-interactive mode) |
<ssd-mount>/
├── .ssd-syncer/
│ ├── snapshots/
│ │ ├── macbook-pro/
│ │ │ └── share_abc.json
│ │ └── win-desktop/
│ │ └── share_abc.json
│ └── sync.log
└── share/
└── abc/
└── (your synced files)
MIT
SSD-Syncer 是一个跨平台(macOS / Windows / Ubuntu)的命令行工具,通过物理 SSD 硬盘在多台电脑之间同步指定文件夹的内容——无需网络。
使用方式类似"U盘中转":将 SSD 插入一台电脑同步,再插入另一台电脑同步,最终所有机器上的文件夹内容完全一致。
MacOS ↔ SSD ↔ Windows
↔ Ubuntu
- SSD 作为中转站(Hub),每次插入一台电脑时,CLI 会执行本地文件夹与 SSD 文件夹之间的双向同步
- 使用三方比对算法:将当前本地状态和 SSD 状态分别与上次同步快照对比,判断各方的变更
- 扫描优化:先比较文件修改时间 + 大小(极快),仅对有变化的文件计算 BLAKE3 哈希
- 跨平台:单个 Rust 二进制文件,支持 macOS、Windows、Linux
- 双向同步:两端的变更都能正确合并
- 冲突检测:5 种冲突解决策略(
both/local-wins/ssd-wins/newer-wins/ask) - 快速扫描:mtime + size 预过滤,仅必要时计算 BLAKE3 哈希
- 智能忽略:默认忽略常见编译/临时目录(
node_modules、__pycache__、target、.git、dist、build等)和系统文件(.DS_Store、._*、Thumbs.db),支持 glob 模式 - Dry Run 模式:预览所有变更,确认后再执行
- 同步历史日志:记录每次同步的时间和操作数
从 release 目录下载对应平台的二进制文件和安装脚本:
Windows:
- 下载
ssd-syncer-windows.exe和install.bat到同一目录 - 双击运行
install.bat(或在 CMD 中执行) - 打开新的终端窗口,即可使用
sync <命令>
macOS:
- 下载
ssd-syncer-macos和install.sh到同一目录 - 执行:
chmod +x install.sh && ./install.sh - 打开新终端(或
source ~/.zshrc)即可使用sync <命令>
Linux:
- 下载
ssd-syncer-linux和install.sh到同一目录 - 执行:
chmod +x install.sh && ./install.sh - 打开新终端(或
source ~/.bashrc)即可使用sync <命令>
需要安装 Rust 工具链。
cd cli
cargo build --release编译产物位于 cli/target/release/ssd-syncer。
使用 cross 工具可以轻松交叉编译:
# 编译 Linux 版本
cross build --release --target x86_64-unknown-linux-gnu
# 编译 Windows 版本
cross build --release --target x86_64-pc-windows-gnu# Mac 上
ssd-syncer init --name "macbook-pro"
# Windows 上
ssd-syncer init --name "win-desktop"
# Ubuntu 上
ssd-syncer init --name "ubuntu-dev"# Mac 上
ssd-syncer add --local /Users/summer/share/abc --ssd /Volumes/MySSD/abc --name WORK
# Windows 上
ssd-syncer add --local D:/share/abc --ssd E:/abc --name WORK
# Ubuntu 上
ssd-syncer add --local /home/summer/share/abc --ssd /mnt/ssd/abc --name WORK# 通过别名同步
ssd-syncer sync WORK
# 只有一个映射时,可省略名称
ssd-syncer sync# Dry Run —— 只看不改
ssd-syncer sync WORK --dry-run
# 快速查看变更摘要
ssd-syncer status WORK
# 查看逐文件差异
ssd-syncer diff WORKssd-syncer init --name "macbook-pro"ssd-syncer add --local /Users/summer/Documents/work --ssd /Volumes/MySSD/work --name WORK--local— 本地目录路径--ssd— SSD 目标绝对路径--name— 映射别名
ssd-syncer remove --name WORKssd-syncer listssd-syncer sync WORK # 通过别名同步
ssd-syncer sync # 只有一个映射时自动选择
ssd-syncer sync WORK --dry-run # 仅预览
ssd-syncer sync WORK --verbose # 详细模式
ssd-syncer sync WORK -v # 简写ssd-syncer status WORK
ssd-syncer status # 只有一个映射时自动选择ssd-syncer diff WORK
ssd-syncer diff # 只有一个映射时自动选择ssd-syncer log WORK
ssd-syncer log WORK --limit 50 # 显示最近 50 条ssd-syncer ignore-resetssd-syncer ignore-list# 名称模式:忽略所有叫这个名字的文件/目录
ssd-syncer ignore-add "*.log" "logs" ".env" "coverage"
# 路径模式(含 /):只忽略特定路径的文件夹
ssd-syncer ignore-add "projects/myapp/tmp" "data/cache"模式规则:
所有模式都是相对于同步文件夹根目录(即
ssd-syncer add --local配置的本地目录)进行匹配的。
- 名称模式(不含
/):匹配任意层级下的同名文件/目录。
- 例如:模式
node_modules会忽略所有叫node_modules的目录,无论嵌套多深。- 路径模式(含
/):只匹配特定相对路径及其下所有内容。
- 例如:模式
projects/myapp/tmp只忽略该特定相对路径下的文件夹。- 通配符(
*、?):两种模式均支持,例如*.log、*.pyc。举例说明“相对于同步文件夹根目录”:
假设你的同步映射配置为:
local = "C:\Users\Summer\sync" ← 这就是同步文件夹根目录 ssd = "MY_SYNC"那么忽略模式
projects/myapp/tmp实际匹配的是:
- 本地:
C:\Users\Summer\sync\projects\myapp\tmp\及其下所有文件- SSD:
<SSD挂载点>/MY_SYNC/projects/myapp/tmp/及其下所有文件忽略规则对本地和 SSD 两侧同时生效,而不是只作用于某一侧。
ssd-syncer ignore-remove "vendor" "dist"本地配置保存在 ~/.ssd-syncer/config.toml:
[machine]
name = "macbook-pro"
[[sync]]
name = "WORK"
local = "/Users/summer/share/abc"
ssd = "/Volumes/MySSD/abc"
[[sync]]
name = "PHOTOS"
local = "/Users/summer/share/xyz"
ssd = "/Volumes/MySSD/xyz"
[ignore]
patterns = [
".DS_Store", "._*", "Thumbs.db", "desktop.ini", ".ssd-syncer",
".git", ".svn", ".hg",
"__pycache__", ".venv", "venv", "node_modules",
"target", "dist", "build", ".cache",
".idea", ".vs",
# ... 更多默认规则(运行 `ignore-reset` 查看完整列表)
]
[conflict]
strategy = "both" # both / local-wins / ssd-wins / newer-wins / ask提示:如果你的配置是在 v0.2.0 之前创建的,运行
ssd-syncer ignore-reset可以更新为最新的默认忽略规则。
| 策略 | 行为 |
|---|---|
both(默认) |
保留双方版本,冲突文件添加 .conflict.<机器名>.<时间戳> 后缀 |
local-wins |
始终以本地版本为准 |
ssd-wins |
始终以 SSD 版本为准 |
newer-wins |
以修改时间更新的版本为准 |
ask |
交互式询问(非交互模式下退回到 both) |
<SSD挂载点>/
├── .ssd-syncer/
│ ├── snapshots/
│ │ ├── macbook-pro/
│ │ │ └── share_abc.json
│ │ └── win-desktop/
│ │ └── share_abc.json
│ └── sync.log
└── share/
└── abc/
└── (你的同步文件)
MIT