Skip to content

Instantly share code, notes, and snippets.

@porg
Created January 20, 2022 22:17
Show Gist options
  • Save porg/b6b3160f41c5c6ce7ced5a4982d4aa2e to your computer and use it in GitHub Desktop.
Save porg/b6b3160f41c5c6ce7ced5a4982d4aa2e to your computer and use it in GitHub Desktop.
Copy modification date from all files of source directory to same named files at destination directory if existing there
#!/bin/bash
if [[ -z "$1" || -z "$2" || "$1" == "-h" || "$1" == "--help" ]] ; then
cat <<EOF
USAGE: `basename $0` backupDir targetDir
Loops through all files on root level of backupDir.
For each file in backupDir it tries to find a same named file in targetDir.
- If not found in target (because renamed or removed meanwhile) the file is skipped.
- If found and they have the same modification timestamp nothing is done either.
- If found and the moddates differ the moddate is copied from the backup to the target.
EOF
exit
fi
backupDir=$1
targetDir=$2
if [[ ! -d "$backupDir" ]]
then
echo "Error! No directory at path for backupDir:"
echo "$1"
exit
fi
if [[ ! -d "$targetDir" ]]
then
echo "Error! No directory at path for targetDir:"
echo "$2"
exit
fi
backupFiles=$(ls -l1 "$backupDir")
targetFiles=$(ls -l1 "$targetDir")
backupFileCount=$(echo "$backupFiles" | wc -l)
targetFileCount=$(echo "$targetFiles" | wc -l)
echo
echo "Directories to process:"
echo " Backup:$backupFileCount files at: $backupDir"
echo " Target:$targetFileCount files at: $targetDir"
echo
echo "Output format:"
echo
echo " File Name.ext"
echo " Backup's creation date"
echo " Backup's modification date"
echo " Target's modification date"
echo
echo "Symbol at line start of target's moddate:"
echo
echo "√ Backup and target have same moddate. No need to act."
echo "≠ Target's mod-date differs. --> Gets restored from backup."
echo "x No same named file in target directory anymore."
echo
echo
echo "Copying modification timestamps..."
echo
echo "$backupFiles" | while read file
do
echo " $file"
backupFileCreation=$(GetFileInfo -d "$backupDir/$file")
backupFileModification=$(GetFileInfo -m "$backupDir/$file")
echo " $backupFileCreation"
echo " $backupFileModification ───┐"
if [[ -f "$targetDir/$file" ]] ; then
targetFileModification=$(GetFileInfo -m "$targetDir/$file")
if [[ "$backupFileModification" == "$targetFileModification" ]] ; then
echo "√ $targetFileModification √ ─┘"
else
SetFile -m "$backupFileModification" "$targetDir/$file"
echo "≠ $targetFileModification └───> Restored from backup √"
fi
else
echo "x Not in target dir ! ─┘"
fi
echo
done
@porg
Copy link
Author

porg commented Jan 20, 2022

Sample output of the script

$ cp-date-modified.sh \
~/Documents/Snagit-2020/Autosaved\ Captures.localized \
~/Documents/Snagit-2021-moddate-reset-to-creationdate

Directories to process:
  Backup:    1466 files at: ~/Documents/Snagit-2020/Autosaved Captures.localized
  Target:     889 files at: ~/Documents/Snagit-2021-moddate-reset-to-creationdate

Output format:

  File Name.ext
  Backup's creation date
  Backup's modification date
  Target's modification date

Symbol at line start of target's moddate:

√ Backup and target have same moddate. No need to act.
≠ Target's mod-date differs. --> Gets restored from backup.
x No same named file in target directory anymore.


Copying modification timestamps...

  0759652_PE750482_S5.snagproj
  09/08/2019 23:40:21
  06/10/2020 20:25:54 ───┐
≠ 10/21/2021 17:23:01    └───> Restored from backup √

  1a.snagproj
  01/04/2021 19:55:55
  01/22/2021 21:43:58 ───┐
x  Not in target dir  ! ─┘

  1c.snagproj
  01/04/2021 19:56:44
  01/04/2021 19:56:45 ───┐
x  Not in target dir  ! ─┘

  ux usp 7.snagproj
  05/25/2021 02:00:15
  05/25/2021 02:00:16 ───┐
≠ 10/21/2021 17:23:02    └───> Restored from backup √

  wordlist ISM vs ISMUS.snagproj
  05/06/2021 22:17:22
  05/06/2021 22:25:41 ───┐
≠ 10/21/2021 17:23:03    └───> Restored from backup √

  wordlist ISMUS reduced a bit but still heavy.snagproj
  05/06/2021 22:18:19
  05/06/2021 22:25:41 ───┐
≠ 10/21/2021 17:23:03    └───> Restored from backup √

  2019-03-03_12-27-17.snagproj
  03/03/2019 12:27:18
  03/03/2019 12:27:18 ───┐
√ 03/03/2019 12:27:18 √ ─┘

  2019-03-03_12-28-29.snagproj
  03/03/2019 12:28:29
  03/03/2019 12:28:29 ───┐
√ 03/03/2019 12:28:29 √ ─┘

@drlambert100
Copy link

Now that I have the script file, does it work when the file extensions in source and target differ? Does only the file name matter or must both the filename and file extension be the same?
Do I run this script in a command prompt?
Will it ask for the source and target folders?

@porg
Copy link
Author

porg commented Aug 8, 2023

  1. It compares the whole filename including the extension as stored in the filesystem.

    • Note: The file extension visibility of a file in the Finder is another file metadata flag only relevant for display in Finder, but is not considered for the comparison of the script.
  2. You run this script in a Terminal. The script file must be executable. If it is not yet executable you must give it the execution flag with:

    chmod +x /path/to/file-cp-date-modified-sh
    
  3. It will not ask for the source and target folder interactively, but you must supply these as the first and second argument, so:

    cp-date-modified.sh /path/to/source-directory/ /path/to/target-directory/
    

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment