Blog · August 19, 2026 · 6 min read

terminal-notifier + Claude Code: Native macOS Alerts When Your Agent Finishes

If you want a real, native macOS notification — banner, sound, badge, the works — when Claude Code finishes a task, there are exactly two tools worth knowing. One ships with every Mac (osascript), and one is a twelve-year-old open-source classic that does the job better: terminal-notifier. This guide wires both into Claude Code, so your agent taps you on the shoulder instead of sitting silently finished — or silently stuck — behind your other windows.

What terminal-notifier is

terminal-notifier is a small command-line tool that posts genuine macOS User Notifications from scripts and terminals. It has been around since OS X Mountain Lion, it is a one-line Homebrew install, and unlike AppleScript one-liners it gives you proper options: titles, subtitles, custom sounds, notification groups, and — the killer feature for agent workflows — a flag that makes clicking the notification jump straight back to your terminal.

brew install terminal-notifier

Test it immediately:

terminal-notifier -title "Claude Code" -message "All done" -sound Glass

If a banner slides in from the top-right, you are in business. If nothing appears, jump to the permissions section below — macOS treats terminal-notifier as its own app and it needs notification permission once.

The one-liner version (no config at all)

The simplest pattern needs no setup inside Claude Code whatsoever: chain the notifier after any long command, exactly as you would with a build:

claude -p "run the test suite and fix failures" && terminal-notifier -title "Claude Code" -message "Task finished" -sound Glass

That works for one-shot, non-interactive runs. But most Claude Code sessions are interactive — and the moment you care about most is not just "done", it is "waiting for your permission". For that you want hooks.

Wiring terminal-notifier into Claude Code hooks

Claude Code fires hook events at exactly the two moments that matter: Stop (the agent finished responding) and Notification (it needs your input or permission). Add this to ~/.claude/settings.json:

{
  "hooks": {
    "Stop": [
      {
        "hooks": [
          {
            "type": "command",
            "command": "terminal-notifier -title 'Claude Code' -message 'Finished — come take a look' -sound Glass -group claude-code"
          }
        ]
      }
    ],
    "Notification": [
      {
        "hooks": [
          {
            "type": "command",
            "command": "terminal-notifier -title 'Claude Code' -message 'Waiting for your input' -sound Sosumi -group claude-code"
          }
        ]
      }
    ]
  }
}

Restart your Claude Code session so the hooks load. Two details doing quiet work here: different sounds for the two events (so you know from the next room whether it is done or blocked), and -group claude-code, which makes each new alert replace the previous one instead of piling up a stack of stale notifications. If hooks are new to you, our Claude Code hooks guide covers the format, and there is a deeper dive into the Notification event specifically.

Click to jump back to your terminal

The flag that makes terminal-notifier nicer than any AppleScript alternative: -activate takes an app bundle ID and brings that app forward when you click the notification.

# Terminal.app
terminal-notifier -title "Claude Code" -message "Done" -activate com.apple.Terminal

# iTerm2
terminal-notifier -title "Claude Code" -message "Done" -activate com.googlecode.iterm2

Notification arrives, you click it, and you are looking at the session that needs you. No dock hunting.

The zero-install alternative: osascript

Every Mac can post a notification without installing anything, via AppleScript:

osascript -e 'display notification "Task finished" with title "Claude Code" sound name "Glass"'

It works in the same hooks, and it is fine for a quick start. The trade-offs: since macOS Big Sur the notification is attributed to whatever app ran the script (your terminal), macOS will ask for notification permission on first use, and you get none of the grouping, activation, or click behaviour above. Start with osascript if you like; most people graduate to terminal-notifier within a week.

When the notification never shows up

Three culprits cover nearly every silent failure:

  • Permission was never granted. Open System Settings → Notifications, find terminal-notifier (or your terminal app, for osascript) and allow alerts. If you are seeing the infamous "notifications are turned off for Claude" message instead, that one has its own step-by-step fix.
  • Focus mode is eating it. Do Not Disturb and Focus silently swallow banners. Either allow the app in your Focus settings or check Notification Center — the alerts are usually sitting there.
  • The hook command is not on PATH. Hooks run in a minimal shell. If terminal-notifier works in your terminal but not from a hook, use the absolute path — /opt/homebrew/bin/terminal-notifier on Apple Silicon.

The honest limits of the DIY route

This setup is good, and for a single tool it may be all you need. Its ceiling: the config lives per machine, the two events are only as granular as your hook commands, and if you also run Cursor, Codex CLI or Gemini CLI you get to repeat the wiring in three other formats — our notification scripts roundup shows quite how varied that zoo is.

Either way, stop watching the terminal scroll. Your agent can wait for you — you should not have to wait for it.

Keep reading

Claude Code Tips and Tricks: 12 Ways to Use Claude Code Effectively

8 min read

Claude Code Multiple Sessions: How to Run Agents in Parallel Without Losing Track

6 min read

A Claude Code Workflow That Doesn't Involve Watching the Terminal

5 min read

Claude Code Hooks: A Practical Guide to Automating Your Agent Workflow

7 min read

Claude Code Auto Mode: Fewer Permission Prompts Without Living Dangerously

7 min read

Claude Code Subagents: How to Delegate Work to Specialized Agents

7 min read

Claude Code Context Management: Treat the Context Window Like a Budget

6 min read

Per-Subagent Model Selection: Route the Grunt Work Down, Keep the Judgment Up Top

7 min read

Skills and Plugins: How to Teach Claude Code Your Way of Working

7 min read

Claude Code Background Tasks: Run Long Commands Without Blocking Your Session

6 min read

Codex CLI Notifications: How to Get a Ding When Codex Is Done or Needs Input

7 min read

Cursor Notification When Done: Every Way to Get Notified When Cursor Finishes

6 min read

Claude Code Notifications: How to Get Notified When Claude Code Finishes or Needs Your Input

6 min read

Want to Be Notified When Claude Responds? How Claude Notifications Work on Web, Desktop, and Mobile

5 min read

Claude Code Notification Scripts: Copy-Paste Recipes for Every Platform

6 min read

Get a Ding the Moment Codex Needs Your Response

6 min read

Get Notified the Moment Claude Code Is Waiting for Your Input

6 min read

“Notifications Are Turned Off for Claude” — Here Is the Fix

6 min read

Codex Sound When Done: Make Codex CLI Play a Sound When It Finishes

6 min read

Gemini CLI Notifications: How to Get a Sound or Alert When Gemini Finishes

6 min read

Get Claude Code Notifications on Your Phone

6 min read