5

I try to write script to check if a file was modified or not. If it did, it should echo "Error!", if not - script keeps running.

My script

#!/bin/bash
date=$(stat -c %y)$1
while true
         do date2=$(stat -c %y$1)
                if (date2 != date)
                        echo "error!"
        done

Are there any errors?

15

you can use inotifywait , read more

inotifywait - wait for changes to files using inotify

inotifywait efficiently waits for changes to files using Linux's inotify(7) interface. It is suitable for waiting for changes to files from shell scripts. It can either exit once an event occurs, or continually execute and output events as they occur.

use this command :

$ inotifywait -m -e modify /tmp/testfile

when i write into testfile , inotifywait alarm to me

e.g;

echo "bh" > /tmp/testfile

inotifywait show this message:

$ inotifywait -m -e modify /tmp/testfile
Setting up watches.  
Watches established.
testfile MODIFY 
testfile MODIFY 

also you can redirect output to while statement :

while read j
do
   echo "file changed"
   break
done <  <(inotifywait -q -e modify /tmp/testfile)
| improve this answer | |
4
filename="$1"

m1=$(md5sum "$filename")

while true; do

  # md5sum is computationally expensive, so check only once every 10 seconds
  sleep 10

  m2=$(md5sum "$filename")

  if [ "$m1" != "$m2" ] ; then
    echo "ERROR: File has changed!" >&2 
    exit 1
  fi
done
| improve this answer | |
0

Consider using md5sum, is safer to check real file modifications. This is script will return "The files are different" if a file diverge from the other, but when you equalize then, it will say the files are equal again.

#!/bin/bash

loop1(){
while sleep 1 
        do 
               md5f1=$(md5sum "$1" | cut -d' ' -f1) 
               md5f2=$(md5sum "$2" | cut -d' ' -f1)
               if [ "$md5f2" != "$md5f1" ]; then 
                    echo "The files are different now." 
                    #stop loop:
                    break 
               fi
        done
}

loop2(){ 
while sleep 1 
        do 
               md5f1=$(md5sum "$1" | cut -d' ' -f1) 
               md5f2=$(md5sum "$2" | cut -d' ' -f1)
               if [ "$md5f2" == "$md5f1" ]; then 
                    echo "The files are equal again." 
                    #stop loop:
                    break 
               fi
        done
}

while true; do 
   loop1 "$1" "$2"
   loop2 "$1" "$2"
done

Save it as autocompare and run like:

./autocompare file1 file2 
| improve this answer | |
  • Not i corrected it 4 mins ago. – Luciano Andress Martini Jun 2 '16 at 15:07
  • md5sum is the right approach, but that script is far more complicated than it needs to be. and it's comparing two different files, not just one file against possibly different versions of itself. – cas Jun 3 '16 at 2:05
  • 3
    md5sum might not be a perfect approach if this is a particularly huge file and you plan to monitor this continually (excessive i/o and cpu usage?) – steve Jun 4 '16 at 16:43
0

If you do want to 'manually' check for change in the modification timestamp, as opposed to actual difference in the contents, you need:

  • stat -c %y $1 consistently with the separating spaces and inside $( ... ). Even better, stat -c %y "$1" will work if your filename contains whitespace or any 'globbing' character

  • test with classic [ ... ] or test ... and "$var" (because stat %y contains spaces; stat %Y would avoid that) or bash-enhanced [[ ... ]] which doesn't need quotes -- but not ( ... ) which does something completely different namely execute in a subshell

  • some delay between loops so this doesn't completely hog your system

 #!/bin/bash 
 date=$(stat -c %y "$1")
 while sleep 1; do date2=$(stat -c %y "$1")
   if [[ $date2 != $date ]]; then echo "changed!"; break; fi
   # possibly exit [status] instead of break
   # or if you want to watch for another change, date=$date2
 done
| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.