Skip to content

Repository files navigation

Macbook Pro dotfiles and setup at GitLab

Goal: Bootstrap my work Macbook with software setup and settings automation.

Current hardware: Macbook Pro 14 inch, M1 Max, 32 GB RAM, 2021 M1 Silicon architecture.

Archive:

[TOC]

Essentials

Type Tools
Credentials 1Password, 1Password for Safari/Chrome
Backup Google Drive for Desktop
Agentic AI Agentic AI: GitLab Duo Agent Platform, Claude Code/Desktop, Glean
Containers Rancher Desktop
Browser Google Chrome, Safari
DevRel Adobe Creative Cloud (Premiere Pro, etc.) - enterprise license, Screen Studio (approved license) - handbook
Editor JetBrains IDE Toolbox (license required for IntelliJ IDEA, PyCharm, GoLand, RubyMine, CLion, RustRover, Rider, DataGrip, etc.).

Environment

Git and compilers

Install Git and compilers/SDK using Xcode install.

sudo xcode-select --switch /Applications/Xcode.app/Contents/Developer
sudo xcodebuild -license accept

neovim with lazyvim and treesitter requires compiling against native SDK.

Terminal

Type Tools
Terminal app Ghostty. iTerm2 as backup
Shell ZSH and Starship
Shell history Atuin in addition to ZSH history
Package manager Homebrew for packages, mise for dev envs (NodeJs, Ruby, etc.)
Editor neovim
Agents Claude Code, GitLab Duo CLI

Package manager

Homebrew

/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"

Packages are managed in Brewfile.

Mise

curl https://mise.run | sh
~/.local/bin/mise --version

Globally installed language frameworks are configured in .config/mise/config.toml. To reinstall them, run:

mise install

Setup

After cloning this repository, run:

./setup.sh

The script checks for Xcode Command Line Tools, installs Homebrew when needed, and applies the small Brewfile.

Important: setup.sh is safe to rerun: it installs and updates Brewfile packages, does not modify macOS defaults, and ensures all symlinks are in place.

Setup also links each skill under skills/ into ~/.claude/skills/, ~/.agents/skills/, and ~/.gitlab/duo/skills/ for Claude Code, Codex, and GitLab Duo, using the same skill directory name for each tool. Existing matching links are left in place; conflicting files or links stop setup for review. These links expose the public skills only; personal AI configuration stays in the home directory.

Ghostty is installed and updated directly from ghostty.org. Its tracked configuration lives in .config/ghostty and uses matching light and dark themes based on the macOS appearance setting. The Brewfile installs JetBrainsMono Nerd Font, which provides the optional symbols used by Starship.

Optional macOS preferences live in .macos. Review the script before applying it, then run:

zsh .macos

It covers keyboard and trackpad behavior, Finder paths and extensions, Dock visibility, immediate authentication after sleep, screenshots, muted system UI sounds, and the macOS application firewall. It does not change shell startup files, power settings, hostnames, hidden system directories, or application-specific preferences.

The reviewed GitHub CLI telemetry opt-out is applied directly by setup.sh and is safe to rerun. Other privacy changes remain narrowly scoped and opt-in; macOS preferences still require running .macos explicitly.

setup.sh links the tracked configuration to its destination in the HOME directory ~. All paths need to remain the same, e.g. .config/starship.toml. If that link has been replaced with a regular file, it stops and shows a recursive diff instead of overwriting local changes. Merge any wanted changes into this repository, remove the local file, and rerun the script.

Tools and Settings

Agentic AI

GitLab Duo Agent Platform

Provisioned access as team member, and Developer Advocate in gitlab.com/gitlab-da.

GitLab Duo CLI

Installed via glab CLI in the Brewfile. The ZSH alias duo runs glab duo cli.

  1. GitLab Duo CLI in the Dev Advocacy Handbook
  2. Add the Agentic Skills from skills/, see README for instructions.

Claude Code

  1. Follow the Developer Advocacy handbook
  2. Add the Agentic Skills from skills/, see README for instructions.

Codex

  1. Follow the Developer Advocacy handbook
  2. Add the Agentic Skills from skills/, see README for instructions.

Glean

Follow the handbook for access and setup.

Productivity

Neovim with LazyVim

Started off a fresh git clone following https://www.lazyvim.org/installation

