Hello Eric, On Fri, Aug 19, 2011 at 5:04 PM, Eric Blake <ebl...@redhat.com> wrote: > On 08/19/2011 08:45 AM, Suvayu Ali wrote: >> >> I am trying to test if a file exists and then source it. My problem is >> the test succeeds even if the variable is empty! If I pass no argument >> at all, it still succeeds. To give you an example: >> >> $ unset bla >> $ [ -f $bla ]&& echo yes >> yes >> $ [ -f ]&& echo yes >> yes > > Both expected behaviors, and evidence of your lack of quoting. > > Remember, the behavior of [] depends on how many arguments are present. > > [ -f "$bla" ] (note the "") - guarantees that there are exactly two > arguments, so it proceeds with the two-argument test where -f is the > operator and "$bla" is the file name. > > [ -f ] (which is the same as [ -f $bla ] if $bla is empty, note the lack of > "") - there is exactly one argument, so it proceeds with the one-argument > test of whether the argument (the literal string -f) is empty (it is not). > > Furthermore, [ -f $bla ] is different than [[ -f $bla ]]. [ is a POSIX > utility, and mandated to do all argument word expansion before [ ever gets a > chance to see what arguments it was given - if $bla is empty or has spaces, > you changed the number of arguments that are given to [. [[ is a bash (and > ksh) extension that is part of the shell syntax (similar to how () for > subshells is part of the syntax), thus it knows how many words, > _pre-expansion_, were present, and the fact that $bla was unquoted is not a > problem, [[ -f $bla ]] is a safe way to check if $bla is a file even if $bla > is empty or contains spaces. >
Thanks a lot for the very clear explanation. I'll be careful in the future. :) -- Suvayu Open source is the future. It sets us free.