Thanks to visit codestin.com
Credit goes to github.com

Skip to content

nkyy/cat-ccnotify-hook

Repository files navigation

🐱 cat-ccnotify-hook

Enhanced Claude Code notification hooks with adorable cat sounds and better styling for macOS.

✨ Features

  • 🐱 Adorable cat meow for all notifications
  • 🎨 Enhanced styling with emojis and better formatting
  • 🧠 Intelligent categorization of notifications (success, error, warning, etc.)
  • πŸ›‘ Special stop notifications with the same adorable cat meow
  • 🍎 macOS optimized using native notification system
  • πŸ€– Automatic environment detection - works seamlessly in SSH, CI, and pipe environments

πŸ“¦ Installation

Via npm (Recommended)

# Install globally
npm install -g cat-ccnotify-hook

# Run the installer
cat-ccnotify-install

This will automatically:

  • Install the package globally
  • Create the ~/.claude directory if needed
  • Update ~/.claude/settings.json with the correct hook configuration
  • Configure Claude Code to use cat notifications

⚠️ Important: After installation, reload Claude Code hooks:

  1. Type /hooks in Claude Code
  2. Press ESC immediately

Local Installation (Development)

  1. Clone this repository:

    git clone https://github.com/cat-ccnotify/cat-ccnotify-hook.git
    cd cat-ccnotify-hook
  2. Install dependencies:

    npm install
  3. Run the installer:

    npm run install-hooks

πŸ§ͺ Testing

Test your installation to make sure everything works:

# Simple notification test (recommended)
cat-notify

# Custom notification
cat-notify "My Title" "My custom message"

# Test actual hook functionality with Claude Code data format
cat-notify --notification-hook
cat-notify --stop-hook

# Test hooks via npm command
cat-ccnotify-test

# Or manually test hooks
node hooks/notification-hook.js
echo '{"title":"Test","message":"Session ended"}' | node hooks/stop-hook.cjs

You should see notifications with:

  • 🐱 Cat meow sounds
  • πŸ“± Native macOS notifications
  • 🎨 Appropriate emojis (βœ… for success, ❌ for errors, etc.)
  • πŸ“ Your actual message content

🎡 Enhanced Notification System

All notifications play the same adorable cat meow sound! 🐱

🧠 Smart Categorization

The system intelligently analyzes your notification content and automatically adds appropriate emojis:

  • βœ… Success: complete, success, passed, done, deployed, published
  • ❌ Error: error, failed, crash, exception, cannot, invalid
  • ⚠️ Warning: warning, deprecated, caution, should, might
  • πŸ’‘ Info: General information and status updates
  • ⏳ Progress: running, processing, installing, building, loading
  • πŸ”„ Git: commit, push, pull, merge, branch, repository
  • πŸ—οΈ Build: build, compile, bundle, webpack, typescript
  • πŸ§ͺ Test: test, spec, jest, coverage, assertion
  • πŸš€ Deploy: deploy, release, production, staging, live
  • πŸ“¦ NPM: npm, yarn, package, dependency, install
  • πŸ“„ File: file, directory, write, read, created, modified

πŸ“ Dynamic Content

Instead of showing generic messages, you'll see your actual notification content:

  • "βœ… Tests Passed - All 25 tests completed successfully!"
  • "❌ Git Push Failed - Permission denied to repository"
  • "πŸ—οΈ Build Complete - TypeScript compilation finished"

Note: All categories use the same adorable cat meow sound. Future versions may include category-specific sounds!

πŸ”§ Configuration

The hooks are automatically configured in ~/.claude/settings.json. You can view the current configuration:

cat ~/.claude/settings.json | jq '.hooks'

Hook Configuration Format

The hooks are configured in the new Claude Code format:

{
  "hooks": {
    "Notification": [
      {
        "type": "command",
        "command": "node /path/to/notification-hook.js",
        "description": "Cat-themed notification with meow sound"
      }
    ],
    "Stop": [
      {
        "type": "command",
        "command": "node /path/to/stop-hook.cjs",
        "description": "Cat-themed session end notification"
      }
    ]
  }
}

Reloading Configuration

