Migrate to RunxBuild and earn up to $50 in hosting credit on your first deposit.

Calculate your savings
unxBuild

rmdir: Directory Not Empty — Removing Non-Empty Directories in Linux

Sean

Platform Writer

Aug 26, 2026
7 min read

rmdir refuses non-empty directories on purpose — it is a deliberately narrow tool that cannot cause a recursive delete by accident. To remove a directory with contents, use rm -r directory. Add -f only when you want errors suppressed, and understand that the two flags do very different things.

rmdir: Directory Not Empty — Removing Non-Empty Directories in Linux

The error is clear enough:

Table of contents

The two commands and what separates them

$ rmdir myfolder
rmdir: failed to remove 'myfolder': Directory not empty

rmdir calls the rmdir(2) system call, which the kernel refuses on a non-empty directory. That is not a limitation somebody forgot to fix — it is the safety property that makes rmdir useful in scripts, where you want to remove a directory only if nothing is in it.

rm -r walks the tree and unlinks everything it finds. Different tool, different guarantees.

rm -r myfolder      # remove the directory and everything under it
rm -ri myfolder     # ask before each file
rm -rf myfolder     # remove, suppressing errors and prompts

The distinction between -r and -f gets blurred because people type them together as one word. They are unrelated:

  • -r is recursion. Without it, rm will not descend into directories at all.
  • -f suppresses prompts and error messages, and makes rm exit 0 even if the target did not exist.

rm -r on its own already removes a full tree. The -f adds nothing to the deletion — it only removes the feedback that might have stopped you.

Look before you delete

The habit that prevents most rm -rf accidents costs one command:

ls -la myfolder
du -sh myfolder
find myfolder -type f | wc -l

If you expected a scratch directory and du reports 40GB across 200,000 files, that is a useful moment to have before the deletion rather than after.

find also gives you a genuine dry run, which rm does not have:

find myfolder -type f -name "*.log" -print          # list matches
find myfolder -type f -name "*.log" -delete        # then delete them

Run the -print form, read the output, then re-run with -delete. For anything selective this is strictly better than rm -rf, because you see the exact set before it goes.

Two habits worth adopting permanently:

  • Never end an rm -rf argument with a variable that could be empty. rm -rf "$DIR/" with DIR unset expands to rm -rf /. Guard it: [ -n "$DIR" ] && rm -rf "$DIR".
  • Use relative paths from a known directory rather than absolute paths typed from memory.

When rm -rf fails anyway

-f suppresses complaints, so a silent failure is easy to miss. The usual causes:

Permissions. To remove a file you need write and execute on its parent directory, not on the file. A file you own inside a directory you cannot write is not yours to delete.

ls -ld myfolder            # check the directory's permissions
sudo rm -r myfolder        # if the directory belongs to another user

A mount point. You cannot remove a directory that has a filesystem mounted on it. Check with mount | grep myfolder, unmount, then remove.

Files in use. Deleting an open file works on Linux — the name goes, the inode survives until the last handle closes. So the space is not reclaimed even though the file is gone. lsof +D myfolder shows what is holding it.

Immutable attributes. Rare but genuinely confusing when hit, because root cannot delete the file either:

lsattr myfolder/stubborn-file    # look for 'i'
sudo chattr -i myfolder/stubborn-file

Argument list too long. With hundreds of thousands of files, glob expansion overflows. Use find instead, which does not build one enormous argument list:

find myfolder -type f -delete && rmdir myfolder

Where rmdir is the better choice

Because it fails on non-empty directories, rmdir is the correct tool whenever emptiness is the condition you actually care about.

rmdir /tmp/build-workspace 2>/dev/null || echo "not empty, leaving it alone"

That is a script that cleans up after itself and refuses to delete anything unexpected. The equivalent with rm -rf would remove whatever happened to be there, including output somebody else was relying on.

-p removes a chain of empty parents in one go, which is tidy for nested scratch paths:

rmdir -p a/b/c     # removes c, then b, then a, stopping at the first non-empty one

And to sweep every empty directory out of a tree without touching anything containing files:

find . -type d -empty -delete

That is a genuinely safe cleanup, because the -empty test guarantees nothing with contents is removed.

How this fits the rest of the stack

The reason rmdir exists alongside rm -r is that a narrow tool which refuses ambiguous input is worth more than a general one that always succeeds. You want the command to fail when the situation is not what you assumed.

That principle scales up. A deploy that fails loudly on a bad build is better than one that ships something unexpected, and infrastructure you can roll back is better than infrastructure you have to repair by hand. RunxBuild keeps a build log and a rollback target for every deploy, so a bad release is a selection rather than a recovery operation. If you want to see what a service, its database and its storage come to before committing, the RunxBuild hosting calculator breaks it out line by line.

Useful related references:

FAQ

Why does rmdir say directory not empty?

Because that is its entire design. rmdir calls a system call that the kernel refuses on non-empty directories, which makes it safe to use in scripts where you only want to remove a directory if nothing is in it. Use rm -r when you intend to delete contents.

What is the difference between rm -r and rm -rf?

-r is what makes rm descend into directories, and on its own it already removes an entire tree. -f only suppresses prompts and error messages and forces a zero exit code. Adding -f does not delete more — it removes the feedback that might have warned you.

How do I delete a directory with too many files for rm?

When glob expansion overflows the argument limit, use find myfolder -type f -delete followed by rmdir myfolder. find processes entries incrementally instead of building one enormous argument list.

Why can I not delete a file even as root?

Check for the immutable attribute with lsattr — a file flagged i cannot be deleted by anyone until you clear it with chattr -i. The other common cause is a mount point, which cannot be removed until the filesystem is unmounted.

How do I safely remove only empty directories in a tree?

find . -type d -empty -delete removes every empty directory and cannot touch anything containing files, because the -empty test does the filtering. For a known nested path, rmdir -p a/b/c removes empty parents and stops at the first non-empty one.

#rmdir non empty directory linux#rmdir#rm#linux#command line