dotfiles
This project turns a new (or factory reset) MacBook into a fully installed and fully configured development machine.
Up and running within 30 minutes!
It is based on dotbot.
Before you start using it you may want to know what it does.
NB: This project focuses on Java / JavaScript / Python development. But you can easilly tailor it to your needs.
Usage
Preparation
- internet connection
- credentials
- Dropbox
- 1Password
- Apple ID (iCloud & App Store)
Run
- Fresh macOS install (optional):
- M1 chip: Use the
Erase All Content and Settings
wizard from theSystem Preferences
menu bar.
- M1 chip: Use the
- Install Xcode Command Line Utilities (required by git & homebrew):
xcode-select --install
- Install & execute the .dotfiles project:
git clone https://github.com/roelfie/dotfiles.git ~/.dotfiles cd ~/.dotfiles ./install
NB: The installation scripts are idempotent so you can run ~/.dotfiles/install
as many times as you wish.
Manual steps
- Setup bookkeeper as a background job
- System Preferences:
- BlueTooth: pair keyboard, phone & headphone
- Keyboard: Use F1, F2, etc. as standard function keys
- Alfred key bindings:
app menu hotkey value System Preferences Keyboard → Shortcuts → Spotlight Show Spotlight search ^ Space
System Preferences Keyboard → Shortcuts → Spotlight Show Finder search window ⌥ Space
Alfred General Alfred Hotkey ⌘ Space
Alfred Features Clipboard History ⌥ ⌘ C
Alfred Features Snippets ⌥ ⌘ S
Overview
Before we dive into the details, let's have a look at a diagram:
Each MacBook comes with pre-installed software:
- in
/bin
: cat, ls, rm, zsh, .. - in
/usr/bin
: git, grep, less, more, .. - in
/Applications
: Mail, Numbers, Pages, Safari, .. - ...
The user can install additional software:
- with Homebrew (into
/opt/homebrew/opt
) - from the App Store (into
/Applications
) - or otherwise ...
Configuration files are typically stored somewhere in the user's home directory:
- dotfiles under
~
(like~/.zshrc
and the.ssh
folder) - under
~/.config
- under
~/Library
(like~/Library/Preferences
and~/Library/Application Support
)
Installing all this software and restoring (macOS or application) configurations to the settings you are used to, can be a cumbersome task.
Dotbot is all about automating the installation & configuration of your macOS system. This dotfiles project is based on dotbot and is specifically tailored to my macOS system. But it can be easilly adjusted to your needs.
What does it do?
This dotfiles project does the following:
- Installation
- Configuration
- Backup to GitHub (.dotfiles project) & Dropbox (mackup)
- Update
Installation
The instructions for Dotbot are defined in install.conf.yaml.
When you run ~/.dotfiles/install
the following will be installed (or upgraded):
- Homebrew
- Homebrew packages and apps
- SSH connection with GitHub
- Node (with n)
- Java / JDK (with jenv)
- and step-by-step instructions for the user (example) in case something can not be automated
NB: In zshrc we've configured the Homebrew --no-quarantine
flag. This will disable the macOS Gatekeeper, so that an application can be used immediately after installation.
cask
over mas
Prefer In Brewfile some GUI macOS applications have the keyword cask
and some mas
(Mac App Store cli).
- A
cask
is downloaded from a Homebrew repository - A
mas
is downloaded from the Mac App Store
Some applications are only available as mas; some only as cask; some as both; and some neither as cask nor mas (these must be downloaded & installed manually).
Only applications that have already been purchased in the App Store can be automatically installed using mas
. If you want to install a paid application for the first time, you have to manually pay for it in & install it from the App Store.
I prefer cask
over mas, since applications stored in the App Store are tied to one (Apple ID) account, and it is not possible to transfer a purchased app from one account to another. The only drawback of installing as cask is that you will have to upload your license manually after installation.
More info:
man brew
brew help bundle
mas help
Command line tools
Some casks are shipped with command line tools. Brew installs them in /opt/homebrew/bin
:
$ ls -la /opt/homebrew/bin | grep /Applications/
bcomp -> /Applications/Beyond Compare.app/Contents/MacOS/bcomp*
code -> /Applications/Visual Studio Code.app/Contents/Resources/app/bin/code*
stree -> /Applications/Sourcetree.app/Contents/Resources/stree*
...
Since this folder is in the $PATH
these tools are automatically available.
Configuration
Configuration files are scattered all over the system.
- dotfiles, like
~/.zshrc
and~/.gitignore
- dotfolders, like
~/.ssh
and~/.config
- stuff under
~/Library/Preferences
- stuff under
~/Library/Application Support
- system preferences
- managed using the
defaults
command (see setup_macos.zsh)
- managed using the
- and more ...
As visualized in the diagram above:
- some config files are backed up to GitHub (as part of this 'dotfiles' project)
- others are backed up to Dropbox (using mackup)
Symlinks are used from the default location to the actual file inside ~/.dotfiles
or ~/Dropbox/Apps/Mackup
. For example: ~/.zshrc -> ~/.dotfiles/zshrc
.
Backup
As explained in the previous section, configuration files & scripts are stored in either ~/.dotfiles
or ~/Dropbox/Apps/Mackup
.
- Dotbot restores symlinks from the default locations to the actual files under
~/.dotfiles
- Mackup (triggered by the dotbot installation) restores symlinks from the default locations to the actual files under
~/Dropbox/Apps/Mackup
.
Some changes to the system are not automatically reflected in ~/.dotfiles
or ~/Dropbox/Apps/Mackup
:
- installing or removing a package with homebrew
- not automatically reflected in Brewfile !
- installing or removing a VScode extension
- not automatically reflected in vscode_extensions !
For this purpose I have written the bookkeeper, which periodically re-generates these files and commits them to GitHub.
NB: Beware that dotfiles
and mackup
can overlap. Always make sure that dot-files stored in this dotfiles
project are excluded from mackup ([applications_to_ignore]
section in mackup.cfg).
Update
The bookkeeper updates all installed Homebrew packages and applications. Installing bookkeeper as a background job will automate this for you.
NB: It is still your own responsibility to upgrade applications that were installed manually or from the App Store!
Best practices
- Installation of packages and applications
- always use homebrew (!!!)
- use the App Store only if an app is not available as a Homebrew cask
- try to avoid manual installation of tools or applications (hard to retrace, hard to update)
- if you do, consider adding it to the manual steps section
- Visual Studio Code
- installation / removal of extensions is automatically backed up to vscode_extensions by the bookkeeper; no action required
- Extend bookkeeper
- if you discover configuration that can only be generated (like 'Brewfile' and 'vscode_extensions')
- Use mackup (i.e. Dropbox) to backup configuration files containing sensitive information (passwords, email, etc.)
- do not store them in this .dotfile project!
Java, Node, Python
- Java
- use homebrew to (un)install JDKs (see below)
- use jenv to switch versions
- Node
- Python
HOW TO
HOW TO - replace pre-installed software with a Homebrew package
MacOS comes with a list of pre-installed tools in /usr/bin
.
For example less
, keytool
, more
, ssh
, zip
, etc ...
You don't want to mess around with the tools in /usr/bin
.
If you want to be able to manage one of these tools with Homebrew (and always use the latest version) you can install the tool alongside the pre-installed one:
which -a <pkg>
<pkg> --version
brew search <pkg>
brew install <pkg>
brew info <pkg>
# open a new shell
zsh
which -a <pkg>
<pkg> --version
As long as /opt/homebrew/bin
appears before /usr/bin
on the $PATH
the brew version will take precedence. On the last line you should see the newest version (installed with brew) instead of the pre-installed version. See this example (nano).
HOW TO - (un)install a JDK
There are detailed instructions on the Oracle website on the installation & removal of a JDK on macOS.
- Installation
brew install --cask oracle-jdk
- check that the JDK ends up in
/Library/Java/JavaVirtualMachines
- add JDK Home directory to JAVA_HOME_LOCATIONS in
setup_java.sh
- Example:
/Library/Java/JavaVirtualMachines/jdk-18.jdk/Contents/Home
- Example:
- re-run
~/.dotfiles/setup_java.sh
to have the new JDK version added to jenv
- Removal
brew uninstall --cask oracle-jdk
- remove JDK Home directory from JAVA_HOME_LOCATIONS in
setup_java.sh
- remove symlink manually from
~/.jenv/versions
NB: the oracle-jdk
cask has no version name. How to install multiple Oracle JDK versions alongside each other?
References
- Dotbot.
- Dotfiles
- Dotfiles from Start to Finish-ish (Udemy)
- Dotfiles repo example (github)
- Youtube
- defaults command:
- macos-defaults.com
- cfprefsd
- macOS Prefs Editor
- Example of a script with lots of defaults
- More info on the defaults command:
man defaults defaults help