I have found myself needing to set up a machine from scratch and, this time, I've decided to write a script to automate setups in future. The full script is on GitHub but I wanted to talk through each step in case others want to do the same.
Execution
I want the script to be executable from a single shell file hosted on GitHub. As GitHub serves static files via the githubusercontent.com
domain, the script can be downloaded and immediately run by bash.
bash <(curl -Ls https://raw.githubusercontent.com/phazonoverload/machine-setup/main/setup.sh)
At the very top of the script, tell the system to use bash to execute it, and to exit if any command fails.
#!/bin/bash
set -e
Install Xcode and Homebrew
XCode comes with a bunch of essential utilities, so we check if it's installed and install if not. Homebrew will be used later to install lots of software, so also check if it exists, and install it if not. This also runs postinstall commands for Homebrew, and fetches latest repository data.
if xcode-select --install 2>&1 | grep installed; then
echo "xcode already installed";
else
xcode-select --install
fi
if test ! $(which brew); then
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
echo 'eval "$(/opt/homebrew/bin/brew shellenv)"' >> /Users/$USER/.zprofile
eval "$(/opt/homebrew/bin/brew shellenv)"
fi
brew update
Install & Configure Git
Install git via Homebrew, configure global settings including git ac
which I have in muscle memory for lazy committing-all, generate a new SSH key pair, and make it easy to immediately add to GitHub.
brew install git
echo -n 'Git username: '
read username
git config --global user.name "$username"
echo -n 'Git email: '
read mail
git config --global user.email $mail
git config --global alias.ac "!git add -A && git commit -m "
ssh-keygen -t rsa
cat ~/.ssh/id_rsa.pub
open -a Safari https://github.com/settings/keys
read -p "Add public key to GitHub and hit [Enter]."
Install Software via Homebrew
Install the GitHub CLI, wget, and mas to later install apps via the Mac App Store.
clis=(
gh
wget
mas
)
brew install ${clis[@]}
Then we install all of the tools with a UI available as a cask:
casks=(
1password
arc
caffeine
camo-studio
cleanshot
cyberduck
cyberghost-vpn
discord
elgato-camera-hub
elgato-control-center
elgato-wave-link
firefox
font-geist-mono
google-chrome
raycast
screenflow
signal
slack
todoist
vanilla
visual-studio-code
visual-studio-code@insiders
whatsapp
zoom
)
brew install --cask ${casks[@]}
And finally cleanup any unused files or caches:
brew cleanup
Install Software via Mac App Store
Some apps are only accessible via the Mac App Store. The first time I wrote this script, I manually installed them and then used mas
(installed earlier as a CLI tool with brew
) to list existing apps with mas list
to reveal the unique IDs for the apps in order to write the lines below:
mas install 1569813296 # 1Password for Safari
mas install 682658836 # GarageBand
mas install 409201541 # Pages
mas install 409203825 # Numbers
mas install 361285480 # Keynote
mas install 6475002485 # Reeder
Install Node via Volta
I use Volta as my Node version management tool. Grab the latest version of Node, and make it the default.
brew install volta
volta install node@latest
volta setup
Download & Configure Oh My Zsh
I use Zsh as my terminal shell with Oh My Zsh! There's a couple of manual steps in here because I was too lazy to fully automate editing lines in the default .zshrc
but that's ok! This also downloads the common theme which I like.
curl -L http://install.ohmyz.sh | sh
wget -O ${ZSH_CUSTOM:-$HOME/.oh-my-zsh/custom}/themes/common.zsh-theme https://raw.githubusercontent.com/jackharrisonsherlock/common/master/common.zsh-theme
open ~/.zshrc
read -p "Set ZSH_THEME=\"common\" and then [enter]"
git clone https://github.com/zsh-users/zsh-autosuggestions ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-autosuggestions
git clone https://github.com/zsh-users/zsh-syntax-highlighting.git ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-syntax-highlighting
open ~/.zshrc
read -p "Please add zsh-autosuggestions & zsh-syntax-highlighting to your Plugins! and hit [enter]."
chsh -s /usr/local/bin/zshd
Configure Mac Settings
A bunch of macOS settings can actually be done via the terminal.
# Dock
defaults write com.apple.dock "orientation" -string "right"
defaults write com.apple.dock "tilesize" -int "24"
defaults write com.apple.dock "autohide" -bool "true"
defaults write com.apple.dock "show-recents" -bool "false"
defaults write com.apple.dock "mineffect" -string "scale"
defaults write com.apple.dock "autohide-delay" -float "2"
killall Dock
# Screenshots
defaults write com.apple.screencapture "type" -string "png"
mkdir -p "$HOME/Pictures/screenshots"
defaults write com.apple.screencapture "location" -string "$HOME/Pictures/screenshots" && killall SystemUIServer
defaults write com.apple.screencapture "disable-shadow" -bool "true"
# Safari
defaults write com.apple.Safari "ShowFullURLInSmartSearchField" -bool "true" && killall Safari
# Finder
defaults write NSGlobalDomain "AppleShowAllExtensions" -bool "true"
defaults write com.apple.finder "AppleShowAllFiles" -bool "true"
defaults write com.apple.finder "ShowPathbar" -bool "true"
defaults write com.apple.finder "FXEnableExtensionChangeWarning" -bool "false"
killall Finder
# Menu Bar
defaults write com.apple.menuextra.clock "DateFormat" -string "\"HH:mm\""
# Mission Control
defaults write com.apple.dock "mru-spaces" -bool "false" && killall Dock
# Window Manager
defaults write com.apple.WindowManager EnableStandardClickToShowDesktop -bool false && killall WindowManager
# Power
defaults write com.apple.screensaver idleTime 0
Last Bits
Because Raycast and VS Code both have excellent settings syncs, they can just be turned on and authenticated and everything snaps back to what it should be. This includes all of my keyboard shortcuts for window management, clipboard management, and AI panels.
In case this falls out of date, the latest version will be on GitHub.