4

I’m using the following code to delete an empty folder on Linux:

bool removeFolder (const QString& path)
{
   QDir dir(path);
   assert(dir.exists());
   return dir.rmdir(".");
}

For some reason it sometimes returns false (for specific folders, but those folders don’t seem to be wrong in any way). If I subsequently use ::rmdir from <unistd.h> to remove the same folder, it succeeds. How can I tell why QDir::rmdir is failing?

This never happened on Windows so far, QDir::rmdir just works.

Violet Giraffe
  • 32,368
  • 48
  • 194
  • 335
  • Check if your dir is really empty. No invisible files? Temporaries? Something like a stray .nfs????? file? – Greenflow Sep 08 '13 at 14:02
  • @Greenflow: it is prefectly empty. I don't believe `rmdir` tolerates non-empty dirs either, and that works fine. I also have `assert(dir.entryList(QDir::NoDotAndDotDot | QDir::Hidden | QDir::System).isEmpty())`, and it never fires. – Violet Giraffe Sep 08 '13 at 14:09
  • Ok, I thought about a race condition between deleting files and your dir, but your assert makes this unlikely. – Greenflow Sep 08 '13 at 14:17
  • Does it make a difference when you do `dir.rmdir(path);` instead of `dir.rmdir(".");`? Don't see why it should. But I also don't see why it should fail at all. – Greenflow Sep 08 '13 at 14:20
  • @Greenflow: So I've had a folder ""/home/alex/Development/krusader/.git/branches" that I couldn't remove. Instead I constructed `QDir dir("/home/alex/Development/krusader/.git")` and called `dir.remove("branches")`. Still a fail. – Violet Giraffe Sep 08 '13 at 15:45
  • No more ideas. Should work. And works for me. Something wrong with your permissions? Though I have no idea why those should only be sometimes wrong. – Greenflow Sep 08 '13 at 16:00
  • You could try: `QFileInfo info("/home/alex/Development/krusader/.git/branches");` and `qDebug() << info.permissions();`. Maybe you see a difference in permissions when the folder can be deleted and when it can not. A desperate attempt, I know, but I have no more ideas. – Greenflow Sep 08 '13 at 16:05
  • Try calling rmdir from a QProcess execute call. If that works and you're happy with it, then great. If not, get the output and see what error you may receive. – TheDarkKnight Sep 09 '13 at 08:38
  • @Merlin069: when I said `rmdir` I meant a system Unix function from `` - much better way than QProcess. It's not a question about how to remove a dir, it's a question of why `QDir` doesn't. – Violet Giraffe Sep 09 '13 at 15:48
  • @VioletGiraffe, I know it's a unix system function, but you're calling from a QDir object which simply returns true or false, with no reason for failing. Called from a QProcess, you should be able to get the error message of why it is failing. I'm not suggesting you just use QProcess instead, but to use it to see what's causing the deletion to fail. – TheDarkKnight Sep 10 '13 at 07:34

3 Answers3

2

Confirming: works on windown, fails on linux.

Reading the "rmdir" doc in <unistd>, here https://pubs.opengroup.org/onlinepubs/007904875/functions/rmdir.html, it says there that "If the path argument refers to a path whose final component is either dot or dot-dot, rmdir() shall fail." So what's probably happening is that QDir::rmdir() is calling the unistd rmdir() function in linux, and this one fails with ".".

I tried to just use the full absolute path ( QDir::rmdir(absolutePath) ) and it worked; however, i see basically no point in using QDir::rmdir() over unistd's rmdir(), so i''ll stick w/ the unistd rmdir() from now on.

note: QDir::removeRecursively() is a different story: it seems to work okay, and it's way more convenient than going through opendir() and then successive readdir()'s (or the nftw(...FTW_DEPTH...) thingie).

Gyll
  • 351
  • 2
  • 6
  • The point of using Qt is to keep the code cross-platform (write once, run everywhere). – Violet Giraffe Mar 01 '21 at 13:27
  • @VioletGiraffe is as cross-platform as it gets. plus, having a function work on win and failing on lin _with the same arguments_ is anything but corss-platform. qt, or any other "cross-platform" toolkit is great, but only as a last resort compatibility layer, if you have a standard libraries alternative that's what you should go with – Gyll Mar 03 '21 at 11:43
1

I had the same problem but on Windows, I could not delete an empty directory with QDir().rmdir(path);. This happened on some older hard drive so may be the ancient file system was to blame. But I found a hack:

QFile(path).setPermissions(QFile::WriteOther); // this works even for dirs
bool success = QDir().rmdir(path);

Of course, you should revert the permissions back to original values if the deletion was unsuccessful anyway, but that's a different story.

0

Try to use this one:

dir.rmdir(dir.absolutePath())
Guinness
  • 86
  • 5