Bash find command : No such file or directory
This one is stumping me quite well! Big points for a resolution! I need to traverse a directory and all levels below it to discover any files or directories that do not match a pattern. I’m using find command —
find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '/home/user/inbox/*' -a ! -path /home/user/inbox/imaging -a ! -path '/home/user/inbox/imaging/*' \) -ls
find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '/home/user/inbox/*' -a ! -path /home/user/inbox/imaging -a ! -path '/home/user/inbox/imaging/*' \) -ls: No such file or directory
ls -ld /home/user/inbox /home/user/inbox/imaging/ drwxr-xr-x. 5 user grp-ftp-admin 8192 Jan 13 12:45 /home/user/inbox drwxr-xr-x. 3 user grp-ftp-admin 152 Jan 13 12:21 /home/user/inbox/imaging/
#!/usr/bin/env bash function findInvalidArtifacts() < unset inbox sshCommand exitCode cmdOutput s ilocal -A VENDOR=( ['FTPBASE']="/home/user" ['FTPSOURCEDIR']="/home/user/inbox/imaging" ['FRIENDLYNAME']="user" ['ENVIRONMENT']="dev" ) inbox="$/inbox" printf -v sshCommand "find -L %s \( ! -path %s -a ! -path '%s/*' -a ! -path %s -a ! -path '%s/*' \) -ls" \ "$" "$" "$" "$" "$" #cmdOutput=$(ssh $ $ "$" 2>&1) cmdOutput=$("$") exitCode="$" if (( 0 != $exitCode )); then printf "FAILED - sshCommand=[%s], exitCode=[%d], cmdOutput=[%s]\n" "$" "$" "$" exit 1 fi printf "SUCCEEDED - sshCommand=[%s] exitCode=[%d]\n" "$" "$" printf "%s\n\n" "$" > # end findInvalidArtifacts()
#!/usr/bin/env bash function findInvalidArtifacts() < unset inbox sshCommand exitCode cmdOutput local -A VENDOR=( ['FTPBASE']="/home/user" ['FTPSOURCEDIR']="/home/user/inbox/imaging" ['FRIENDLYNAME']="user" ['ENVIRONMENT']="dev" ) inbox="$/inbox" printf -v sshCommand "find -L %s \( ! -path %s -a ! -path '%s/*' -a ! -path %s -a ! -path '%s/*' \) -ls" \ "$" "$" "$" "$" "$" #cmdOutput=$(ssh $ $ "$" 2>&1) cmdOutput=$("$") exitCode="$" if (( 0 != $exitCode )); then printf "FAILED - sshCommand=[%s], exitCode=[%d], cmdOutput=[%s]\n" "$" "$" "$" exit 1 fi printf "SUCCEEDED - sshCommand=[%s] exitCode=[%d]\n" "$" "$" printf "%s\n\n" "$" > # end findInvalidArtifacts() findInvalidArtifacts + findInvalidArtifacts + unset inbox sshCommand exitCode cmdOutput + VENDOR=(['FTPBASE']="/home/user" ['FTPSOURCEDIR']="/home/user/inbox/imaging" ['FRIENDLYNAME']="user" ['ENVIRONMENT']="dev") + local -A VENDOR + inbox=/home/user/inbox + printf -v sshCommand 'find -L %s \( ! -path %s -a ! -path '\''%s/*'\'' -a ! -path %s -a ! -path '\''%s/*'\'' \) -ls' /home/user/inbox /home/user/inbox /home/user/inbox /home/user/inbox/imaging /home/user/inbox/imaging ++ 'find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '\''/home/user/inbox/*'\'' -a ! -path /home/user/inbox/imaging -a ! -path '\''/home/user/inbox/imaging/*'\'' \) -ls' ./try.sh: line 16: find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '/home/user/inbox/*' -a ! -path /home/user/inbox/imaging -a ! -path '/home/user/inbox/imaging/*' \) -ls: No such file or directory + cmdOutput= + exitCode=127 + (( 0 != 127 )) + printf 'FAILED - sshCommand=[%s], exitCode=[%d], cmdOutput=[%s]\n' 'find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '\''/home/user/inbox/*'\'' -a ! -path /home/user/inbox/imaging -a ! -path '\''/home/user/inbox/imaging/*'\'' \) -ls' 127 '' FAILED - sshCommand=[find -L /home/user/inbox \( ! -path /home/user/inbox -a ! -path '/home/user/inbox/*' -a ! -path /home/user/inbox/imaging -a ! -path '/home/user/inbox/imaging/*' \) -ls], exitCode=[127], cmdOutput=[] + exit 1
This is a stumper. I cannot see where why find is complaining about ‘no such file or directory’. Appreciate the valiant effort, however the constructed command still does not return the desired results. The contents of finding all existing artifacts in /home/user/inbox are:
/home/user/inbox /home/user/inbox/invalidDir2 /home/user/inbox/invalidDir2/invalidSubdir2 /home/user/inbox/invalidDir2/invalidSubdir2/invalidFile1 /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2 /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2/invalidSubSubSubDir2 /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2/invalidSubSubSubDir2/invalidSubSubSubSubDir2 /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2/invalidSubSubSubDir2/invalidSubSubSubSubDir2/invalidFile /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2/invalidSubSubSubDir2/invalidFile /home/user/inbox/invalidDir2/invalidSubdir2/invalidSubSubDir2/invalidFile /home/user/inbox/imaging /home/user/inbox/imaging/validFile /home/user/inbox/imaging/invalidFile /home/user/inbox/imaging/invalidImagingDir1 /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1 /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1/invalidFile1 /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1/invalidSubSubDir1 /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1/invalidSubSubDir1/invalidSubSubSubDir1 /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1/invalidSubSubDir1/invalidSubSubSubDir1/invalidFile /home/user/inbox/imaging/invalidImagingDir1/invalidSubdir1/invalidSubSubDir1/invalidFile /home/user/inbox/imaging/invalidImagingDir1/invalildFile /home/user/inbox/invalidFile /home/user/inbox/invalidDir1 /home/user/inbox/invalidDir1/invalidSubdir1 /home/user/inbox/invalidDir1/invalidSubdir1/invalidFile1 /home/user/inbox/invalidDir1/invalidSubdir1/invalidSubSubDir1 /home/user/inbox/invalidDir1/invalidSubdir1/invalidSubSubDir1/invalidSubSubSubDir1 /home/user/inbox/invalidDir1/invalidSubdir1/invalidSubSubDir1/invalidSubSubSubDir1/invalidFile /home/user/inbox/invalidDir1/invalidSubdir1/invalidSubSubDir1/invalidFile
The result set should NOT contain anything matching the directory to search in, or any of the parameters passed to your function that constructs the command. Results should NOT contain these lines —
/home/user/inbox /home/user/inbox/imaging /home/user/inbox/imaging/validFile
find -L /home/user/inbox '(' '!' -path /home/user/inbox -a '!' -path '/home/user/inbox/*' -a '!' -path /home/user/inbox/imaging -a '!' -path '/home/user/inbox/imaging/*' ')' -ls
which returns nothing at all I’m beginning to think that the find command is not what I need to obtain the desired results and that I’ll need to do some more processing of the result set to disclude, probably awk or something.
find: `./folder’: No such file or directory
Now I would like to remove everything from this directory except for the file demo.c . Here’s the command I’ve come up with:
find . ! \( -name demo.c -o -name . \) -exec rm -Rf <> \;
It does exactly what you’d think it would do (meaning, the file test and the directory folder are gone), but at the same time it also displays the following error message:
find: `./folder': No such file or directory
3 Answers 3
it also displays this error message:
find: `./folder': No such file or directory
Because find recognizes ./folder as a directory when it first reads directory . , before considering whether it matches the find criteria or performing any action on it. It does not recognize that the action will remove that directory, so after performing the action, it attempts to descend into that directory to scan its contents. By the time it does that, however, the directory no longer exists.
There are multiple ways to address the problem. One not yet mentioned is to use the -prune action. This tells find not to descend into directories that match the tests:
find . ! \( -name demo.c -o -name . \) -exec rm -Rf <> \; -prune
That will serve nicely here, and it also has applications in areas where you are not deleting the directory and you do not want to limit the search depth.
Additionally, another way to avoid affecting . would be to make use of the fact that find accepts multiple base paths to test, that these can designate regular files if you wish, and that during pathname expansion any leading . in a filename must be matched explicitly. If, as in your case, there are no dotfiles in the target directory (other than . and .. ), then you can accomplish your objective like this:
find * ! -name demo.c -exec rm -Rf <> \; -prune
«find: .: No such file or directory» while using find on the current directory
Find command seems not to work at all. For example, I’m in a directory where there absolutely is file named index.php and I execute this:
[root@server htdocs]# find . -name "index.php" find: .: No such file or directory
I always get this no such file or directory error. No matter what path I define, or what file I search for, I always get this error. I’m pretty sure that I’m overlooking something very simple. Can someone point out what I’m doing wrong?
[root@server htdocs]# pwd /srv/www/htdocs [root@server htdocs]# type -a find find is /usr/bin/find [root@server htdocs]# ls -la | grep index.php -rw-rw-r-- 1 andris users 413 Sep 1 2013 index.php [root@server htdocs]# find . -name "index.php" find: .: No such file or directory [root@server htdocs]# find . . find: .: No such file or directory [root@server htdocs]# stat . File: `.' Size: 4096 Blocks: 8 IO Block: 4096 directory Device: ca00h/51712d Inode: 155686 Links: 12 Access: (0775/drwxrwxr-x) Uid: ( 504/ andris) Gid: ( 100/ users) Access: 2014-06-17 19:37:22.000000000 +0000 Modify: 2014-06-08 21:06:16.000000000 +0000 Change: 2014-06-08 21:06:16.000000000 +0000 [root@server htdocs]# find --version GNU find version 4.2.27 Features enabled: D_TYPE O_NOFOLLOW(enabled) LEAF_OPTIMISATION SELINUX
[root@server htdocs]# find . -noleaf -name "index.php" find: .: No such file or directory
find command in bash script resulting in «No such file or directory» error only for directories?
UPDATE 2014-03-21 So I realized I wasn’t as efficient as I could be, as all the disks that I needed to «scrub» were under /media and named » disk1 , disk2 , disk3 , etc.» Here’s the final script:
DIRTY_DIR="/media/disk*" find $DIRTY_DIR -depth -type d -name .AppleDouble -exec rm -rf <> \; find $DIRTY_DIR -depth -type d -name .AppleDB -exec rm -rf <> \; find $DIRTY_DIR -depth -type d -name .AppleDesktop -exec rm -rf <> \; find $DIRTY_DIR -type f -name ".*DS_Store" -exec rm -f <> \; find $DIRTY_DIR -type f -name ".Thumbs.db" -exec rm -f <> \; # I know, I know, this is a Windows file.
Next will probably to just clean up the code even more, and add features like logging and reporting results (through e-mail or otherwise); excluding system and directories; and allowing people to customize the list of files/directories. Thanks for all the help! UPDATE Before I incorporated the helpful suggestions provided by everyone, I performed some tests, the results of which were very interesting (see below). As a test, I ran this command:
root@doi:~# find /media/disk3 -type d -name .AppleDouble -exec echo rm -rf <> \;
rm -rf /media/disk3/Videos/Chorus/.AppleDouble
root@doi:~# find /media/disk3 -type d -name .AppleDouble -exec rm -rf <> \;
find: `/media/disk3/Videos/Chorus/.AppleDouble': No such file or directory
I put «error» in quotes because obviously the folder was removed, as verified by immediately running:
root@doi:~# find /media/disk3 -type d -name .AppleDouble -exec rm -rf <> \; root@doi:~#
It seems like the find command stored the original results, acted on it by deleting the directory, but then tried to delete it again? Or is the -f option of rm , which is supposed to be for ignoring nonexistent files and arguments, is ignored? I note that when I run tests with the rm command alone without the find command, everything worked as expected. Thus, directly running rm -rf . \nonexistent_directory , no errors were returned even though the «non_existent_directory» was not there, and directly running rm -r \nonexistent_directory provided the expected:
rm: cannot remove 'non_existent_directory': No such file or directory
Should I use the -delete option instead of the -exec rm . option? I had wanted to make the script as broadly applicable as possible for systems that didn’t have -delete option for find . Lastly, I don’t presume it matters if /media/disk1 , /media/disk2 , . are combined in an AUFS filesystem under /media/storage as the find command is operating on the individual disks themselves? Thanks for all the help so far, guys. I’ll publish the script when I’m done. ORIGINAL POST I’m writing a bash script to delete a few OS X remnants on my Lubuntu file shares. However, when executing this:
. BASE_DIR="/media/disk" # I have 4 disks: disk1, disk2, . COUNTER=1 while [ $COUNTER -lt 5 ]; do # Iterate through disk1, disk2, . DIRTY_DIR=$$COUNTER # Look under the current disk counter /media/disk1, /media/disk2, . find $DIRTY_DIR -name \.AppleDouble -exec rm -rf <> \; # Delete all .AppleDouble directories find $DIRTY_DIR -name ".*DS_Store" -exec rm -rf <> \; # Delete all .DS_Store and ._.DS_Store files COUNTER=$(($COUNTER+1)) done .
I see the following output: find: /media/disk1/Pictures/.AppleDouble : No such file or directory Before I added the -exec rm . portion the script found the /media/disk1/Pictures/.AppleDouble directory. The script works properly for removing DS_Store files, but what am I missing for the find command for directories? I’m afraid to screw too much with the -exec portion as I don’t want to obliterate directories in error.