After installation or making manual changes:

  1. Type /hooks in Claude Code
  2. Press ESC immediately to reload settings

Environment Variables

You can customize the notification behavior with these environment variables:

# Force console output (echo) instead of system notifications
export CAT_CCNOTIFY_FORCE_CONSOLE=true

# Enable debug logging
export CAT_CCNOTIFY_DEBUG=true

πŸ€– Automatic Environment Detection: The system automatically detects when to use console output in these scenarios:

  • SSH connections without X11 forwarding (SSH_CONNECTION without DISPLAY)
  • CI environments (GitHub Actions, GitLab CI, Jenkins, Travis, CircleCI, etc.)
  • Non-TTY environments (pipes, redirects, background processes)

Examples:

# SSH connection - automatically uses console output
ssh user@server
claude-code  # β†’ 🐱 Console notifications

# CI environment - automatically uses console output  
# GitHub Actions, GitLab CI, etc.
claude-code  # β†’ 🐱 Console notifications

# Pipe usage - automatically uses console output
claude-code | tee output.log  # β†’ 🐱 Console notifications

# Normal desktop usage - uses GUI notifications
claude-code  # β†’ Native macOS notifications + sound

Manual override (rarely needed):

# Force console output even in GUI environments
export CAT_CCNOTIFY_FORCE_CONSOLE=true

# Or temporarily
CAT_CCNOTIFY_FORCE_CONSOLE=true claude-code

Priority order:

  1. CAT_CCNOTIFY_FORCE_CONSOLE=true (manual override)
  2. Automatic environment detection
  3. Platform-specific GUI notifications
  4. Console fallback

πŸ“ Project Structure

cat-ccnotify-hook/
β”œβ”€β”€ package.json              # Package configuration and npm scripts
β”œβ”€β”€ README.md                # This documentation
β”œβ”€β”€ INSTALL.md               # Detailed installation guide
β”œβ”€β”€ PUBLISHING.md            # npm publishing instructions
β”œβ”€β”€ jest.config.js           # Test configuration
β”œβ”€β”€ .npmignore               # npm package exclusions
β”œβ”€β”€ bin/
β”‚   └── cat-notify              # Command line testing tool
β”œβ”€β”€ hooks/                   # Core hook implementations
β”‚   β”œβ”€β”€ notification-hook.js    # Smart notification processor
β”‚   β”œβ”€β”€ stop-hook.cjs           # Session end handler
β”‚   └── hooks.json              # Hook configuration template
β”œβ”€β”€ lib/                     # Shared utilities
β”‚   β”œβ”€β”€ shell-executor.js       # Secure command execution (ES)
β”‚   β”œβ”€β”€ shell-executor.cjs      # Secure command execution (CJS)
β”‚   β”œβ”€β”€ error-handler.js        # Comprehensive error handling (ES)
β”‚   └── error-handler.cjs       # Comprehensive error handling (CJS)
β”œβ”€β”€ sounds/                  # Audio assets
β”‚   └── cat-meow-1-fx-323465.mp3 # Adorable cat meow sound
β”œβ”€β”€ scripts/                 # Management tools
β”‚   β”œβ”€β”€ install-hooks.js        # Intelligent installer
β”‚   β”œβ”€β”€ uninstall-hooks.js      # Clean uninstaller
β”‚   └── test-hooks.js           # Manual testing utility
└── test/                    # Test suite
    β”œβ”€β”€ unit/                   # Unit tests
    β”‚   β”œβ”€β”€ shell-executor.test.js  # Shell execution tests
    β”‚   └── error-handler.test.js   # Error handling tests
    └── e2e/                    # End-to-end tests
        └── notification-flow.test.js # Full workflow tests

πŸ“„ Key Files

  • hooks/notification-hook.js: Main notification processor with smart categorization
  • hooks/stop-hook.cjs: Handles Claude Code session termination
  • lib/shell-executor.js: Secure execution of macOS commands
  • lib/error-handler.js: Comprehensive error handling and logging
  • scripts/install-hooks.js: Automatic hook configuration setup
  • test/: Complete test suite with unit and E2E tests

πŸ› οΈ Development

πŸš€ Quick Start

