C# - 在Windows 7中为所有用户设置目录权限

14

这应该是一个相当简单的问题,但出于某些原因,我似乎无法使其起作用。我想做的只是将给定目录的权限设置为允许所有用户完全访问。目前我拥有以下代码:

System.IO.DirectoryInfo di = new System.IO.DirectoryInfo(destinationDirectory);
FileSystemAccessRule fsar = new FileSystemAccessRule("Users", FileSystemRights.FullControl, AccessControlType.Allow);
DirectorySecurity ds = null;

    if (!di.Exists)
    {
       System.IO.Directory.CreateDirectory(destinationDirectory);
    }

ds = di.GetAccessControl();
ds.AddAccessRule(fsar);

没有任何异常被抛出,但也没有发生任何事情。当我在代码运行后检查目录权限时,我发现没有任何更改。

有任何想法吗?


你尝试过禁用UAC运行上述代码吗? - rkosegi
1
@David - 我已经尝试以管理员身份运行编译后的exe文件,但结果没有任何改变。 - Sonny Boy
@rkosegi - 我该怎么做?这是在Visual Studio中的一个设置吗? - Sonny Boy
2
@SonnyBoy 不,这是一个系统级别的设置,你不应该禁用它。如果你禁用了它,那么当你的用户运行你的代码时发现由于缺乏权限而失败时,你会感到非常惊讶。最好不要有这样的意外。 - David Heffernan
2个回答

33

您还需要调用SetAccessControl来应用更改。

ds = di.GetAccessControl();
ds.AddAccessRule(fsar);
di.SetAccessControl(ds); // nothing happens until you do this

看起来MSDN上的示例缺乏细节,正如这里所讨论的那样。我从这篇文章中改编了代码,得到以下表现良好的代码:


static bool SetAcl()
{
    FileSystemRights Rights = (FileSystemRights)0;
    Rights = FileSystemRights.FullControl;

    // *** Add Access Rule to the actual directory itself
    FileSystemAccessRule AccessRule = new FileSystemAccessRule("Users", Rights,
                                InheritanceFlags.None,
                                PropagationFlags.NoPropagateInherit,
                                AccessControlType.Allow);

    DirectoryInfo Info = new DirectoryInfo(destinationDirectory);
    DirectorySecurity Security = Info.GetAccessControl(AccessControlSections.Access);

    bool Result = false;
    Security.ModifyAccessRule(AccessControlModification.Set, AccessRule, out Result);

    if (!Result)
        return false;

    // *** Always allow objects to inherit on a directory
    InheritanceFlags iFlags = InheritanceFlags.ObjectInherit;
    iFlags = InheritanceFlags.ContainerInherit | InheritanceFlags.ObjectInherit;

    // *** Add Access rule for the inheritance
    AccessRule = new FileSystemAccessRule("Users", Rights,
                                iFlags,
                                PropagationFlags.InheritOnly,
                                AccessControlType.Allow);
    Result = false;
    Security.ModifyAccessRule(AccessControlModification.Add, AccessRule, out Result);

    if (!Result)
        return false;

    Info.SetAccessControl(Security);

    return true;
}

2
接近了。现在将“users”更改为“Everyone”,已将“Everyone”组添加到文件夹中,但权限为空;没有授予任何权限。 - Sonny Boy
@Dinesh 目录和文件以相同的方式处理。 - David Heffernan
那段代码很棒 - 很高兴我找到它,而你也努力完善它。不然我真不敢想象要花多长时间解决这个问题。 - From Orbonia
2
这是非常尴尬的代码。这个简单得多:https://dev59.com/O2ox5IYBdhLWcg3wl1T4?answertab=active#tab-top - Elmue
1
@Elmue 那个解决方案对我不起作用 - “所有用户”没有获得完全控制权。然而,这个答案和Timothée Lecomte的答案是有效的(显然是由于2阶段权限设置)。 - Alonzzo2
显示剩余7条评论

19

David Heffernan的答案在非英语环境的计算机上无法工作,在尝试设置“Users”的权限时会出现IdentityNotMapped异常。以下代码将在任何地方都可以工作,它使用WellKnownSidType.BuiltinUsersSid代替:

static void SetFullControlPermissionsToEveryone(string path)
{
    const FileSystemRights rights = FileSystemRights.FullControl;

    var allUsers = new SecurityIdentifier(WellKnownSidType.BuiltinUsersSid, null);

    // Add Access Rule to the actual directory itself
    var accessRule = new FileSystemAccessRule(
        allUsers,
        rights,
        InheritanceFlags.None,
        PropagationFlags.NoPropagateInherit,
        AccessControlType.Allow);

    var info = new DirectoryInfo(path);
    var security = info.GetAccessControl(AccessControlSections.Access);

    bool result;
    security.ModifyAccessRule(AccessControlModification.Set, accessRule, out result);

    if (!result)
    {
        throw new InvalidOperationException("Failed to give full-control permission to all users for path " + path);
    }

    // add inheritance
    var inheritedAccessRule = new FileSystemAccessRule(
        allUsers,
        rights,
        InheritanceFlags.ContainerInherit | InheritanceFlags.ObjectInherit,
        PropagationFlags.InheritOnly,
        AccessControlType.Allow);

    bool inheritedResult;
    security.ModifyAccessRule(AccessControlModification.Add, inheritedAccessRule, out inheritedResult);

    if (!inheritedResult)
    {
        throw new InvalidOperationException("Failed to give full-control permission inheritance to all users for " + path);
    }

    info.SetAccessControl(security);
}

我能更改“网络文件夹”吗,例如\server\folder1\subfolder1\subfolder2 - Kiquenet

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接