While loop to test if a file exists in bash

BashShell

Bash Problem Overview


I'm working on a shell script that does certain changes on a txt file only if it does exist, however this test loop doesn't work, I wonder why? Thank you!

while [ ! -f /tmp/list.txt ] ;
do
      sleep 2
done

Bash Solutions


Solution 1 - Bash

When you say "doesn't work", how do you know it doesn't work?

You might try to figure out if the file actually exists by adding:

while [ ! -f /tmp/list.txt ]
do
  sleep 2 # or less like 0.2
done
ls -l /tmp/list.txt

You might also make sure that you're using a Bash (or related) shell by typing 'echo $SHELL'. I think that CSH and TCSH use a slightly different semantic for this loop.

Solution 2 - Bash

If you are on linux and have inotify-tools installed, you can do this:

file=/tmp/list.txt
while [ ! -f "$file" ]
do
    inotifywait -qqt 2 -e create -e moved_to "$(dirname $file)"
done

This reduces the delay introduced by sleep while still polling every "x" seconds. You can add more events if you anticipate that they are needed.

Solution 3 - Bash

I had the same problem, put the ! outside the brackets;

while ! [ -f /tmp/list.txt ];
do
    echo "#"
    sleep 1
done

Also, if you add an echo inside the loop it will tell you if you are getting into the loop or not.

Solution 4 - Bash

I ran into a similar issue and it lead me here so I just wanted to leave my solution for anyone who experiences the same.

I found that if I ran cat /tmp/list.txt the file would be empty, even though I was certain that there were contents being placed immediately in the file. Turns out if I put a sleep 1; just before the cat /tmp/list.txt it worked as expected. There must have been a delay between the time the file was created and the time it was written, or something along those lines.

My final code:

while [ ! -f /tmp/list.txt ];
do
    sleep 1;
done;
sleep 1;
cat /tmp/list.txt;

Hope this helps save someone a frustrating half hour!

Solution 5 - Bash

Like @zane-hooper, I've had a similar problem on NFS. On parallel / distributed filesystems the lag between you creating a file on one machine and the other machine "seeing" it can be very large, so I could wait up to a full minute after the creation of the file before the while loop exits (and there also is an aftereffect of it "seeing" an already deleted file).

This creates the illusion that the script "doesn't work", while in fact it is the filesystem that is dropping the ball.

This took me a while to figure out, hope it saves somebody some time.

PS This also causes an annoying number of "Stale file handler" errors.

Solution 6 - Bash

Here is a version with a timeout so that after an amount of time the loop ends with an error:

# After 60 seconds the loop will exit
timeout=60

while [ ! -f /tmp/list.txt ];
do
  # When the timeout is equal to zero, show an error and leave the loop.
  if [ "$timeout" == 0 ]; then
    echo "ERROR: Timeout while waiting for the file /tmp/list.txt."
    exit 1
  fi

  sleep 1

  # Decrease the timeout of one
  ((timeout--))
done

Solution 7 - Bash

works with bash and sh both:

touch /tmp/testfile
sleep 10 && rm /tmp/testfile &
until ! [ -f /tmp/testfile ]
do
   echo "testfile still exist..."
   sleep 1
done
echo "now testfile is deleted.."

Solution 8 - Bash

do it like this

while true
do
  [ -f /tmp/list.txt ] && break
  sleep 2
done
ls -l /tmp/list.txt

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionZenetView Question on Stackoverflow
Solution 1 - BashCWFView Answer on Stackoverflow
Solution 2 - BashyingtedView Answer on Stackoverflow
Solution 3 - BashDavid CoxView Answer on Stackoverflow
Solution 4 - BashZaneView Answer on Stackoverflow
Solution 5 - BashRuslan ShaydulinView Answer on Stackoverflow
Solution 6 - BashZedTuXView Answer on Stackoverflow
Solution 7 - BashneerajmalveView Answer on Stackoverflow
Solution 8 - Bashghostdog74View Answer on Stackoverflow