# Test hooks with different notification types
node hooks/notification-hook.js "Tests Passed" "All 25 tests completed successfully!"
node hooks/notification-hook.js "Build Failed" "TypeScript compilation errors found"
node hooks/notification-hook.js "Git Push" "Successfully pushed to origin/main"

# Test with JSON input
echo '{"title":"Deploy Complete","message":"Application deployed to production"}' | node hooks/notification-hook.js

# Test stop hook
echo '{"title":"Session Ended","message":"Claude Code session terminated"}' | node hooks/stop-hook.cjs

# Run test suite
npm test
npm run test:unit
npm run test:e2e

# Test with debug mode
CAT_CCNOTIFY_DEBUG=true node hooks/notification-hook.js "Debug Test" "Testing with detailed logging"

πŸ”Š Adding new sounds

  1. Add audio files to the sounds/ directory (supported: .mp3, .wav, .m4a, .aiff, .aac)
  2. Update hook files to reference new sounds in the sendEnhancedNotification function
  3. Test audio playback: afplay sounds/your-new-sound.mp3
  4. Test integration: npm test

🎨 Customizing notifications

  1. Modify emoji mappings in enhanceNotificationStyle() function
  2. Add new categories in analyzeNotificationContent() function
  3. Adjust content patterns to match your workflow
  4. Test changes: Run notification tests to verify new behavior

πŸ—‘οΈ Uninstallation

# If installed via npm:
cat-ccnotify-uninstall

# If installed locally:
cd /path/to/cat-ccnotify-hook
npm run uninstall-hooks

# Or manually edit ~/.claude/settings.json to remove the notification and stop hook entries

This will restore Claude Code to use default notifications.

🐾 How it works

πŸ”” Notification Flow

  1. Claude Code triggers a notification (file saved, command completed, error occurred, etc.)
  2. Hook receives data via multiple input methods:
    • Environment variables (CLAUDE_NOTIFICATION, NOTIFICATION_TITLE)
    • JSON data through stdin
    • Plain text through stdin
    • Command line arguments
  3. Content analysis - AI categorizes the notification (success, error, warning, git, build, etc.)
  4. Enhancement applied:
    • Appropriate emoji added (βœ…, ❌, ⚠️, πŸ—οΈ, etc.)
    • Content formatting and truncation
    • Context-aware styling
  5. Native macOS notification displayed using osascript
  6. Cat sound plays using afplay

πŸ›‘ Stop Hook

  1. Claude Code session ends
  2. Stop hook triggered with session metadata
  3. Special notification shown: "🐱 Claude Code - セッション硂了: [session info]"
  4. Cat meow plays to signal session end

πŸ“Š Smart Input Processing

The hook intelligently handles various input formats:

// JSON format
{"title":"Build Complete","message":"Compilation successful"}

// Plain text
"Tests passed - 25/25 successful"

// Multi-line
"Git Push Failed\nPermission denied to repository"

// Command args
node notification-hook.js "Title" "Message"

πŸ› Debug Mode

For troubleshooting, enable debug mode to see comprehensive logging:

# Enable debug mode for a single test
CAT_CCNOTIFY_DEBUG=true node hooks/notification-hook.js "Debug Test" "Testing notification"

# Set globally for your session
export CAT_CCNOTIFY_DEBUG=true

# View debug logs
tail -f ~/.claude/cat-ccnotify/notification-hook.log
tail -f ~/.claude/cat-ccnotify/stop-hook.log

# View recent debug activity
tail -20 ~/.claude/cat-ccnotify/notification-hook.log

πŸ” Debug Information Includes

  • Environment Analysis: All Claude-related environment variables
  • Input Processing: Raw stdin, JSON parsing, command line arguments
  • Content Analysis: How notifications are categorized
  • Enhancement Process: Emoji addition and message formatting
  • Execution Flow: Each step of the notification process
  • Error Details: Comprehensive error reporting and stack traces
  • System Info: Process arguments, working directory, file paths

πŸ“Š Example Debug Output

