fso (File System Organizer) - A CLI tool that automatically organizes files into categorized folders
Project description
fso
fso (File System Organizer) - A cross-platform CLI tool that automatically organizes files into categorized folders based on their extensions.
Features
- Clean: Instantly organize files in any directory into categorized subfolders
- Watch: Monitor a directory and automatically organize new files as they appear
- Undo: Revert organization operations (single, multiple, or all)
- Dedup: Find and handle duplicate files using content hashing
- Conflict Handling: Choose how to handle filename collisions (skip, overwrite, rename)
- Dry Run: Preview what would happen without actually moving files
- Customizable: Define your own rules via a simple YAML configuration
- Cross-Platform: Works on Windows, macOS, and Linux
How It Works
Click to see the data flow diagram
flowchart TD
A[User runs fso clean PATH] --> B[Load config.yaml]
B --> C[Scan directory for files]
C --> D{For each file}
D --> E[Match extension to rule]
E --> F{Destination exists?}
F -->|No| G[Create folder]
F -->|Yes| H{File name collision?}
G --> H
H -->|Yes| I[Rename: file_1.ext]
H -->|No| J[Move file]
I --> J
J --> K[Log to history.json]
K --> L[Update Rich progress]
L --> D
D -->|Done| M[Print summary table]
Installation
From PyPI (Recommended)
pip install fso-cli
From Source
# Clone the repository
git clone https://github.com/mitacheto/fso.git
cd fso
# Create a virtual environment (recommended)
python -m venv venv
# Activate the virtual environment
# Windows (PowerShell)
.\venv\Scripts\Activate.ps1
# Windows (CMD)
.\venv\Scripts\activate.bat
# macOS/Linux
source venv/bin/activate
# Install in development mode
pip install -e .
Usage
Clean Command
Organize files in a directory:
# Organize your Downloads folder
fso clean ~/Downloads
# Preview what would happen (dry run)
fso clean ~/Downloads --dry-run
# Use a custom config file
fso clean ~/Downloads --config ./my-config.yaml
# Show detailed output
fso clean ~/Downloads --verbose
# Silent mode (errors only)
fso clean ~/Downloads --quiet
# Handle filename conflicts (skip, overwrite, or rename)
fso clean ~/Downloads --on-conflict skip
fso clean ~/Downloads --on-conflict overwrite
fso clean ~/Downloads --on-conflict rename # default
Example Output:
Organizing files... ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 100% photo.jpg
Moved Files Summary
┏━━━━━━━━━━━┳━━━━━━━┓
┃ Folder ┃ Files ┃
┡━━━━━━━━━━━╇━━━━━━━┩
│ Archives │ 2 │
│ Documents │ 5 │
│ Images │ 12 │
├───────────┼───────┤
│ Total │ 19 │
└───────────┴───────┘
Created 3 new folder(s)
Watch Command
Monitor a directory and organize files as they appear:
# Watch your Downloads folder
fso watch ~/Downloads
# Custom delay before organizing (for large downloads)
fso watch ~/Downloads --delay 3.0
# Use custom config
fso watch ~/Downloads --config ./my-config.yaml
Press Ctrl+C to stop watching.
Example Output:
Watching: C:\Users\you\Downloads
Delay: 1.0s | Press Ctrl+C to stop
-> vacation-photo.jpg moved to Images/
-> quarterly-report.pdf moved to Documents/
-> project-backup.zip moved to Archives/
Undo Command
Revert organization operations:
# Undo the last operation
fso undo
# View undo history
fso undo --list
# Undo the last 3 operations
fso undo --count 3
# Undo all operations
fso undo --all
Example Output:
Undoing operation from 2024-01-15T10:30:45
Target directory: C:\Users\you\Downloads
Files to restore: 19
Proceed with undo? [y/n]: y
✓ Restored 19 file(s)
✓ Removed 3 empty folder(s)
Dedup Command
Find and handle duplicate files:
# Find duplicates (report only)
fso dedup ~/Downloads
# Move duplicates to a Duplicates folder
fso dedup ~/Downloads --action move
# Delete duplicates (keeps oldest file)
fso dedup ~/Downloads --action delete
# Interactive mode - prompt for each group
fso dedup ~/Downloads --action delete --interactive
# Preview without making changes
fso dedup ~/Downloads --action delete --dry-run
Example Output:
Scanning for duplicates in: ~/Downloads
Duplicate Files Found
+--------------------------------------------+
| # | Size | Duplicates | Wasted | Files |
|---+--------+------------+---------+--------|
| 1 | 2.5 MB | 2 | 5.0 MB | photo.jpg |
| | | | | photo_copy.jpg |
| | | | | photo_backup.jpg |
+--------------------------------------------+
Summary:
Files scanned: 150
Duplicate groups: 1
Total duplicates: 2
Wasted space: 5.0 MB
Config Command
View configuration information:
# Show user config file location
fso config
# Show current configuration
fso config --show
# Show config file path with status
fso config --path
Configuration
fso uses a YAML configuration file. The default configuration organizes files into these categories:
rules:
Images: [jpg, jpeg, png, gif, svg, webp, ico, bmp, tiff, raw, heic]
Documents: [pdf, doc, docx, txt, rtf, odt, xlsx, xls, pptx, ppt, csv, epub]
Archives: [zip, tar, rar, gz, 7z, bz2, xz, iso]
Videos: [mp4, mkv, avi, mov, wmv, flv, webm, m4v, mpeg, mpg]
Audio: [mp3, wav, flac, aac, ogg, m4a, wma, opus, aiff]
Code: [py, js, ts, html, css, json, xml, yaml, yml, md, sh, bat, ps1]
Executables: [exe, msi, dmg, deb, rpm, appimage, apk]
default_folder: Misc
# How to handle filename conflicts: skip | overwrite | rename
conflict_strategy: rename
exclude_patterns:
- "*.tmp"
- "*.part"
- "*.crdownload"
- "*.download"
- "desktop.ini"
- "Thumbs.db"
- ".DS_Store"
Config File Locations
The user config file is stored in a platform-specific location:
| Platform | Location |
|---|---|
| Windows | %LOCALAPPDATA%\fso\config.yaml |
| macOS | ~/Library/Application Support/fso/config.yaml |
| Linux | ~/.config/fso/config.yaml |
To customize, copy the default config.yaml to your user config location.
Safety Features
- No Overwrites: If a file with the same name exists in the destination, the new file is automatically renamed (e.g.,
photo.jpg->photo_1.jpg) - Undo Support: Every operation is logged, allowing you to revert changes
- Dry Run Mode: Preview changes before executing
- Hidden Files Ignored: Files starting with
.are never moved - Exclude Patterns: Skip temporary files, partial downloads, and system files
Roadmap
fso is actively being developed! Here's what's coming:
| Phase | Focus | Key Features | Status |
|---|---|---|---|
| Phase 1 | Safety & Performance | Faster scanning, batch undo, conflict handling, dedup | Done |
| Phase 2 | Smart Sorting | Photo/music metadata sorting, date-based templates | Planned |
| Phase 3 | Automation | Background service, scheduled runs, plugin system | Planned |
| Phase 4 | AI-Powered | Local AI classification, smart file renaming | Planned |
Upcoming highlights:
- Photo sorting by date taken - Uses EXIF data, not file dates
- Music sorting by artist/album - Reads ID3 tags
- AI document classification - Local LLMs, 100% private
- Run as background service - Auto-organize on system startup
See the full ROADMAP.md for details and status.
Development
Running Tests
# Install dev dependencies
pip install -e ".[dev]"
# Run tests
pytest
# Run tests with coverage
pytest --cov=fso
Project Structure
fso/
├── fso/
│ ├── __init__.py # Package version
│ ├── main.py # CLI commands (Typer)
│ ├── core.py # File organization logic
│ ├── config.py # Configuration loading
│ ├── observers.py # File watching (Watchdog)
│ └── utils.py # History tracking, helpers
├── tests/
│ ├── test_config.py
│ └── test_core.py
├── config.yaml # Default configuration
├── pyproject.toml # Package configuration
└── README.md
License
MIT License - see LICENSE file for details.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file fso_cli-1.1.0.tar.gz.
File metadata
- Download URL: fso_cli-1.1.0.tar.gz
- Upload date:
- Size: 30.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.0
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d6ce2742600e9e8e8ac76dd920a5b22675ba5882181433cdbdd52c5c565b04aa
|
|
| MD5 |
2600f5e0f07e50a9079f01a7534459cb
|
|
| BLAKE2b-256 |
fe129d37f9c12e4838719b340cc6780597f4cd2184943afc07a0bd5d93e0a538
|
File details
Details for the file fso_cli-1.1.0-py3-none-any.whl.
File metadata
- Download URL: fso_cli-1.1.0-py3-none-any.whl
- Upload date:
- Size: 24.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.0
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
23c56ed3c85ba13ba4deec841cffbc585a46d9e5d2e2062a8f2779407337116c
|
|
| MD5 |
cb67fb03b6e5289daead776cffa6d567
|
|
| BLAKE2b-256 |
7fdaf76d9cfb78eb490a2f5536c8473fdf00437b781dd9222f7950145823666a
|