{"id":27309150,"url":"https://github.com/fruffy/sort_pictures","last_synced_at":"2025-04-12T05:07:12.329Z","repository":{"id":286485686,"uuid":"961547434","full_name":"fruffy/sort_pictures","owner":"fruffy","description":"Little Python script to correctly tag and sort pictures.","archived":false,"fork":false,"pushed_at":"2025-04-06T18:31:38.000Z","size":5,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-04-06T19:32:25.801Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/fruffy.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2025-04-06T18:29:58.000Z","updated_at":"2025-04-06T18:31:42.000Z","dependencies_parsed_at":"2025-04-06T19:42:29.149Z","dependency_job_id":null,"html_url":"https://github.com/fruffy/sort_pictures","commit_stats":null,"previous_names":["fruffy/sort_pictures"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fruffy%2Fsort_pictures","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fruffy%2Fsort_pictures/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fruffy%2Fsort_pictures/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fruffy%2Fsort_pictures/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/fruffy","download_url":"https://codeload.github.com/fruffy/sort_pictures/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248519541,"owners_count":21117761,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2025-04-12T05:07:11.629Z","updated_at":"2025-04-12T05:07:12.287Z","avatar_url":"https://github.com/fruffy.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Python Script for Media File Organization\n\n## Description\n\nThis Python script sorts image and video files based on creation date, renames dated files according to a specified format, and organizes them into a structured output directory. It includes features for handling duplicates, identifying potentially unwanted files, managing metadata, and ensuring data safety through backups and dry runs.\n\n## Features\n\n* **Automatic Backup:** Creates a timestamped copy of the source directory within the target directory before processing begins.\n* **Recursive Processing:** Scans the source directory and its subdirectories for media files.\n* **Date Extraction:** Determines file date using the following priority:\n    1.  Image EXIF metadata (`DateTimeOriginal`).\n    2.  Video file metadata (`creation_date`, etc., using `hachoir`).\n    3.  Filename pattern (`YYYYMMDD_HHMMSS`).\n* **Configurable Output Structure:** Organizes dated files into subdirectories based on the `--structure` option:\n    * `Y`: Year (`YYYY/`) (Default)\n    * `YM`: Year and Month (`YYYY/MM/`)\n    * `YMD`: Year, Month, and Day (`YYYY/MM/DD/`)\n* **Configurable File Renaming:** Renames dated files using a Python `strftime`-compatible format provided via `--filename-format` (Default: `%Y-%m-%d_%H%M%S`).\n* **Video File Support:** Processes common video formats and attempts to extract creation dates.\n* **EXIF Data Update:** Attempts to write the creation date to image EXIF metadata if the date was determined from the filename and was previously missing.\n* **Exact Duplicate Handling:** Skips processing files identified as having identical content (SHA256 hash) to a previously processed file.\n* **Near-Duplicate Image Detection:** Identifies visually similar images using perceptual hashing (`imagehash`). Configurable action (`--near-duplicates-action`):\n    * `ignore`: No action (Default).\n    * `log`: Records sets of similar image paths in the log file.\n    * `move`: Moves sets of similar images to subfolders within a `_near_duplicates` review directory.\n* **Low-Quality Image Detection:** Identifies images below specified file size (`--min-filesize`) or dimension (`--min-dimension`) thresholds. Configurable action (`--low-quality-action`):\n    * `ignore`: No action (Default).\n    * `log`: Records paths of flagged images in the log file.\n    * `move`: Moves flagged images to a `_low_quality` review directory.\n* **Unknown Date Handling:** Moves files without a determinable date to an `unknown_date` subdirectory, preserving original filenames.\n* **Dry Run Mode:** The `--dry-run` option simulates all actions (copying, moving, renaming, EXIF writing) without making changes, logging the intended operations instead.\n* **Logging:** Records detailed operational information, warnings, and errors to the console and optionally to a specified log file (`--log-file`, `--log-level`).\n* **Progress Indication:** Displays a progress bar (`tqdm`) during the file processing stage for larger sets of files.\n\n## Warning: File Operations\n\n**Operation:** This script **MOVES** files from the source directory to the target directory after the initial backup step. It also **MODIFIES** image EXIF data in the source directory before moving if adding a date derived from the filename.\n\n**Backup Recommendation:** The script attempts an automatic backup of the source directory before processing. However, **it is strongly recommended to have an independent, verified backup of your source directory before execution**, as the primary function involves moving and potentially modifying original files. Use the `--dry-run` option to review planned actions before execution.\n\n## Requirements\n\n* Python 3.10 or newer\n* Required Python libraries:\n    * `Pillow`\n    * `piexif`\n    * `tqdm`\n    * `hachoir`\n    * `ImageHash`\n\n## Installation\n\n1.  Confirm Python 3.10+ is installed and accessible.\n2.  Install the necessary libraries using pip:\n\n    ```bash\n    pip install Pillow piexif tqdm hachoir ImageHash\n    ```\n    Alternatively, use a virtual environment manager like `uv`:\n    ```bash\n    uv pip install Pillow piexif tqdm hachoir ImageHash\n    ```\n\n## Usage\n\nExecute the script from the command line.\n\n**Syntax:**\n\n```bash\nsort_pictures.py --source \u003cSOURCE_PATH\u003e --target \u003cTARGET_PATH\u003e [OPTIONS]\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffruffy%2Fsort_pictures","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ffruffy%2Fsort_pictures","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffruffy%2Fsort_pictures/lists"}