Modified .config/nvim and symlinked into HOME. The editor uses the Gruvbox hard-contrast theme and follows the macOS light/dark appearance setting, matching the Ghostty themes.

Note: lazyvim uses treesitter which requires a compiler/SDK match with full XCode installation.

ZSH history with Atuin

Press Ctrl-R to search history with Atuin. Up and Down keep Zsh's native history navigation. Native history settings save commands incrementally to ~/.zsh_history, without importing commands from other active terminal sessions into the current shell.

Import existing history with

atuin import auto

ZSH completion and editor

Completion settings load Homebrew completions and initialize Zsh's completion system. Tab offers case-insensitive matching, then partial and substring matching, with selectable, grouped results. The completion cache lives under ${XDG_CACHE_HOME:-$HOME/.cache}/zsh.

.zshrc loads history, completion, aliases, and functions explicitly, followed by tool integrations. Syntax highlighting loads last. EDITOR and VISUAL are both set to nvim for commands that open an external editor.

Sudo

sudo vim /private/etc/sudoers.d/mfriedrich

mfriedrich ALL=(ALL) NOPASSWD: ALL

TinyCast - launcher and emoji picker

TinyCast is installed through Homebrew in Brewfile. It provides app launcher, search and emoji picker as a Spotlight alternative. The current shortcuts are:

  • Cmd+Space launches TinyCast.
  • Cmd+2 opens the emoji picker.

On a fresh macOS setup:

  1. Open Settings > Keyboard > Keyboard Shortcuts.
  2. Disable the Spotlight shortcuts so Cmd+Space can launch TinyCast.
  3. Start TinyCast and confirm its launcher shortcut is Cmd+Space.
  4. Open TinyCast, search for Settings, and open it.
  5. Select Emoji & Symbols.
  6. Enable Search Emoji & Symbols, click its shortcut field, and press Cmd+2.

VS Code

Install VS Code manually so its own updater controls its release cycle. Its user settings are tracked in .config/vscode/settings.json. setup.sh links that file to VS Code's macOS user-settings location. The editor follows macOS light and dark appearance automatically, using the built-in Light Modern and Dark Modern themes.

The tracked inventory lives in vscode/extensions.txt. After installing VS Code and any extensions manually, discover what is present with:

bash ./vscode-extensions-install.sh --discover

Review the result, then update the tracked inventory from the installed set with:

bash ./vscode-extensions-install.sh --update-inventory

Run the script without an option to install the tracked inventory on another Mac. Review the generated inventory before committing it; manually installed extensions can be adopted later without changing the script.

Settings

1Password overrides the screenshot shortcut cmd+shift+4+space by default with shift+cmd+space. Clear it in 1Password → Settings → General → Global keyboard shortcuts → Show Quick Access.

Ghostty

If Ghostty needs to remove protected application data, such as leftover files under ~/Library/, grant it access in:

System Settings > Privacy & Security > Full Disk Access

Enable Ghostty, restart it, and rerun the cleanup command. sudo alone cannot bypass macOS privacy protection for these directories.

Finder

Open Finder and navigate into Settings > Sidebar to add

  • User home (user name)
  • System root (Macbook name)

Zoom

https://handbook.gitlab.com/handbook/tools-and-tips/zoom/

Settings > General: Untick Ask me to confirm when I leave a meeting. Settings > Audio: Tick Mute my mic when joining. Settings > Keyboard Shortcuts: Mute/Unmute my audio: cmd 1.

Backup

Use Google Drive for Desktop, Chrome profile sync, and 1Password for credentials/SSH keys.

Keep personal .codex, .claude, and .cursor configuration in the home directory and private backups. Do not symlink these configurations into this public repository. Public, reusable skills can stay in skills/.

Close applications that write to these directories before copying. Run this from the home directory, adjusting the source list for files that exist on the machine. Each backup gets a new directory outside the repository:

cd "$HOME"
umask 077
backup_dir="$HOME/backup/$(date +%Y%m%d-%H%M%S)"
mkdir -p "$backup_dir/home"
cp -RL .ssh .gnupg .env .claude .codex .cursor .agents .config \
  .zsh_history .claude.json .ansible "$backup_dir/home/"

cp -RL copies the files behind symlinks, including linked dotfiles and skills. Review any copy errors before continuing; running applications can leave sockets that cannot be copied. This is a backup of the selected paths, not the whole home directory.

