Usage Guide
Quick Start
Close Lightroom Classic, then run:
# macOS — auto-discovers catalog at ~/Pictures/Lightroom/
lrc-auto scan
# Windows — auto-discovers catalog at %USERPROFILE%\Pictures\Lightroom\
lrc-auto scan
# Or point at a specific catalog
lrc-auto -c "/path/to/Lightroom Catalog.lrcat" scan
The recommended workflow is always scan → plan → apply → validate.
Installation
Option 1 — Python (recommended for full feature set)
Or with pipx:
To include GPS-based location folders (macOS / Linux only):
Option 2 — Standalone binary (no Python required)
Download the pre-built binary from the GitHub Releases page:
| Platform | File |
|---|---|
| macOS (Apple Silicon + Intel) | lrc-auto-macos-universal2 |
| Windows x86-64 | lrc-auto-windows-x86_64.exe |
macOS:
chmod +x lrc-auto-macos-universal2
sudo mv lrc-auto-macos-universal2 /usr/local/bin/lrc-auto
lrc-auto --help
macOS Gatekeeper
On first run macOS may block the binary. Open System Settings → Privacy & Security and click Allow Anyway, or run:
Windows:
# Rename and place somewhere on your PATH (e.g. C:\Tools\)
Rename-Item lrc-auto-windows-x86_64.exe lrc-auto.exe
lrc-auto --help
Option 3 — Docker
# Scan a catalog mounted from the host
docker run --rm \
-v "/path/to/Lightroom:/catalog" \
ghcr.io/fjacquet/lrc-automation:latest \
scan -c /catalog/Catalog.lrcat
# Apply fixes (mount every volume root the catalog references)
docker run --rm \
-v "/Volumes/photo:/photo" \
-v "/path/to/Lightroom:/catalog" \
ghcr.io/fjacquet/lrc-automation:latest \
apply -c /catalog/Catalog.lrcat -y
Docker and disk moves
For apply to move files, the container needs read-write access to every volume root referenced in the catalog, not just the catalog directory.
Windows Notes
MAX_PATH advisory
Windows limits paths to 260 characters by default. If your catalog roots are deeply nested (NAS, external drive), enable long paths first:
Group Policy Editor:
- Open
gpedit.msc - Navigate to: Computer Configuration > Administrative Templates > System > Filesystem
- Enable "Enable Win32 long paths"
PowerShell (run as Administrator):
New-ItemProperty -Path "HKLM:\SYSTEM\CurrentControlSet\Control\FileSystem" `
-Name "LongPathsEnabled" -Value 1 -PropertyType DWORD -Force
.env file on Windows
Both forward slashes and escaped backslashes work:
# Forward slashes (recommended — works on all platforms)
LRC_CATALOG_PATH=C:/Users/YourName/Pictures/Lightroom/Catalog.lrcat
LRC_BACKUP_DIR=C:/Users/YourName/Documents/LightroomBackups
# Backslashes also work
LRC_CATALOG_PATH=C:\\Users\\YourName\\Pictures\\Lightroom\\Catalog.lrcat
Known limitations on Windows
- Location folders (
--location-folders): The[geo]extra has no Windows wheel. GPS-basedCountry/City/subfolders are macOS / Linux only. - AppleDouble (
._*) cleanup: Silently skipped on Windows — those files only appear on macOS-formatted volumes.
Configuration
Copy .env.example to .env and edit:
LRC_CATALOG_PATH=/path/to/Lightroom Catalog.lrcat
LRC_BACKUP_DIR= # optional — defaults to catalog directory
LRC_TARGET_LAYOUT=%Y/%m/ # optional — strftime format for target folders
LRC_LOCATION_FOLDERS=false # optional — enable GPS-based Country/City subfolders
LRC_LOG_FILE= # optional — defaults to <catalog>.log alongside catalog
All variables can also be passed as CLI flags; flags take precedence over env vars.
Target folder layout
Controls the target folder structure using Python strftime codes. Defaults to %Y/%m/.
| Layout | Example | Description |
|---|---|---|
%Y/%m/ |
2023/06/ |
Year/Month (default) |
%Y/%m/%d/ |
2023/06/15/ |
Year/Month/Day |
%Y-%m/ |
2023-06/ |
Year-Month with dash |
%Y/ |
2023/ |
Flat yearly |
Log file
A debug-level log is written alongside the catalog as <catalog>.log by default. The console shows only warnings unless -v is set.
# Override the log path
lrc-auto --log-file /tmp/lrc-debug.log -c catalog.lrcat apply
# Also print debug to the terminal
lrc-auto -v --log-file /tmp/lrc-debug.log apply
Commands
scan (read-only)
Detects misplaced photos (EXIF date does not match folder date) and duplicate / malformed filename prefixes.
lrc-auto scan
lrc-auto -c "/path/to/catalog.lrcat" scan
lrc-auto --location-folders scan # show GPS-aware target paths
# Export results
lrc-auto scan -o results.json
lrc-auto scan -o results.csv
plan (read-only)
Generates a move plan from scan results. Prints a table of all proposed changes and optionally exports it for review before touching anything.
lrc-auto plan
lrc-auto plan --fix moves # moves only
lrc-auto plan --fix renames # prefix renames only
lrc-auto plan -o plan.json # export as JSON
apply (modifies catalog + disk)
Executes the plan: moves files on disk and updates the catalog in a single atomic transaction. Always creates a timestamped backup first.
lrc-auto apply # prompts for confirmation
lrc-auto apply -y # skip confirmation prompt
lrc-auto apply --fix moves
lrc-auto apply --fix renames
On any error all disk moves are reversed automatically (rollback stack).
validate
Runs PRAGMA integrity_check, checks every catalog record against disk, and reports missing / misplaced files.
lrc-auto validate
# Export audit results
lrc-auto validate -o audit.json
lrc-auto validate -o audit.csv
cleanup
Removes empty directories left behind by apply runs and deletes macOS AppleDouble (._*) metadata files. Safe to run at any time — never touches photo files.
What it does, in order:
- Walks every catalog root bottom-up
- On macOS: deletes
._*files before attemptingrmdir - Removes now-empty directories from disk
- Removes orphaned
AgLibraryFolderrows from the catalog
reconcile
Runs a full disk audit, then fixes catalog pointers for files that exist on disk but are registered at the wrong path. No files are moved — only catalog metadata is updated.
Useful after a partial apply run or an out-of-band file move left catalog pointers stale. Ambiguous matches (same filename found in multiple locations) are skipped and printed for manual resolution.
Output reports: reconciled count, skipped-ambiguous count, truly-missing count.
restore
Rolls back the catalog from a timestamped backup created by apply or reconcile.
Advanced: location-based subfolders
Requires the [geo] extra (macOS / Linux only):
When enabled, photos with GPS data land in subfolders like 2023/06/CH/Zurich/ instead of 2023/06/. Photos without GPS fall back to the date-only path.
Control the ordering of month and location within the path:
--location-order |
Example path |
|---|---|
month_cc_city (default) |
2023/06/CH/Zurich/ |
cc_city_month |
CH/Zurich/2023/06/ |
cc_month_city |
CH/2023/06/Zurich/ |
Lookups are performed offline using the reverse_geocoder K-D tree — no network calls. Country codes follow ISO 3166-1 alpha-2 (CH, FR, NZ, …).
Supported folder structures
The scanner reads dates from the full path (root + pathFromRoot) right-to-left, so the deepest recognisable date segment wins.
| Pattern | Example | Notes |
|---|---|---|
YYYY/MM/ |
2023/06/ |
Classic Lightroom hierarchy |
YYYY-MM-DD |
2023-12-24/ |
ISO date folders — day ignored, year+month extracted |
| French dates | 1 avril 2016/ |
Apple Photos / iPhoto exports; accented forms (février, août, décembre) and case-insensitive |
| Year in root + month | Root /photos/2021/, path 06/ |
Year from root, month from immediate subfolder |
Filtered out automatically:
- 1904 — Lightroom's "no date" epoch value
- Topical folders — no recognisable date pattern (e.g.
Vacances/,Family/) — silently skipped - Years outside 1900–2100