Mode d’emploi
- Copiez la commande et examinez le paquet avant de l’installer dans votre environnement agent.
- Consultez le document original pour les outils, identifiants et environnements requis.
- Décrivez les entrées et le livrable souhaité ; comparez la sortie aux sources.
npx skills add https://github.com/moonlight-lupin/agent-skills --skill file-organizerAvant de commencer
- L’installation n’inclut ni abonnement au modèle, ni quota API, ni accès aux fichiers.
- Étoiles et installations reflètent l’activité, pas un test indépendant de qualité ou de sécurité.
Rendu depuis le dépôt source en conservant titres, exemples, code, tableaux, liens et images.
File Organizer
An LLM-powered file organizer that reads file contents, proposes a sensible folder structure with renamed files, and executes moves in chunks — with a mandatory user confirmation gate before any filesystem changes.
Overview
Inspired by LlamaFS but designed for Hermes: the script handles filesystem I/O (scan, read snippets, execute moves). The agent's own LLM does the reasoning by default. An optional propose subcommand can call a cheaper external LLM (deepseek, openrouter, ollama) for cost-conscious runs on large directories. Uses stdlib-only HTTP (urllib) — no requests/openai SDK needed.
When to Use
- User says "organize my Downloads" / "tidy my Desktop" / "clean up this folder"
- User has a messy directory and wants files sorted into categories
- User wants files renamed based on their content (not just moved)
- User wants to organize files on a local disk, network mount, or remote filesystem
Don't use for:
- Bulk file deletion (this skill only moves and renames, never deletes)
- Deduplication (use a dedicated dedup tool)
- File content search (use
search_filesinstead)
Workflow
Step 1 — Scan
Run the scan script to get file metadata + content snippets:
python3 scripts/organize.py scan --path <directory> [--depth N] [--max-snippet-chars 500]Output is a JSON array. Each file entry contains:
path: full file pathrelative_path: path relative to scanned directoryname: current filenamesize: bytesmtime: ISO timestamptype: text, image, audio, pdf, office, archive, othermime: detected MIME typesnippet: first N chars of content (text/pdf) or metadata (image/audio)
Flags: --depth N (max directory depth), --max-snippet-chars N (per-file snippet limit, default 500), --include-hidden (include dotfiles, skipped by default).
Step 2 — Propose Organization (Agent LLM — Default)
Using the scan output, reason about:
- Natural categories based on file content and types
- A clean folder hierarchy (not too deep — 2-3 levels max)
- Descriptive filenames that reflect content (not
IMG_3847.jpg→Hawaii-Beach-Sunset.jpg) - Time-based grouping when appropriate (e.g.,
2024-Taxes/,2023-Receipts/)
Build a plan JSON:
{
"source_dir": "<scanned dir>",
"moves": [
{"source": "<full path>", "destination": "<full path>"}
],
"folders_to_create": ["<full path>", ...]
}Cost-saving offer: When presenting the plan (Step 3), mention to the user:
"This used the agent's own model. For larger directories, I can run the reasoning through a cheaper LLM to save costs. Available options:" | Provider | Model | Cost | Notes | |----------|-------|------|-------| | deepseek | deepseek-chat | ~$0.14/M in, $0.28/M out | Cheapest cloud | | openrouter | deepseek/deepseek-chat | pay-as-you-go | Multi-model routing | | ollama | llama3.2:3b | Free (local CPU) | Slow but zero cost | Just say "use deepseek" or "use ollama" and I'll re-run via the cheaper model.
Only offer this if the scan had 20+ files (not worth it for tiny directories).
Using a cheaper model (opt-in): If the user requests a cheaper model, or if the directory is very large (100+ files), use the propose subcommand instead:
python3 scripts/organize.py propose --scan /tmp/scan.json --source-dir <dir> \
--provider deepseek [--model <model-id>]Provider priority: --provider flag > DEEPSEEK_API_KEY env > OPENAI_API_KEY env
OPENROUTER_API_KEYenv >OLLAMA_HOSTenv > error
If propose fails (network, auth, parse), fall back to agent reasoning manually.
Step 3 — Present Plan to User (MANDATORY GATE)
This step is non-negotiable. Present the plan as a formatted table:
| # | Current Name | → | New Location | Type | Snippet Preview |
|---|
Ask the user to:
- Confirm the plan as-is
- Adjust specific moves (rename, re-categorize, skip)
- Cancel entirely
Never proceed to execution without explicit user confirmation.
Step 4 — Execute in Chunks
After user confirms, write the plan to a temp file and execute:
python3 scripts/organize.py execute --plan /tmp/plan.json --chunk-size 10The script:
- Creates destination folders first
- Moves files in chunks of 10 (configurable)
- Prints progress after each chunk:
[chunk 2/5] moved 10, failed 0 - Skips conflicts (destination exists) — never overwrites
- Logs per-file errors without aborting the batch
Step 5 — Report Results
Present the final summary to the user:
- Files moved successfully
- Files skipped (conflicts)
- Files failed (errors)
- Suggest next steps (e.g., "want me to organize another directory?")
Cross-Filesystem Support
The organizer works on any path accessible from the host:
| Target | Path Format | Notes |
|---|---|---|
| Local disk | Any local path | Direct filesystem access |
| Network mount | NFS, SMB/CIFS, SSHFS mounts | Use smaller chunk sizes for latency |
| Remote filesystem | Any path Python shutil.move can handle | SSHFS, FUSE, etc. |
Key Guardrails
- Never delete — only move and rename. If the user wants deletions, that's a
separate task with its own confirmation flow.
- Never overwrite — if a destination file exists, skip and log.
- Always gate — present plan to user before executing. No silent moves.
- Chunk execution — process in batches of 10 to manage failures gracefully.
- Agent LLM by default, cheap LLM opt-in —
scanandexecuteare pure
filesystem I/O. The agent's own LLM does the reasoning by default. The propose subcommand is an opt-in for cheaper external models on large directories.
Common Pitfalls
- Huge directories — scanning 10,000+ files will produce massive output. Use
--depth 1 first to survey, then drill into subdirectories. Or scan by file type subsets.
- Binary files with no snippet — images, audio, office docs get metadata only.
The LLM must infer categories from filename, size, and mtime.
- Paths with spaces — always quote paths in the plan JSON. The script handles
this correctly via Python pathlib.
- Network filesystem latency — organizing files on SSHFS/NFS/SMB mounts is
slower due to network round-trips. Use smaller chunk sizes (5) for remote targets.
- Permission errors — some files may not be readable. The scan script handles
this gracefully (returns metadata with snippet: null).
Verification Checklist
- [ ] Scan completed and returned JSON output
- [ ] Plan includes
source_dir,moves, andfolders_to_create - [ ] Plan presented to user as a table with clear before → after mapping
- [ ] User explicitly confirmed the plan
- [ ] Plan written to temp JSON file
- [ ] Execution completed with chunked progress output
- [ ] Final summary reported (moved / failed / skipped counts)
- [ ] No files were deleted or overwritten
One-Shot Recipes
Organize Downloads folder
# 1. Scan
python3 scripts/organize.py scan --path ~/Downloads --depth 2 > /tmp/scan.json
# 2. Agent reasons over scan JSON, builds plan (default — uses agent's own LLM)
# OR for large directories, use cheap LLM:
# python3 scripts/organize.py propose --scan /tmp/scan.json --source-dir ~/Downloads --provider deepseek > /tmp/plan.json
# 3. Agent presents plan to user (with cost-saving offer if 20+ files)
# 4. After confirmation:
python3 scripts/organize.py execute --plan /tmp/plan.json --chunk-size 10Organize a network-mounted directory
# 1. Scan
python3 scripts/organize.py scan --path /mnt/remote/Desktop --depth 2 > /tmp/scan.json
# 2. Agent reasons over scan JSON, builds plan (default)
# OR: python3 scripts/organize.py propose --scan /tmp/scan.json --source-dir /mnt/remote/Desktop --provider deepseek > /tmp/plan.json
# 3. Agent presents plan to user
# 4. After confirmation (smaller chunks for network latency):
python3 scripts/organize.py execute --plan /tmp/plan.json --chunk-size 5Dry run (preview only)
python3 scripts/organize.py execute --plan /tmp/plan.json --dry-runCheap LLM (opt-in for large directories)
# Scan → Propose via deepseek → Execute
python3 scripts/organize.py scan --path ~/Downloads > /tmp/scan.json
python3 scripts/organize.py propose --scan /tmp/scan.json --source-dir ~/Downloads --provider deepseek > /tmp/plan.json
# Agent reviews plan, presents to user, then:
python3 scripts/organize.py execute --plan /tmp/plan.json --chunk-size 10Run self-tests
python3 scripts/organize.py --self-testScript Reference
| Command | Purpose |
|---|---|
scan --path <dir> [--depth N] [--max-snippet-chars N] [--include-hidden] | Scan directory, output JSON with file metadata + snippets |
propose --scan <json> --source-dir <dir> [--provider <p>] [--model <m>] | Opt-in: call a cheap external LLM to generate plan JSON |
execute --plan <json> [--chunk-size N] [--dry-run] | Execute move plan in chunks, print progress per chunk |
--self-test | Run built-in test suite (19 tests, self-contained in tempdir) |
Optional Python deps (degrade gracefully if missing):
Pillow— image dimensions and EXIF datesmutagen— audio duration and ID3 tagsPyMuPDF(fitz) — PDF first-page text extraction


