DEV Community

Cover image for How I Freed 15GB on My 256GB MacBook and Made an External SSD My Primary Storage (With 46 Automation Scripts)
Shravan Omanakuttan
Shravan Omanakuttan

Posted on

How I Freed 15GB on My 256GB MacBook and Made an External SSD My Primary Storage (With 46 Automation Scripts)

My MacBook's internal storage was full. Not "almost full" — full. No more space for new projects, no room for dependencies, constant "Your disk is almost full" alerts.

I had a 1TB external SSD sitting on my desk doing nothing.

So I built a system to use the SSD as my Mac's primary storage — transparently, automatically, with a full terminal menu and 18 scheduled automation scripts running in the background.

Here's exactly how I did it, and how you can too.


The Problem

256GB internal SSD. Here's what was eating it:

What Size
Notion app data 7.7G
Google Chrome cache 7.4G
Claude desktop 6.8G
OperaGX 1.6G
VS Code 1.7G
Discord 998M
Whisky (unused) 854M
Wondershare installer 493M
TabNine models 477M
.rustup toolchain 1.4G
.android SDK 515M
.pub-cache 434M
.nvm Node versions 204M
.npm cache 460M

That's ~30GB in things that either don't need to be on the internal drive or can be moved transparently.


The Solution: SSD as Primary Storage via Symlinks

The core idea is simple. macOS follows symlinks transparently — apps and tools have no idea they're reading from an external drive.

# Move Downloads to SSD
mv ~/Downloads /Volumes/007/Downloads
ln -s /Volumes/007/Downloads ~/Downloads

# Now everything that writes to ~/Downloads
# actually writes to the SSD — no config changes needed
Enter fullscreen mode Exit fullscreen mode

I did this for:

  • ~/Downloads, ~/Documents, ~/Desktop, ~/Movies
  • All Dev projects (leadgen-platform, linkedin_automate, etc.)
  • Toolchains: .rustup, .cargo, .android, .nvm, .npm, .m2, .gradle, .pub-cache

Result: 36GB freed on internal. Mac went from 96% full to 68% full in one session.


The Automation Layer

Moving files manually is a one-time fix. The real value is automation. I built 27 shell scripts and wired them to macOS launchd.

ssd — Terminal Menu for SSD Management

  ╔═══════════════════════════════════════════════════════════════════════╗
  ║                      ◈  SSD TOOLS — 007  ◈                           ║
  ╚═══════════════════════════════════════════════════════════════════════╝

  ● SSD 007   899G free / 33G used       ● Mac Internal  36G free / 17G used

  STORAGE & SYSTEM
  ┌──────┬──────────────────────┬────────────────────────────────────────┐
  │  1   │  mount-check         │  Check SSD mount + symlink health      │
  │  2   │  cache-cleanup       │  Clear caches (Library, npm, pnpm)     │
  │  3   │  low-disk-alert      │  Check internal Mac free space         │
  │  7   │  duplicate-finder    │  Scan SSD for duplicate files          │
  │ 12   │  ssd-health          │  SSD space + fill prediction           │
  └──────┴──────────────────────┴────────────────────────────────────────┘

  DEV & CODE
  ┌──────┬──────────────────────┬────────────────────────────────────────┐
  │  5   │  dev-backup          │  Rsync active projects to backup       │
  │  9   │  git-status          │  Uncommitted changes across projects   │
  │ 20   │  env-backup          │  Backup all .env files                 │
  │ 25   │  focus-mode          │  Block distractions (25min)            │
  └──────┴──────────────────────┴────────────────────────────────────────┘
Enter fullscreen mode Exit fullscreen mode

mac — Terminal Menu for Mac System Tools

  ╔═══════════════════════════════════════════════════════════════════════╗
  ║                    ◈  MAC TOOLS — SHRAVAN  ◈                         ║
  ╚═══════════════════════════════════════════════════════════════════════╝

  CPU 12%   Battery 100% (charged)   Uptime 2 days
  Wifi HomeNetwork   IP 192.168.1.6

  SYSTEM        APPS           MAINTENANCE      SECURITY        POWER
  system-stats  kill-hogs      clear-caches     firewall-status caffeinate
  battery-health app-usage     brew-update      open-ports      sleep-timer
  wifi-info     startup-items  run-all-agents   lock-screen     battery-saver
  processes     force-quit     large-files      ssh-keys
Enter fullscreen mode Exit fullscreen mode

The 18 Scheduled LaunchAgents

These run automatically via macOS launchd — no cron, no manual triggers.

# Check what's running
launchctl list | grep shravan
Enter fullscreen mode Exit fullscreen mode
Agent Schedule What it does
dev-backup Nightly 11pm Rsync projects to SSD backup, keeps 7 days
dotfiles-backup Nightly 10:30pm Backup .zshrc, .gitconfig, SSH config
env-backup Nightly 10pm Backup all .env files, keeps 14 days
cache-cleanup Monday 9am Clear Library/Caches, npm, pnpm
git-status Daily 9am Report uncommitted changes across all projects
dep-audit Monday 10am npm vulnerability scan
ssd-health Daily 10am Space usage + fill rate prediction
low-disk-alert Every hour Alert if Mac internal < 5GB free
ram-monitor Every 5min Log RAM usage
battery-logger Daily 12pm Log battery cycles + health

Serial Lock: SSD Only Works on My Mac

I didn't want the SSD to work if stolen. So I built a serial number lock:

#!/bin/zsh
AUTHORIZED_SERIAL="CPWY0XTG9Y"
CURRENT_SERIAL=$(system_profiler SPHardwareDataType | grep "Serial Number" | awk '{print $NF}')

if [ "$CURRENT_SERIAL" != "$AUTHORIZED_SERIAL" ]; then
  diskutil eject disk5
  osascript -e 'display alert "Unauthorized Mac. SSD ejected." as critical'
fi
Enter fullscreen mode Exit fullscreen mode

This fires automatically via a WatchPaths LaunchAgent whenever the SSD mounts. Wrong Mac → instant eject.


The Install Script

The whole toolkit is packaged with a one-command installer:

git clone https://github.com/sxrxvxnn/mac-ssd-toolkit
cd mac-ssd-toolkit
./install.sh
Enter fullscreen mode Exit fullscreen mode

It asks for your username, SSD volume name, and project names — then configures everything, installs LaunchAgents, and adds aliases to .zshrc.


Results

Before After
23GB free 36GB free
Manual backups Nightly automated
No disk monitoring Hourly alerts
Scattered dotfiles Nightly backup
No SSD security Serial lock

What's Next

The repo is open source and looking for contributors. If you have ideas for new scripts — storage tools, dev workflow automation, system monitoring — open an issue or PR.

GitHub: github.com/sxrxvxnn/mac-ssd-toolkit

Ideas already in the backlog:

  • Git commit streak tracker
  • Wifi speed daily logger
  • Auto-organize Downloads by file type
  • Monthly storage trend report

If you're a Mac developer with limited internal storage, give it a try. One command and you're set up.


Built while working as a BD intern at Beagle Security, building Sonar — an Apollo-style B2B intelligence platform.


Enter fullscreen mode Exit fullscreen mode

Top comments (1)

Collapse
 
alexshev profile image
Alex Shev

This is a very practical kind of automation because storage cleanup is usually death by small forgotten directories. Scripts help most when they make the state visible before deleting or moving anything.

I would keep a dry-run mode and a recovery path as first-class features. External SSD workflows are great, but the dangerous moment is when a script turns "move cache" and "move source of truth" into the same-looking operation.