Create a tarball, then encrypt it with 7z from the Brewfile's p7zip package:

tar -czf "$backup_dir/home.tar.gz" -C "$backup_dir" home
7z a -t7z -mhe=on -p "$backup_dir/home.tar.gz.7z" "$backup_dir/home.tar.gz"
7z t "$backup_dir/home.tar.gz.7z"

Enter a strong password at the prompt and save it in 1Password. Upload only home.tar.gz.7z to Google Drive after verification succeeds. The copied home/ directory and home.tar.gz contain unencrypted private keys, credentials, and application data; keep the staging directory outside Google Drive and remove those unencrypted copies after checking the backup.

To verify a restore, download the encrypted archive and extract it into a new local directory. Replace the archive path below with the downloaded file:

restore_dir="$(mktemp -d "$HOME/backup/restore.XXXXXX")"
7z x /path/to/home.tar.gz.7z -o"$restore_dir"
tar -xzf "$restore_dir/home.tar.gz" -C "$restore_dir"

Inspect the restored files in "$restore_dir/home" before copying anything back into the home directory.

Development

GitLab Development Kit (GDK)

Follow the one-line installation and use mise (requirement since 2025-04).

Alternatively, use GDK-in-a-box with Docker containers.

GitLab Docs

The CI/CD pipelines for GitLab docs use linting which can be installed locally to test problems faster.

yarn global add markdownlint-cli2
yarn global add markdownlint-cli

mise plugin add vale && mise install vale

The VS Code editor integration is managed through vscode-extensions-install.sh.

cd ~/dev/work/gitlab-org/gitlab

yarn install

./scripts/lint-doc.sh

Troubleshooting

Zsh warns about insecure completion directories

When opening Ghostty, Zsh may prompt:

zsh compinit: insecure directories, run compaudit for list.
Ignore insecure directories and continue [y] or abort compinit [n]?

Run the following to identify the affected directories:

autoload -Uz compaudit
compaudit

On this workstation, /opt/homebrew/share was owned by the current user but group-writable. Check its permissions and remove group write access:

ls -ld /opt/homebrew/share
chmod g-w /opt/homebrew/share

Run compaudit again; no output means the check passed. Open a new Ghostty tab to confirm completion initializes without prompting. This fix needs no sudo, recursive permission changes, or completion-cache deletion.

If the audit lists different paths, inspect their ownership and permissions before changing them. Keep the normal compinit security checks enabled. See Homebrew's Zsh completion guidance.

DNS troubleshooting

If DNS causes problems on macOS:

sudo dscacheutil -flushcache
sudo killall -HUP mDNSResponder
sudo killall -9 mDNSResponder

Homebrew binary incompatibilities after macOS upgrades

On major version upgrades, binaries might be incompatible or need a local rebuild. You can enforce a reinstall by running the two commands below, the second command only reinstalls all application casks.

brew reinstall $(brew list)

brew reinstall $(brew list --cask)

When Xcode and compilers break, re-install the command line tools.

sudo rm -rf /Library/Developer/CommandLineTools
sudo xcode-select --install

Git xcrun errors on macOS Ventura upgrades

xcrun: error: invalid active developer path

You need to explicity agree to the terms of services for the developer tools.

xcode-select --install

Settings do not work after upgrades

The settings in .macos use macOS internal APIs on the command line. Sometimes the configuration settings change, for example with the Trackpad on macOS Ventura. To debug and capture which settings are in effect, create a new Git repository somewhere, and persist the system settings output.

mkdir $HOME/dev/work/system-settings
cd $HOME/dev/work/system-settings
git init

defaults read > settings.txt

git add settings.txt
git commit -av -m "Initial settings"

Then navigate into the Systems settings GUI, change parameters, export the system settings into the same file, and analyze the Git diff to figure out the correct parameter names and values.

defaults read > settings.txt

git diff

Example from June 2023

Thanks

Contributing

The main repository is hosted on GitLab.com, mirrored to GitHub.com: https://gitlab.com/dnsmichi/dotfiles

About

Configuration and scripts to bootstrap my Macbook Pro

Resources

Stars

14 stars

Watchers

1 watching

Forks

Releases

Packages

Used by

Contributors

Languages