在使用C#/ .Net时,只读如何影响目录?

我发现我可以写(即复制一个文件)到一个只读目录。 也就是说,一个具有...Attributes = FileAttributes.ReadOnly的目录。我甚至可以改变它的名字。 我发现唯一不能做的就是删除它。 这是ReadOnly防止的唯一事情吗?

编辑:

这是代码:(目录是空的。)

 (new DirectoryInfo(path)).Attributes = FileAttributes.ReadOnly; Directory.Delete(path); 

它抛出一个Access to the path 'c:\... is denied. 例外。

但更改ReadOnlyNormal工作正常。

那么ReadOnly是什么防止,什么不能防止? (当然编程, 不是 :通过Windows资源pipe理器。)

编辑2:

我收到了链接到文档的答案,说ReadOnly在目录上是不被尊重的,而且可能是.Net ,它负责删除的失败。 所以我将重新修改这个问题:“ 使用C#/ .Net时 ,只读如何影响目录?

Solutions Collecting From Web of "在使用C#/ .Net时,只读如何影响目录?"

正如Damien_The_Unbeliever提到的,如果我们查看FILE_ATTRIBUTE_READONLY的Win32 API,它会提到:

这个属性不符合目录。

另请参阅: http : //go.microsoft.com/fwlink/p/?linkid=125896

所以你可以简单地使用win32或者Explorer删除这些目录。 但是,.NET似乎在删除它们之前检查目录上的标志。 你可以在Directory.Delete中使用DotPeek或Reflector来查看。 这是什么导致你的“访问被拒绝”的错误。

编辑:

我仔细看了一下这个,看起来好像不是抛出拒绝访问错误的.NET。 考虑以下测试代码:

 using System; using System.IO; using System.Runtime.InteropServices; namespace ReadOnlyDirTest { class Program { [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true, BestFitMapping = false)] extern static bool RemoveDirectory(string path); static String CreateTempDir() { String tempDir; do { tempDir = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName()); } while (Directory.Exists(tempDir)); Directory.CreateDirectory(tempDir); return tempDir; } static void Main(string[] args) { var tempDir = CreateTempDir(); // Set readonly. new DirectoryInfo(tempDir).Attributes |= FileAttributes.ReadOnly; try { Directory.Delete(tempDir); } catch (Exception e) { Console.WriteLine("Directory.Delete: " + e.Message); } if (!Directory.Exists(tempDir)) Console.WriteLine("Directory.Delete deleted directory"); try { if (!RemoveDirectory(tempDir)) Console.WriteLine("RemoveDirectory Win32 error: " + Marshal.GetLastWin32Error().ToString()); } catch (Exception e) { Console.WriteLine("RemoveDirectory: " + e.Message); } if (!Directory.Exists(tempDir)) Console.WriteLine("RemoveDirectory deleted directory"); // Try again without readonly, for both. tempDir = CreateTempDir(); Directory.Delete(tempDir); Console.WriteLine("Directory.Delete: removed normal directory"); tempDir = CreateTempDir(); if (!RemoveDirectory(tempDir)) Console.WriteLine("RemoveDirectory: could not remove directory, error is " + Marshal.GetLastWin32Error().ToString()); else Console.WriteLine("RemoveDirectory: removed normal directory"); Console.ReadLine(); } } } 

在我的机器上运行(赢得7)我得到以下输出:

     Directory.Delete:访问路径“C:\ ... \ Local \ Temp \ a4udkkax.jcy”被拒绝。
     RemoveDirectory Win32错误:5
     Directory.Delete:删除正常的目录
     RemoveDirectory:删除正常的目录

我们看到我们得到错误代码5,根据http://msdn.microsoft.com/en-gb/library/windows/desktop/ms681382(v=vs.85).aspx ,是一个访问被拒绝的错误。

然后,我可以只假定资源管理器在删除一个目录之前取消只读属性,这当然很容易完成。 命令rmdir还会删除标记为只读的目录。

正如文档所建议的只读标志应该是不尊重目录(即使它似乎在Win 7中),我不会依赖这种行为。 换句话说,我不会依靠只读来防止任何事情。

它不。 剥离足够的图层,并且您会发现用于更改目录上的属性的函数是SetFileAttributes

设置文件或目录的属性。

并注意:

FILE_ATTRIBUTE_READONLY 1(0x1)一个只读的文件。 应用程序可以读取文件,但不能写入或删除它。 这个属性不符合目录 。 有关详细信息,请参阅“无法查看或更改Windows server 2003,Windows XP或Windows Vista中的文件夹的只读或系统属性。

(我的重点)

文件系统中目录条目的只读属性的用处有限。 大多数用户都希望目录中的所有文件都是只读的。 但是这不是NTFS的工作方式,属性只适用于文件系统对象本身,并不像安全属性那样“继承”。

请注意,资源管理器如何修改该属性在其用户界面中的工作方式,当您将其打开时,它将执行用户所期望的任务,它将使所有文件成为只读而不是在目录本身上设置属性。

但是,是的,它可以工作,它可以防止修改目录对象本身。 所以,如果你在代码中打开它,那么确实会阻止删除目录。 就像它与一个文件一样。