LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Programming (https://www.linuxquestions.org/questions/programming-9/)
-   -   Sorting photos into folders based on exif date (https://www.linuxquestions.org/questions/programming-9/sorting-photos-into-folders-based-on-exif-date-722733/)

SuperJediWombat! 04-30-2009 10:55 AM

Sorting photos into folders based on exif date
 
I am trying to create a bash script to take photos from a directory, rename and sort them based on the date found in the exif data made by my camera.

When the script is finished it should move all the files into this structure: ./YYYY-MM/YYMMDD-HHMMSS.ext

The section I am having trouble with is sorting the renamed files into folders.

This command
Code:

jhead -autorot -ft -nf%y%m%d-%H%M%S *
renames the files in the current folder to YYMMDD-HHMMSS.jpg taken from exif data.

I am new to scripting as I'm sure you can see, is there an easy way to strip the first four numbers from the file names, and sort them based on that?

Code:

#!/bin/sh
#

# move files from camera to sorting area
mv /<pathtomemcard>/* /<pathtosortlocation>/

# rename all image files in sorting area based on exif dates
# YYMMDD-HHMMSS.ext
jhead  -autorot -ft -nf%y%m%d-%H%M%S /<pathtosortlocation>/*

# Sort files into folders based on the file name or exif date (whichever is easiest)
# NEED TO DO

# move sorted files into photo library
mv /<pathtosortlocation>/* /<pathtophotolib>/

Thanks in advance for any help!

jan61 04-30-2009 01:21 PM

Moin,

you're using bash?

Untested:
Code:

ls <pathtosortlocation> | while read f; do
  # extract first 4 characters from filename
  YYMM=${f:0:4}
  # create directory if it does not exist
  test -d $YYMM || mkdir $YYMM
  # move the current file to the destination dir
  mv <pathtosortlocation>/$f $YYMM/$f
done

Jan

SuperJediWombat! 04-30-2009 07:30 PM

Thank you!
 
Thanks jan61, that worked perfectly.

Here is my script so far:
Code:

#!/bin/bash
#
#
CameraPath="/home/angus/st/camera"
SortLocation="/home/angus/st/sort"
PhotoLibrary="/home/angus/st/library"
CharFromName=4

############
# move files from camera to $SortLocation
mv $CameraPath/* $SortLocation/

############
# rename all image files in $SortLocation
# YYMMDD-HHMMSS.ext
jhead  -autorot -ft -nf%y%m%d-%H%M%S $SortLocation/*

###########
# Sort files into folders using $CharFromName letters of the file name
#
ls $SortLocation | while read file; do
 # extract first $CharFromName characters from filename
 YYMM=${file:0:$CharFromName}
 # create directory if it does not exist
 test -d $SortLocation/$YYMM || mkdir $SortLocation/$YYMM
 # move the current file to the destination dir
 mv -v $SortLocation/$file $SortLocation/$YYMM/$file
done

##########
# move sorted files into photo library
mv -v $SortLocation/* $PhotoLibrary/

would it be possible to set $CameraPath to either the string set in the script, or the first argument used when running it. ($1)?

So I could execute the script as ./ImageSort.sh /new/location/of/images
to use /new/location/of/images as the camera path, but if I don't specify an argument it just uses the value given inside?

Also, can I have it pause when run, before moving the files to the sort location, and echo $CameraPath for confirmation?

Thanks again.

jan61 05-01-2009 10:39 AM

Moin,

Quote:

Originally Posted by SuperJediWombat! (Post 3526273)
...would it be possible to set $CameraPath to either the string set in the script, or the first argument used when running it. ($1)?

Code:

CameraPath=/path/to/default
test -n "$1" && CameraPath="$1"

Quote:

Originally Posted by SuperJediWombat! (Post 3526273)
Also, can I have it pause when run, before moving the files to the sort location, and echo $CameraPath for confirmation?

Code:

read -p "Path: $CameraPath; continue (y/n)?" confirm
test "$confirm" = "y" || exit 0

Jan

SuperJediWombat! 05-01-2009 12:38 PM

Moin,

Thanks jan, it's all coming together. I've just found that when using mv to move a directory, it does not merge the folders if the target directory has files inside.

Code:

##########
# move sorted files into photo library
mv -v $SortLocation/* $PhotoLibrary/

Gives this error
Code:

mv: cannot move `/home/angus/.imagesort/0905' to `/home/angus/Photos/0905': Directory not empty
Checking the mv man pages, and google hasn't helped, is there an argument to fix that?

SuperJediWombat! 05-02-2009 02:15 AM

Finished
 
All finished.

Code:

#!/bin/bash
#
#
PhotosPath="/media/4GBSD/DCIM/101CANON"
SortPath="/home/angus/.imagesort"
LibraryPath="/home/angus/Photos"
CameraPath="/media/4GBSD"
CharFromName=4
echo
echo
############
# Test to see if $PhotosPath exists, if not promp for new path / exit.
test -d $PhotosPath || read -p "$PhotosPath does not exist, close to exit or type new path:" PhotosPath
test -d $PhotosPath || "read -p '$PhotosPath is invalid. Press enter to close' && exit"

############
# move files from camera to $SortPath
mv $PhotosPath/* $SortPath/

############
# rename all image files in $SortPath
# FolderDateDD-HHMMSS.ext
jhead  -autorot -ft -nf%y%m%d-%H%M%S $SortPath/*

###########
# Sort files into folders using $CharFromName letters of the file name
#
ls $SortPath | while read file; do
 # extract first $CharFromName characters from filename
 FolderDate=${file:0:$CharFromName}
 # create directory if it does not exist
 test -d $LibraryPath/$FolderDate || mkdir $LibraryPath/$FolderDate
 # move the current file to the destination dir
 mv -v $SortPath/$file $LibraryPath/$FolderDate/$file
done

##########
# move sorted files into photo library
#mv -v $SortPath/* $LibraryPath/

##########
# Umount the card
umount $CameraPath

##########
# End notification
echo
echo "Photos  from: $PhotosPath"
echo "End location: $LibraryPath"
echo
echo "The card has been ejected."
echo
read -p "Press enter to close this window…"


manville 05-16-2009 08:03 AM

Simplifying
 
A lot of effort gone into this script but it also also useful to note that jhead as used here can be used to move the photos directly into directories as it renames them by modifying the output string format:

e.g.:

jhead -n%Y/%m/%d/%f *.jpg

will put the photos into a directory structure of /year/month/day (I used %f to retain the original filename and there are differences between -n and -nf so check the manual).

(Also works in "the other os" but you need to use "\" not "/" for directories)

SuperJediWombat! 05-16-2009 06:53 PM

Quote:

Originally Posted by manville (Post 3542728)
jhead -n%Y/%m/%d/%f *.jpg

Wow, thanks Manville. jhead is amazingly useful.


All times are GMT -5. The time now is 12:34 AM.