=== Debug Information ===
Process arguments: ["node", "/path/to/notification-hook.js", "Tests Passed", "All tests successful"]
Env CLAUDECODE: "1"
Using command line arguments: ["Tests Passed", "All tests successful"]
=== Final Result ===
Title: "Tests Passed"
Message: "All tests successful"
Level: "info"
Analyzed notification type: success
Enhanced notification - Title: "βœ… Tests Passed", Message: "All tests successful"

πŸ” Troubleshooting

πŸ”‡ No sound playing

  1. Check audio file: ls sounds/cat-meow-1-fx-323465.mp3
  2. Test audio manually: afplay sounds/cat-meow-1-fx-323465.mp3
  3. Check macOS sound settings and volume levels
  4. Verify permissions: macOS may block audio from scripts

πŸ“΅ No notifications appearing

  1. Check notification permissions: System Settings β†’ Notifications β†’ Terminal/iTerm
  2. Test manually: osascript -e 'display notification "Test" with title "Test"'
  3. Verify hooks config: cat ~/.claude/settings.json | grep -A 20 hooks
  4. Check Claude Code version: Ensure you're using a compatible version

🚫 Hooks not triggering

  1. Verify installation:

    which claude
    cat ~/.claude/settings.json | grep hooks
  2. Reload hooks: Type /hooks in Claude Code, then press ESC

  3. Enable debug mode:

    export CAT_CCNOTIFY_DEBUG=true
    # Test a notification to generate logs
    echo '{"title":"Debug","message":"Test"}' | node hooks/notification-hook.js
    # Check logs
    tail -f ~/.claude/cat-ccnotify/notification-hook.log
  4. Check file permissions: ls -la ~/.claude/settings.json

  5. Verify hook paths: Ensure the paths in settings.json point to existing files

πŸ”§ Common Issues

  • "Command not found": Use full paths in settings.json
  • "Permission denied": Check file permissions with chmod +x hooks/*.js
  • "Module not found": Ensure all dependencies are installed
  • Silent failures: Enable debug mode to see detailed error messages
  • Script opens when clicking notification: This is a macOS behavior when notifications are sent from scripts

πŸ“± Notification Click Behavior

Issue: Clicking on notifications may open the script file in your default editor.

Why this happens: macOS associates notifications with their source. When sent from a script, clicking the notification opens that script.

Solutions:

  1. Ignore the behavior: The notification functionality works perfectly; you can simply ignore clicking on them.

  2. Install terminal-notifier (recommended):

    # Install via Homebrew
    brew install terminal-notifier
    
    # The hooks will automatically use it if available
  3. Change default app for .js files:

    • Right-click any .js file β†’ "Get Info"
    • Under "Open with", select a different app
    • Click "Change All..."
  4. Disable notification clicking:

    • System Settings β†’ Notifications β†’ Script Editor (or Terminal)
    • Turn off "Allow Notifications"
    • This prevents the script from opening but may disable other notifications

Note: This is a macOS system behavior, not a bug in cat-ccnotify-hook. The notifications work correctly; the click behavior is just a side effect of how macOS handles script-generated notifications.

# Enable debug mode
export CAT_CCNOTIFY_DEBUG=true

# Or set it permanently in your shell profile
echo 'export CAT_CCNOTIFY_DEBUG=true' >> ~/.zshrc

# View logs (only created when debug mode is enabled)
tail -f ~/.claude/cat-ccnotify/notification-hook.log
tail -f ~/.claude/cat-ccnotify/stop-hook.log

# View all cat-ccnotify logs
tail -f ~/.claude/cat-ccnotify/*.log

πŸ“ Requirements

  • macOS (uses afplay and osascript)
  • Node.js 16+
  • Claude Code CLI installed

🀝 Contributing

  1. Fork the repository
  2. Create a feature branch
  3. Make your changes
  4. Test thoroughly
  5. Submit a pull request

πŸ“„ License

MIT License - see LICENSE file for details.

πŸ™ Credits

  • Cat sound effects from freesound.org
  • Built for the Claude Code CLI by Anthropic
  • Inspired by the need for more delightful notifications

Made with πŸ’ and 🐱 for Claude Code users who love cats!

About

Cat-themed notification hooks for Claude Code CLI with adorable cat sounds

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Contributors 2

  •  
  •