π Table of Contents
- β¨ Features
- π Quick Start
- βοΈ Configuration
- π Rules
- β¨οΈ Keybindings
- π¨ Themes
- ποΈ Architecture
- π§ Building from Source
- π€ Contributing
- π License
β¨ Features
π Smart File Watching
Watch any folder for new and changed files with configurable debouncing and recursive monitoring.
π― Flexible Rules Engine
Define powerful rules with conditions based on name, extension, size, age, and more.
β‘ Powerful Actions
Move, copy, rename, delete, archive files, or run custom scripts β all automated.
π₯οΈ Beautiful TUI
A gorgeous terminal interface for managing rules and monitoring activity in real-time.
π§ Background Daemon
Set it and forget it β the daemon runs quietly and applies rules 24/7.
π Simple Configuration
Human-readable TOML config that's easy to write and maintain.
Feature Highlights
| Feature | Description |
|---|---|
| π Pattern Matching | Glob patterns and regex for precise file matching |
| π Size Conditions | Filter files by size (greater than, less than) |
| π Age Conditions | Match files by modification date |
| π·οΈ Multiple Extensions | Match any of multiple file types |
| π Recursive Watching | Monitor subdirectories automatically |
| π¨ 15 Built-in Themes | From Dracula to Cyberpunk |
| π Dry Run Mode | Preview what would happen before applying |
| π Activity Log | Full history of all file operations |
π Quick Start
Installation
Homebrew (Recommended)
Cargo
From Source
First Run
- Create a config file at
~/.config/hazelnut/config.toml:
# Watch your Downloads folder
[[]]
= "~/Downloads"
# Organize PDFs automatically
[[]]
= "Organize PDFs"
[]
= "pdf"
[]
= "move"
= "~/Documents/PDFs"
- Launch the TUI to manage and monitor:
- Or start the daemon to run in the background:
βοΈ Configuration
Hazelnut uses TOML for configuration. The default location is:
~/.config/hazelnut/config.toml
Full Configuration Example
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
# General Settings
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
[]
# Logging level: trace, debug, info, warn, error
= "info"
# Optional log file path
= "~/.local/share/hazelnut/hazelnut.log"
# Preview actions without executing (great for testing)
= false
# Wait time (seconds) before processing a file after change detected
= 2
# Theme for the TUI
= "catppuccin-mocha"
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
# Watch Folders
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
[[]]
= "~/Downloads"
= false
[[]]
= "~/Desktop"
= false
# Only apply specific rules to this folder
= ["screenshots", "temp-files"]
[[]]
= "~/Documents/Inbox"
= true # Watch subdirectories too
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
# Rules
# βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
[[]]
= "Organize PDFs"
= true
= false # Continue checking other rules
[]
= "pdf"
[]
= "move"
= "~/Documents/PDFs"
= true
= false
[[]]
= "Screenshots"
= true
[]
= "Screenshot*.png"
[]
= "move"
= "~/Pictures/Screenshots"
[[]]
= "Clean Old Downloads"
= true
[]
= 30
= ["tmp", "log", "bak"]
[]
= "trash"
See docs/configuration.md for the complete reference.
π Rules
Rules are the heart of Hazelnut. Each rule has a condition (what files to match) and an action (what to do with them).
Conditions
All conditions in a rule must match for the rule to apply.
File Name
[]
# Glob pattern matching
= "Screenshot*.png"
# Regex pattern matching
= "^invoice_\\d{4}\\.pdf$"
File Extension
[]
# Single extension
= "pdf"
# Multiple extensions (match any)
= ["jpg", "jpeg", "png", "gif", "webp"]
File Size
[]
# Size in bytes
= 10485760 # > 10 MB
= 1048576 # < 1 MB
File Age
[]
# Age in days (based on modification time)
= 30 # Older than 30 days
= 7 # Newer than 7 days
File Type
[]
= false # Match only files
= true # Match hidden files (starting with .)
Actions
Move
[]
= "move"
= "~/Documents/Archive"
= true # Create folder if missing
= false # Don't overwrite existing files
Copy
[]
= "copy"
= "~/Backup"
= true
= false
Rename
[]
= "rename"
= "{date}_{name}.{ext}"
Available variables:
| Variable | Description | Example |
|---|---|---|
{name} |
Filename without extension | document |
{filename} |
Full filename | document.pdf |
{ext} |
Extension | pdf |
{path} |
Full path | /home/user/document.pdf |
{dir} |
Parent directory | /home/user |
{date} |
Current date | 2024-01-15 |
{datetime} |
Current datetime | 2024-01-15_14-30-00 |
{date:FORMAT} |
Custom format | {date:%Y%m%d} β 20240115 |
Trash
[]
= "trash"
Moves files to the system trash (recoverable).
Delete
[]
= "delete"
β οΈ Warning: This permanently deletes files!
Run Command
[]
= "run"
= "convert"
= ["{path}", "-resize", "50%", "{dir}/{name}_small.{ext}"]
Archive
[]
= "archive"
= "~/Archives"
= false
Example Rules
[[]]
= "Screenshots to folder"
[]
= "Screenshot*.png"
[]
= "move"
= "~/Pictures/Screenshots"
[[]]
= "PDFs to Documents"
[]
= "pdf"
[]
= "move"
= "~/Documents/PDFs"
[[]]
= "Spreadsheets to Documents"
[]
= ["xlsx", "xls", "csv"]
[]
= "move"
= "~/Documents/Spreadsheets"
[[]]
= "Delete old temp files"
[]
= 30
= ["tmp", "log", "bak"]
[]
= "trash"
[[]]
= "Prefix invoices with date"
[]
= "^invoice.*\\.pdf$"
[]
= "rename"
= "{date:YYYY-MM-DD}_{filename}"
[[]]
= "Compress large images"
[]
= ["jpg", "png"]
= 5242880 # > 5 MB
[]
= "run"
= "convert"
= ["{path}", "-quality", "80", "{path}"]
β¨οΈ Keybindings
Global
| Key | Action |
|---|---|
Tab |
Next view |
Shift+Tab |
Previous view |
1 2 3 4 |
Jump to view (Dashboard, Rules, Watches, Log) |
s |
Open settings |
t |
Open theme picker |
A |
About Hazelnut |
? / F1 |
Show help |
q |
Quit (from Dashboard) |
Ctrl+c / Ctrl+q |
Force quit |
Navigation
| Key | Action |
|---|---|
β / k |
Move up |
β / j |
Move down |
g / Home |
Go to first item |
G / End |
Go to last item |
PageUp |
Page up |
PageDown |
Page down |
Rules View
| Key | Action |
|---|---|
Enter / Space |
Toggle rule enabled/disabled |
e |
Edit rule (coming soon) |
n |
New rule (coming soon) |
d / Delete |
Delete rule (coming soon) |
Watches View
| Key | Action |
|---|---|
a |
Add watch folder (coming soon) |
d / Delete |
Remove watch (coming soon) |
o / Enter |
Open folder |
Log View
| Key | Action |
|---|---|
c |
Clear log |
Theme Picker
| Key | Action |
|---|---|
β / k |
Previous theme (with live preview) |
β / j |
Next theme (with live preview) |
Enter |
Apply selected theme |
Esc |
Cancel |
π¨ Themes
Hazelnut includes 15 beautiful themes based on popular terminal and editor color schemes.
Press t in the TUI to open the theme picker with live preview.
Available Themes
| Theme | Description |
|---|---|
| π¦ Dracula | Dark purple aesthetic (default) |
| π One Dark Pro | Atom's iconic dark theme |
| βοΈ Nord | Arctic, bluish color palette |
| π± Catppuccin Mocha | Warm pastel dark theme |
| β Catppuccin Latte | Warm pastel light theme |
| πΈ Gruvbox Dark | Retro groove colors |
| π Gruvbox Light | Retro groove, light variant |
| π Tokyo Night | Futuristic dark blue |
| π Solarized Dark | Precision colors, dark |
| π Solarized Light | Precision colors, light |
| π¨ Monokai Pro | Classic syntax highlighting |
| πΉ RosΓ© Pine | All natural pine with soho vibes |
| π Kanagawa | Inspired by Katsushika Hokusai |
| π² Everforest | Comfortable green forest theme |
| π Cyberpunk | Neon-soaked futuristic theme |
ποΈ Architecture
Hazelnut consists of two binaries that work together:
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β User β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
βΌ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β hazelnut (TUI) β
β β’ Manage rules β
β β’ Monitor activity β
β β’ Change themes β
β β’ View logs β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
Unix Socket
β
βΌ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β hazelnutd (Daemon) β
β β’ Watch folders β
β β’ Evaluate rules β
β β’ Execute actions β
β β’ Run 24/7 in background β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
βΌ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β File System β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
hazelnut β The TUI
Interactive terminal interface for:
- Viewing and managing rules
- Monitoring watch folders
- Viewing activity logs
- Changing themes
- Sending commands to the daemon
hazelnutd β The Daemon
Background service that does the actual work:
π§ Building from Source
Requirements
- Rust 1.93+ (uses Edition 2024 features)
- Linux or macOS
Build
# Clone the repository
# Build release binary
# The binaries will be at:
# - target/release/hazelnut
# - target/release/hazelnutd
# Or install directly
Development
# Run TUI in development
# Run daemon in foreground
# Run with sample config
# Run tests
# Run linter
# Format code
π€ Contributing
Contributions are welcome! Please see CONTRIBUTING.md for guidelines.
Quick Start for Contributors
- Fork the repository
- Create a feature branch:
git checkout -b feature/amazing-feature - Make your changes
- Run tests:
cargo test - Run clippy:
cargo clippy - Format:
cargo fmt - Commit:
git commit -m "Add amazing feature" - Push:
git push origin feature/amazing-feature - Open a Pull Request
Project Structure
hazelnut/
βββ src/
β βββ main.rs # TUI entry point
β βββ daemon.rs # Daemon entry point
β βββ lib.rs # Library root
β βββ theme.rs # Color themes
β βββ app/ # TUI application
β β βββ events.rs # Key event handling
β β βββ state.rs # Application state
β β βββ ui.rs # UI rendering
β βββ config/ # Configuration loading
β βββ rules/ # Rule engine
β β βββ action.rs # Rule actions
β β βββ condition.rs # Rule conditions
β β βββ engine.rs # Rule evaluation
β βββ watcher/ # File system watcher
β βββ ipc/ # TUI-daemon communication
βββ docs/
β βββ configuration.md # Full config reference
βββ screenshots/ # Screenshots for docs
βββ tests/ # Integration tests
π License
This project is licensed under the MIT License β see the LICENSE file for details.