# file-organizer

[![CI](https://github.com/thedog737/file-organizer/workflows/CI/badge.svg)](https://github.com/thedog737/file-organizer/actions)
[![Python](https://img.shields.io/pypi/pyversions/file-organizer.svg)](https://pypi.org/project/file-organizer/)
[![License: Non-Commercial](https://img.shields.io/badge/License-Non--Commercial-red.svg)](LICENSE)

A smart CLI tool to organize messy directories (Downloads, Desktop, etc.) by file type, date, or size — with safety features like dry-run, undo, and configurable ignore patterns.

## Features

- **Organize by type** — Images, Documents, Videos, Audio, Archives, Code, Executables, Spreadsheets, Presentations, Fonts, Data
- **Organize by date** — Group files by modification date (year-month or year-month-day)
- **Organize by size** — Small / Medium / Large buckets (configurable thresholds)
- **Safety first** — Dry-run by default, explicit `--apply` to execute, `--undo` to revert
- **Configurable** — YAML config with custom ignore patterns, size limits, date formats
- **Cross-platform** — Works on Windows, macOS, Linux
- **Rich output** — Beautiful tables and progress with `rich`
- **Recursive mode** — Organize nested subdirectories with `--recursive`
- **Progress bar** — Visual progress during file moves
- **Category summary** — File count & size per category in dry-run
- **Export plan** — Save organization plan to JSON for review/scripting

## Installation

### pipx (recommended)
```bash
pipx install file-organizer
```

### pip
```bash
pip install file-organizer
```

### From source
```bash
git clone https://github.com/OWNER/file-organizer.git
cd file-organizer
pip install -e .
```

## Quick Start

```bash
# Preview what would happen (dry-run)
file-organizer organize ~/Downloads --by type

# Actually organize by file type
file-organizer organize ~/Downloads --by type --apply

# Organize by date (year-month folders)
file-organizer organize ~/Downloads --by date --apply

# Organize by size
file-organizer organize ~/Downloads --by size --apply

# Organize recursively (includes subdirectories)
file-organizer organize ~/Downloads --by type --recursive --apply

# Export plan to JSON for review
file-organizer organize ~/Downloads --by type --export-plan plan.json --dry-run

# Skip confirmation prompt
file-organizer organize ~/Downloads --by type --apply -y

# Undo last operation
file-organizer undo
```

## Commands

### `organize`
Organize files in a directory.

```bash
file-organizer organize [PATH] [OPTIONS]

Options:
  --by, -b              Organization mode: type, date, size (default: type)
  --apply, -a           Actually move files (default: dry-run)
  --dry-run             Show what would be done without changes
  --yes, -y             Skip confirmation prompt
  --recursive, -r       Organize files in subdirectories recursively
  --export-plan FILE    Export organization plan to JSON file
```

### `undo`
Revert the last organization operation.

```bash
file-organizer undo
```

### `config`
Manage configuration.

```bash
file-organizer config [OPTIONS]

Options:
  --show, -s        Show current configuration
  --set KEY=VALUE   Set a configuration value
  --reset           Reset to default configuration
```

### `ignore`
Manage ignore patterns.

```bash
file-organizer ignore [OPTIONS]

Options:
  --add, -a PATTERN     Add ignore pattern
  --remove, -r PATTERN  Remove ignore pattern
  --list, -l            List ignore patterns
```

## Configuration

Configuration file: `~/.config/file-organizer/config.yaml` (Linux/macOS) or `%APPDATA%\file-organizer\config.yaml` (Windows)

```yaml
organize:
  default_mode: type          # type, date, or size
  date_format: "%Y-%m"        # strftime format for date mode
  size_thresholds:            # MB thresholds for size mode
    small_mb: 1
    large_mb: 100
  create_subdirs: true        # Create category subdirectories

ignore:
  patterns:                   # Glob patterns to ignore
    - "*.tmp"
    - "*.crdownload"
    - "*.part"
    - ".DS_Store"
    - "Thumbs.db"
  hidden_files: true          # Ignore hidden files
  system_files: true          # Ignore system files

safety:
  dry_run_by_default: true    # Default to dry-run
  require_confirmation: false # Ask before applying
  max_file_size_mb: 1000      # Skip files larger than this
  preserve_timestamps: true   # Preserve file timestamps

advanced:
  follow_symlinks: false      # Follow symbolic links
  ignore_errors: false        # Continue on errors
  log_level: INFO             # Logging level
```

### Examples

Set default mode to date:
```bash
file-organizer config --set organize.default_mode=date
```

Add custom ignore pattern:
```bash
file-organizer ignore --add "*.bak"
```

## How It Works

1. **Scan** — Reads all files in the target directory (optionally recursive with `--recursive`)
2. **Filter** — Applies ignore patterns (hidden, system, custom)
3. **Categorize** — Determines destination folder based on mode
4. **Plan** — Creates a move plan with conflict resolution, shows category summary
5. **Execute** — Moves files (only with `--apply`), shows progress bar
6. **Log** — Saves undo log for reversal

## Undo

The last organization is logged to `~/.config/file-organizer/undo_log.json`. Run `file-organizer undo` to move all files back to their original locations.

## Development

```bash
# Clone and setup
git clone https://github.com/OWNER/file-organizer.git
cd file-organizer
pip install -e ".[dev]"

# Run tests
pytest -v

# Lint
ruff check .

# Type check
mypy src/file_organizer
```

## License

Non-Commercial License — see [LICENSE](LICENSE) for details.

This software is free for non-commercial use only. Commercial use requires a separate license.
Attribution to Blake Nary (thedog737) is required for all uses.

## Contributing

1. Fork the repository
2. Create a feature branch
3. Make your changes
4. Run tests and linting
5. Submit a pull request

---

**Made with ❤️ using Python, Typer, and Rich**