A set of macOS and Windows dotfiles, keyboard customizations, editor settings, and backup/restore helpers.
Current setup status: the maintained setup flow is the manifest-driven
dot/CLI. The deprecatedscripts/dot-restore.sh,scripts/local-backup.sh, andscripts/local-restore.shwrappers only point to their replacements; use the other scripts only for their specific, documented purposes.
Table of Contents (click to expand)
Use this section as the source of truth when completing setup on behalf of a user.
- Prefer cloning to
~/dotfiles. Thedot/CLI resolves the repository from its own location, but the trackedzshenvcurrently adds the literal path~/dotfiles/bintoPATH. If you clone elsewhere, replace command paths and update thatzshenventry before setup. - Do not run destructive restores without an explicit
--apply.dot/dot restoreanddot/local restoreintentionally default to dry-run mode unless--applyis supplied. - Setup preserves existing config by default. Conflict policies apply to both symlinks and copied files. Use explicit
--overwriteonly after reviewing the matching dry-run. - Do not put private secrets in this repository. Machine/company/private files belong in
~/.localrc,~/.localenv,~/.gitconfig, and~/.ssh, and can be backed up withdot/local backup. - Prefer the manifest-driven CLI. The maintained entrypoints are
dot/dotanddot/local; the deprecated wrappers inscripts/are not the primary setup flow. - macOS support is first-class.
dot/dot setup,dot/dot backup, anddot/dot restorecurrently enforce macOS viauname -s == Darwin.
-
Install Apple's command line tools if Git is not already available:
xcode-select --install
-
Clone this repository:
git clone https://github.com/zhuochun/dotfiles.git ~/dotfiles cd ~/dotfiles
-
Install Homebrew if
brewis not available:/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)" -
Install the Homebrew bundle separately;
dot/dot setupconfigures files but does not install packages for you:brew bundle check --file=~/dotfiles/scripts/Brewfile || brew bundle install --file=~/dotfiles/scripts/Brewfile
-
Preview dotfile setup actions:
~/dotfiles/dot/dot setup --dry-run --skip-existing --verbose -
Apply tracked dotfile setup. It defaults to
--skip-existingfor both symlink and copy entries; use explicit--overwriteonly when you intend to replace existing config:~/dotfiles/dot/dot setup --skip-existing --verbose -
Ensure Zsh is allowed and make it the default shell if needed:
which zsh grep -Fx "$(which zsh)" /etc/shells || echo "$(which zsh)" | sudo tee -a /etc/shells chsh -s "$(which zsh)"
-
Install oh-my-zsh and custom plugins if they are missing:
test -d ~/.oh-my-zsh || RUNZSH=no CHSH=no KEEP_ZSHRC=yes sh -c "$(curl -fsSL https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh)" ZSH_CUSTOM="${ZSH_CUSTOM:-$HOME/.oh-my-zsh/custom}" for plugin in zsh-autosuggestions zsh-completions; do test -d "$ZSH_CUSTOM/plugins/$plugin" || git clone "https://github.com/zsh-users/$plugin" "$ZSH_CUSTOM/plugins/$plugin" done
-
Install Tmux Plugin Manager if it is missing:
test -d ~/.tmux/plugins/tpm || git clone https://github.com/tmux-plugins/tpm ~/.tmux/plugins/tpm
-
Install Vim/Neovim plugins:
if [ ! -d ~/.cache/dein/repos/github.com/Shougo/dein.vim ]; then mkdir -p ~/.cache/dein/repos/github.com/Shougo git clone https://github.com/Shougo/dein.vim.git ~/.cache/dein/repos/github.com/Shougo/dein.vim fi nvim +'call dein#install()' +qall
-
Open GUI apps that need permissions and complete their prompts:
- Karabiner-Elements: grant keyboard/input monitoring permissions, then restart Karabiner.
- Espanso: grant accessibility permissions.
- Rectangle: import or verify its config if needed.
- Rime/Squirrel: deploy the input method configuration if installed.
-
Create or restore private local config outside this repository:
touch ~/.localrc ~/.localenv ~/dotfiles/dot/local backup --dry-run --verbose # To restore an existing private backup: # ~/dotfiles/dot/local restore --from ~/localrc/backup-YYYY-MM-DD --dry-run --verbose # ~/dotfiles/dot/local restore --from ~/localrc/backup-YYYY-MM-DD --apply --verbose
Run these checks after setup:
brew bundle check --file=~/dotfiles/scripts/Brewfile
~/dotfiles/dot/dot setup --dry-run --skip-existing --verbose
for file in ~/dotfiles/zshrc ~/dotfiles/zshenv; do zsh -n "$file"; done
for file in ~/dotfiles/dot/dot ~/dotfiles/dot/local ~/dotfiles/dot/lib/common.sh ~/dotfiles/dot/lib/symlink.sh; do bash -n "$file"; done
bash ~/dotfiles/dot/tests/dot_test.sh
nvim --headless +qExpected results:
brew bundle checkexits successfully, or prints the packages still needing installation.dot/dot setup --dry-run --verboselists planned actions without writing files.- Shell syntax checks exit successfully.
nvim --headless +qexits successfully after Neovim is installed.
dot/dot manages tracked dotfiles and app configuration on macOS.
~/dotfiles/dot/dot setup [--dry-run] [--overwrite|--skip-existing|--interactive] [--verbose]
~/dotfiles/dot/dot backup [--dry-run] [--verbose]
~/dotfiles/dot/dot restore [--dry-run] [--apply] [--verbose]setupreadsdot/manifests/setup.macos.tsvand creates symlinks/copies into$HOME; both action types default to--skip-existing.backuprequires Homebrew, updatesscripts/Brewfile, and captures only copy-managed app config fromdot/manifests/backup.macos.tsv. Setup-managed symlinks already point into the repository and are not backed up.- Backup run logs use
partialwhen optional app sources are missing andfailedwhen an operation exits unsuccessfully. restorepreflightsrsync, then copies/syncs tracked app files from the repo back into$HOMEusingdot/manifests/restore.macos.tsv; it is dry-run by default and requires--applyto write.- Restore creates rollback snapshots under
~/.dotfiles-restore-backups/<timestamp>/before overwriting existing paths.
dot/local manages private machine/company config that should not be committed.
~/dotfiles/dot/local backup [--dry-run] [--verbose]
~/dotfiles/dot/local restore --from <backup_dir> [--dry-run] [--apply] [--overwrite|--skip-existing] [--verbose]backupwrites timestamped backups under~/localrc/backup-YYYY-MM-DD/or~/localrc/backup-YYYY-MM-DD-HHMMSS/if the daily directory already exists.- Backup content includes
.localrc,.localenv,.gitconfig, and~/.ssh/excludingauthorized*files when present. restoreis dry-run by default and requires--applyto write.- Both commands preflight
rsyncbefore creating or restoring backup content. - Local restores also create rollback snapshots under
~/.dotfiles-restore-backups/<timestamp>/.
- Trackpad -> Enable
Tap to click. - Accessibility -> Pointer Control -> Trackpad Options -> Enable dragging
Three finger dragging. - Dock -> Position
Left, EnableAutomatically hide and showandMinimise windows into application icon, DisableShow recent applications in Dock. - Keyboard -> Keyboard
- Fastest Key Repeat, Shortest Delay, Enable
Standard function keys. - Modifier Keys... -> Change
Caps LocktoCommandkey.
- Fastest Key Repeat, Shortest Delay, Enable
- Keyboard -> Shortcuts -> Screen Shots
- Disable "picture of screen" shortcuts.
- Remap picture of selected area to
<M-s>(File) and<M-S>(Clipboard).
- Keyboard -> Input Sources -> Add
Pinyin - Simplified.
Other preferences:
# Disable "press and hold" option
defaults write -g ApplePressAndHoldEnabled -bool false
# Display all file extensions in Finder
defaults write NSGlobalDomain AppleShowAllExtensions -bool trueInstall GitHub Desktop if you prefer a GUI Git client. Otherwise, use the CLI clone flow from Fresh macOS Setup Checklist.
Follow the Fresh macOS Setup Checklist for the canonical Homebrew, setup, backup, and restore sequence. See Command Reference for command safety and conflict behavior.
Follow steps 7-8 of the Fresh macOS Setup Checklist to set the default shell and install oh-my-zsh without replacing the repo-managed ~/.zshrc symlink.
zshrc currently enables autojump, git, gitignore, golang, tmux, zsh-completions, and zsh-autosuggestions.
Install Tmux Plugin Manager in step 9 of the Fresh macOS Setup Checklist, then:
# Start a session
tmux new -s dev
# Reload Tmux environment to source TPM (optional)
tmux source ~/.tmux.conf
# Press prefix (C-b) + I to install pluginsOpen Karabiner-Elements and grant permissions.
dot/dot setup copies the main Karabiner config and symlinks custom rules. To re-run only the documented manual steps:
cp ~/dotfiles/mac/karabiner.json ~/.config/karabiner/karabiner.json
ln -s ~/dotfiles/mac/karabiner-rules ~/.config/karabiner/assets/complex_modificationsRefer to zhuochun/mac-keyboard and Ergodox-EZ layout (Mac/Win).
Both Mac and Windows use similar key mappings. For muscle memory, <D-*> mappings on Mac are <M-*> mappings on Windows.
- macOS: Use
vim/vimrcwithbrew install neovimor the tracked Homebrew bundle. - Windows: Use
windows/_vimrc(not actively updated).
Install Shougo/dein.vim in step 10 of the Fresh macOS Setup Checklist. That direct clone intentionally avoids replacing the repo-managed Vim/Neovim config.
dot/dot setup creates the Vim/Neovim symlinks. Manual equivalents are:
# neovim
ln -s ~/dotfiles/vim/vimrc ~/.config/nvim/init.vim
ln -s ~/dotfiles/vim/rc ~/.config/nvim/rc
# vim
ln -s ~/dotfiles/vim/vimrc ~/.vimrc
ln -s ~/dotfiles/vim/rc ~/.vim/rc
ln -s ~/dotfiles/vim/gvimrc ~/.gvimrcOpen Vim/Neovim and install plugins: :call dein#install().
I use AutoHotkey in Windows to enhance productivity.
Refer to:
windows/AutoHotkey.ahkwindows/AutoHotkey-v2.ahkwindows/AutoHotkey-LLM.ahkwindows/README.md
Some useful/interesting scripts are under bin/, e.g. PDF renaming helpers.
zshenv adds ~/dotfiles/bin to PATH, so dot/dot setup plus a new shell should make these available.
Install Powerline Fonts if your terminal theme needs them.
Install gruvbox colorscheme for terminal.
Install Espanso. dot/dot setup symlinks the tracked match files. Manual equivalents are:
ln -s ~/dotfiles/espanso/match.yml "$HOME/Library/Application Support/espanso/match/base.yml"
ln -s ~/dotfiles/espanso/form.yml "$HOME/Library/Application Support/espanso/match/form.yml"Rime is a powerful Chinese Input Method Engine.
- Use
Ctrl + ~to adjust Traditional/Simplified Chinese.
dot/dot setup symlinks the macOS Squirrel custom config. Manual equivalent:
ln -s ~/dotfiles/rime/squirrel.custom.yaml ~/Library/Rime/squirrel.custom.yamlAtom is no longer part of the main setup flow. Historical plugin note: apm install markdown-writer.