If you use Homebrew to install apps or developer tools, you probably run commands like brew update and brew upgrade often.
Wouldn’t it be great if your Mac handled that automatically—without you having to open Terminal?
In this post, you’ll set up a simple, invisible background script that updates both Homebrew casks (macOS apps) and formulae (CLI packages) once per day. It runs quietly at login—no pop-ups, no notifications, no visible windows.
⸻
Step 1: Find Your Mac Username
- You’ll need your macOS username for one of the commands later.
- Open Terminal and type:
whoami
- Press Enter, and you’ll see something like:
john
That’s your username.
In the steps below, replace every YOUR_MACS_USERNAME with your actual username (for example, john).
⸻
Step 2: Create the Auto-Update Script
This script checks if it already ran today. If not, it runs Homebrew’s update and upgrade commands in the background — silently.
Copy and paste this into Terminal:
mkdir -p ~/.scripts
cat << 'EOF' > ~/.scripts/brew_auto_update.sh
#!/bin/zsh
LOGFILE="$HOME/.scripts/brew_daily.log"
TODAY=$(date +"%Y-%m-%d")
# Skip if today's update already ran
if grep -q "$TODAY" "$LOGFILE" 2>/dev/null; then
exit 0
fi
# Silent Homebrew maintenance
/opt/homebrew/bin/brew update >/dev/null 2>&1
/opt/homebrew/bin/brew upgrade --cask >/dev/null 2>&1
/opt/homebrew/bin/brew upgrade --formula >/dev/null 2>&1
/opt/homebrew/bin/brew upgrade >/dev/null 2>&1
/opt/homebrew/bin/brew cleanup >/dev/null 2>&1
# Mark completion
echo "$TODAY" >> "$LOGFILE"
EOF
chmod +x ~/.scripts/brew_auto_update.sh
- This creates and saves the script in a hidden folder ~/.scripts and makes it executable.
⸻
Step 3: Create the LaunchAgent
This tells macOS to automatically run the script when you log in.
Copy and paste this into Terminal (replace YOUR_MACS_USERNAME with your own username):
mkdir -p ~/Library/LaunchAgents
cat << 'EOF' > ~/Library/LaunchAgents/com.user.brewautoupdate.plist
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Label</key>
<string>com.user.brewautoupdate</string>
<key>ProgramArguments</key>
<array>
<string>/bin/zsh</string>
<string>/Users/YOUR_MACS_USERNAME/.scripts/brew_auto_update.sh</string>
</array>
<key>RunAtLoad</key>
<true/>
<key>KeepAlive</key>
<false/>
<key>StandardOutPath</key>
<string>/dev/null</string>
<key>StandardErrorPath</key>
<string>/dev/null</string>
</dict>
</plist>
EOF
- Now load the agent into macOS:
launchctl load ~/Library/LaunchAgents/com.user.brewautoupdate.plist
⸻
Step 4: Verify It’s Working
- To confirm that it’s loaded:
launchctl list | grep brewautoupdate
-
If you see an entry like this, it’s running:
0 com.user.brewautoupdate
To check whether it ran today:
cat ~/.scripts/brew_daily.log
- Each line shows the date the updater completed successfully.
⸻
Step 5: Disable (Optional)
- If you ever want to stop the automation, run:
launchctl unload ~/Library/LaunchAgents/com.user.brewautoupdate.plist
⸻
Done.
Your Mac now keeps itself updated with no interruptions and no visible background processes. Simple, efficient, and future-proof.
Top comments (2)
This Script:
~/.scripts/brew_daily.log
.It only updates software installed through Homebrew — both:
• Formulae → command-line tools installed with brew install something
• Casks → macOS apps installed with brew install --cask something
It does not affect:
• System apps from Apple
• Apps installed manually (drag-and-drop .app files)
• Apps from the Mac App Store