12

I'm trying to find a way to immediately move a file to another folder as soon as it appears in my dropbox on CentOS.

I have scoured the internet for some clues but I can't get any further than the fact that I need to use inotify to invoke a script which will process the file as it appears.

My BASH knowledge is very limited and I doubt I can write this in PHP.

In other words, how can I move a file to another folder as soon as it appears using inotify?

  • Is the name of the file consistently predictable? Or it's location? More detail would be helpful... – jasonwryan Aug 10 '13 at 22:07
  • @jasonwryan It's a dropbox folder so the location is consistent. And it applies to any file dropped in that folder. – Ortix92 Aug 10 '13 at 22:14
13

This is a simple approach:

#!/usr/bin/env bash

dir=/home/ortix/Dropbox/new/
target=/home/ortix/movedfiles/

inotifywait -m "$dir" --format '%w%f' -e create |
    while read file; do
        mv "$file" "$target"
    done

With more details about the types of files you wanted to move, you could add some checking, logging etc...

|improve this answer|||||
  • I haven't been able to test either of the suggested answers. Things came up. Will do so ASAP! I do have a question though. If I were to put this in a bash file and run it, I assume that it will run in the background, correct? I always have the feeling that a script is a 1 time run thing, but here inotifywait keeps running, correct? – Ortix92 Aug 14 '13 at 19:09
  • 2
    listening on create event isn't correct, as you will do a mv on a file which may not be fully copied on disk. See @Gilles answer, using close_write event instead. – fduff Jun 26 '14 at 7:57
  • 3
    @fduff Seeing Gilles answer is always the correct thing to do... – jasonwryan Jun 26 '14 at 8:00
17

The command inotifywait prints a message each time a the contents of the specified directory change. You'll need to pick on the right event: not when the file is created, but when Dropbox has finished downloading it. I don't know exactly how Dropbox operates. If it writes to the file in its final place, listen to close_write events. If it writes to the file into a temporary location and then moves it into place, listen to moved_to events. Pass the options -m -q to inotifywait so that it keeps listening for events (by default, it only waits for the next event) and only prints relevant messages.

cd ~/Dropbox/myfolder
inotifywait -m -q -e close_write --format %f . | while IFS= read -r file; do
  cp -p "$file" /path/to/other/directory
done
|improve this answer|||||
  • 1
    This fails for files which include newlines in their names. I was unable to find a way to have inotifywait output null-terminated filenames. The best I could do was to use a character that's less likely than newline, for example %f$'\001', and use -d $'\001' with while IFS= read -r or xargs. – Paused until further notice. Nov 3 '15 at 22:48
  • 1
    @DennisWilliamson Yes, inotifywait is annoying that way. You can use something like //%f, as the file name will never contain a double slash as long as the path to watch doesn't; then the annoyance is on the parsing side. – Gilles 'SO- stop being evil' Nov 3 '15 at 22:53

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.