Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/327.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C#:如何检查我是否可以读取和/或删除目录_C#_Access Control_Directory - Fatal编程技术网

C#:如何检查我是否可以读取和/或删除目录

C#:如何检查我是否可以读取和/或删除目录,c#,access-control,directory,C#,Access Control,Directory,我递归地遍历一堆目录。其中一些(如D:\$RECYCLE.BIN\S-1-5-20)给了我一个系统。UnauthorizedAccessException。我想我可以抓住它继续前进,但我宁愿事先弄清楚这一点 所以,当我有一个DirectoryInfo对象时。我怎样才能知道我是否被允许GetDirectories()和可能的Delete()它?我相信你需要编写自己的GetDirectories()方法;它递归地得到它里面的那些 有一篇关于如何做到这一点的好文章,通过一些工作,您可以清理它以使用通用

我递归地遍历一堆目录。其中一些(如D:\$RECYCLE.BIN\S-1-5-20)给了我一个
系统。UnauthorizedAccessException
。我想我可以抓住它继续前进,但我宁愿事先弄清楚这一点


所以,当我有一个
DirectoryInfo
对象时。我怎样才能知道我是否被允许
GetDirectories()
和可能的
Delete()
它?

我相信你需要编写自己的
GetDirectories()
方法;它递归地得到它里面的那些

有一篇关于如何做到这一点的好文章,通过一些工作,您可以清理它以使用通用列表并使其适合您的解决方案

简单地说,System.IO.Directory.GetDirectories()每次遇到这些异常之一时都会失败

大致像这样的代码(从上面复制)应该可以让您开始

    List<String> directories = new List<String>();
    void DirSearch(string sDir) 
    {
        try 
        {
            foreach (string d in Directory.GetDirectories(sDir)) 
            {
                //foreach (string f in Directory.GetFiles(d, txtFile.Text)) 
                //{
                //    
                //}
                // use this to search for files recursivly.
                directories.Add(d);
                DirSearch(d);
            }
        }
        catch (System.Exception excpt) 
        {
            Console.WriteLine(excpt.Message);
        }
    }
列表目录=新列表();
void DirSearch(字符串sDir)
{
尝试
{
foreach(Directory.GetDirectories(sDir)中的字符串d)
{
//foreach(Directory.GetFiles(d,txtFile.Text)中的字符串f)
//{
//    
//}
//使用此选项可递归搜索文件。
目录。添加(d);
DirSearch(d);
}
}
捕获(系统异常excpt)
{
控制台写入线(除消息外);
}
}

一旦你有了目录列表,你就可以对它们执行操作,使用一些MOD,上述方法应该确保你对列表中的任何内容都有读取权限。

如果你想删除它,尝试删除它,然后继续(根据需要处理异常)


如果您先执行检查,然后执行删除,如果您应该能够删除,那么文件系统上就有可能出现争用情况,尽管这种情况很轻微。这适用于大多数文件/目录访问操作。大多数文件系统操作都被设计为原子操作,将此逻辑移动到用户代码中会与此原子性冲突,并且仍然需要处理可能引发的异常。请看它是否有帮助:

//using System.IO;
//using System.Security.AccessControl;
//using System.Security.Principal;

string[] directories = Directory.GetDirectories(
    Path.Combine(Environment.CurrentDirectory, @"..\.."), 
    "*", SearchOption.AllDirectories);
foreach (string directory in directories)
{
    DirectoryInfo info = new DirectoryInfo(directory);
    DirectorySecurity security = info.GetAccessControl();
    Console.WriteLine(info.FullName);
    foreach (FileSystemAccessRule rule in 
             security.GetAccessRules(true, true, typeof(NTAccount)))
    {
        Console.WriteLine("\tIdentityReference = {0}", rule.IdentityReference);
        Console.WriteLine("\tInheritanceFlags  = {0}", rule.InheritanceFlags );
        Console.WriteLine("\tPropagationFlags  = {0}", rule.PropagationFlags );
        Console.WriteLine("\tAccessControlType = {0}", rule.AccessControlType);
        Console.WriteLine("\tFileSystemRights  = {0}", rule.FileSystemRights );
        Console.WriteLine();
    }
}
结果:

D:\Projects\ConsoleApplication1\bin IdentityReference = BUILTIN\Administrators InheritanceFlags = ContainerInherit, ObjectInherit PropagationFlags = None AccessControlType = Allow FileSystemRights = FullControl D:\Projects\ConsoleApplication1\bin IdentityReference=BUILTIN\Administrators InheritanceFlags=ContainerInherit,ObjectInherit PropagationFlags=None AccessControlType=Allow FileSystemRights=FullControl
请注意,
IdentityReference
FileSystemRights
属性;在尝试删除目录之前,您可能应该对当前ACL进行测试。

同意……另外,在删除之前检查每个文件夹的删除权限似乎比处理偶尔出现的异常(如果没有删除权限是异常而不是规则)会对性能造成很大影响。问题是,我首先获取目录,然后对所有这些目录调用相同的方法。然后我检查目录是否为空,如果为空,我尝试将其删除。换句话说,它首先是读取,然后可能是删除,这取决于目录是否仍然为空。@pjabbott,我想这是一个很好的观点。也许我会处理这个异常。我可能应该这样做……我不经常使用windows安全性(好的,一点也不),因此您能否详细说明如何检查当前用户(WindowsIdentity.GetCurrent())是否可以从目录中删除文件?非常感谢你的帮助