bash shell script to delete directory only if there are no files
Asked Answered
L

4

10

Ok so I am writing a shell script to delete a directory but only if there are no files inside.

what I want to do is have an if statement that will check if there are files in the directory and if there are files ask the user if they want to delete the files first and then delete the directory.

I have looked quite a bit into this and have found a way to check if files exist in the directory but I haven't been able to make it past that stage.

here is the if statement I have created so far to check if files exist in a directory:

echo "Please type the name of the directory you wish to remove "

                read dName
        shopt -s nullglob
        shopt -s dotglob
        directory=$Dname

        if [ ${#directory[@]} -gt 0 ];
        then
                echo "There are files in this directory! ";
        else
                echo "This directory is ok to delete! "
        fi
        ;;
Lindo answered 16/4, 2014 at 23:8 Comment(3)
rmdir already does this by default.Awful
As an aside, for shell scripts it is more convenient to accept arguments via $@ and $n variables instead of (or at least supplemental to) keyboard interaction.Geilich
releted: unix.stackexchange.com/a/46326/157086Deutsch
T
17

You don't need to check; rmdir will only delete empty directories.

$ mkdir foo
$ touch foo/bar
$ rmdir foo
rmdir: foo: Directory not empty
$ rm foo/bar
$ rmdir foo
$ ls foo
ls: foo: No such file or directory

In a more practical setting, you can use the rmdir command with an if statement to ask the user if they want to remove everything.

if ! rmdir foo 2> /dev/null; then
    echo "foo contains the following files:"
    ls foo/
    read -p "Delete them all? [y/n]" answer
    if [[ $answer = [yY] ]]; then
        rm -rf foo
    fi
fi
Tractable answered 16/4, 2014 at 23:40 Comment(1)
rmdir doesn't only error if the directory is full. So would probably be better to save stderr in a variable, and check to make sure it contains something like Directory not empty before deleting.Scourge
S
1

It feels like you're mixing some languages in the syntax you're using. Making minimal changes to your script, you can just use bash globing to see if it's full (could make an array as well, but don't see a good reason to), though I would probably still use something similar to chepner's script and let rmdir handle error checking.

#!/bin/bash

echo "Please type the name of the directory you wish to remove "

read dName
[[ ! -d $dName ]] && echo "$dName is not a directory" >&2 && exit 1 
shopt -s nullglob
shopt -s dotglob

found=
for i in "$dName"/*; do
  found=: && break
done

[[ -n $found ]] && echo 'There are files in this directory!' || echo 'This directory is ok to delete!'

Note couple of errors in your original syntax:

  • Variable names are case sensitive, $dName does not equal $Dname (and you should really quote variable names in case they have spaces or other special characters)
  • directory is not an array, you could have made it one by doing something like directory=($Dname/*)
  • ! will try to perform history expansion in double quotes if you have the option on.
Scourge answered 16/4, 2014 at 23:54 Comment(0)
B
1

If the directory is not empty, rmdir will raise an error and your script will stop if you run set -e before. You can simply check the ls output to see if a directory is empty before removing such directory:

test -n "$(ls -A "$directory")" || rmdir "$directory"

It's sadly prone to race conditions, because it will raise an error if a file gets added to the directory after the first and before the second command.

Backward answered 15/7, 2022 at 14:19 Comment(0)
S
0
rm -d $directory

rm since at least version 8.22 has supported this.

Shrew answered 22/8 at 21:45 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.