Skip to content

Instantly share code, notes, and snippets.

@jwmann
Last active March 16, 2024 22:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jwmann/bde6db8b31d9d9048a01e980f93a3073 to your computer and use it in GitHub Desktop.
Save jwmann/bde6db8b31d9d9048a01e980f93a3073 to your computer and use it in GitHub Desktop.
Use exiftool to recursively sort my images into a pre-defined folder structure. Source this file and call sortMedia
#! /bin/bash
sortMedia() {
EXIFTOOL=/opt/homebrew/bin/exiftool
DEFAULT_SOURCE_DIR_PATH="./" # Current Directory
DEFAULT_DESTINATION_DIR_PATH="/Volumes/home/Photos/" # NAS Photos
EXIFDATETAG="${3:-CreateDate}"
PREFIX="${4:-jwm}"
SORT_FILETYPE="${5:-true}"
ALLOW_DUPS="${6:-true}"
CLEAN_SRC_DIR="${7:-false}"
echo "Filename prefix set to: $PREFIX"
echo "Sorting by FileType set to: $SORT_FILETYPE"
if [ ! -e "$EXIFTOOL" ]
then
echo "Error: exiftool binary missing..."
echo "Please install exiftool: brew install exiftool"
return 255
fi
_src="${1:-$DEFAULT_SOURCE_DIR_PATH}"
SOURCE_DIR_PATH=$(cd $_src 2> /dev/null && pwd -P)
if [ -d "$SOURCE_DIR_PATH" ]
then
echo "Sorting through directory: $SOURCE_DIR_PATH"
else
echo "ERROR: Source directory is not a valid directory"
return 255
fi
_dest="${2:-$DEFAULT_DESTINATION_DIR_PATH}"
DESTINATION_DIR_PATH=$(cd $_dest 2> /dev/null && pwd -P)
if [ -d "$DESTINATION_DIR_PATH" ]
then
echo "Moving to destination: $DESTINATION_DIR_PATH"
else
echo "ERROR: Destination directory is not a valid directory"
return 255
fi
run_exiftool() {
_format="$DESTINATION_DIR_PATH"
_format+="\${$1#;DateFmt('/%Y/%Y-%m-%d/')}" # Folder Structure based on Date e.g.: /2022/2002-08-23/
if [ "$SORT_FILETYPE" = true ]; then
_format+="\${FileType;s/([A-Za-z]+)/\L\$1\E/}/" # Folder Structure based on File Type e.g.: /2022/2002-08-23/JPEG/
fi
_format+="$PREFIX-" # Prefix for filename e.g.: 20221231-1 -> jwm-20221231-1
_format+="\${$1#;DateFmt('%Y%m%d')}" # Add Date to file name e.g.: jwm-20221231-1
_format+="\${FileName;" # Start original FileName manipulation
_format+="s/$PREFIX-*\d{4,8}-*//g;" # Account for any existing formatted filenames e.g.: jwm-1231-111 -> 111
_format+="s/([A-Za-z]+)\s+/\L\$1-/g;" # Convert sentence style filename to hyphen case e.g.: This file name.jpg -> this-file-name.jpg
_format+="s/[A-Z0_\.]*/-/;" # Remove Camera default Prefix e.g.: DSC0_111 -> -111
_format+="s/_/-/g;" # Convert any _'s to dashes '-' e.g.: DSC0_111_1_1 -> DSC0_111-1-1
_format+="s/[.](\d)/-\$1/g;" # Convert any .'s followed by a number to dashes '-' e.g.: DSC0_111.11.jpg -> DSC0_111-11.jpg
if [ "$ALLOW_DUPS" = true ]; then
_format+="s/([.a-zA-Z]*$)/%-c\$1/;" # Add unique sequence at the end of the filename for duplicates e.g.: DSC0_111 -> DSC0_111-1
fi
_format+="}" # End original FileName manipulation
# echo $_format
# $EXIFTOOL -r -ext+ AVI -progress "-TestName<$_format" $SOURCE_DIR_PATH
$EXIFTOOL -r -ext+ AVI -progress "-FileName<$_format" $SOURCE_DIR_PATH
}
run_exiftool $EXIFDATETAG
# _remaining=$(ls $SOURCE_DIR_PATH | wc -l | tr -d " \t")
# if [ "$_remaining" -gt 0 ]
# then
# echo "Found $_remaining files to sort"
# echo "Processing extra files..."
# run_exiftool "FileModifyDate"
# fi
echo "Sorting Complete!"
if [ "$CLEAN_SRC_DIR" = true ]; then
echo "Cleaning up the contents of: $SOURCE_DIR_PATH"
rm -rf $SOURCE_DIR_PATH/*
echo "Done!"
fi
return 0
}
sortMedia "$@"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment