【问题标题】:Powershell, Set-Acl, How to sort users to folders and apply permissions oncePowershell,Set-Acl,如何将用户排序到文件夹并应用权限一次
【发布时间】:2015-01-27 21:18:32
【问题描述】:

我正在尝试对一个非常大的文件夹树(多个服务器/共享)应用权限。我的脚本可以运行,但效率不高,而且运行时间太长,因为它是基于每个用户和每个文件夹设置的。

我有一个包含三列用户 ID、路径和偏移量的 csv 文件。下面的例子

Domain\OneUser,\\\Server\Share\1\2\3\4\5\6,5<BR>
Domain\TwoUser,\\\Server\Share\1\2\3\4\5\6,5<BR>
Domain\OneUser,\\\Server\Share\1\2\A\B\C\D,5<BR>
Domain\ThreeUser,\\\Server\Share\1\2\A\B\C,5<BR>
Domain\TwoUser,\\\Server\Share\1\2\3\4\5,5

脚本读取文件,然后使用偏移量设置每个对象的权限。在此示例中,偏移量为 5,这将使脚本在 1 处停止。它还会忽略路径中的最后一个文件夹。

在上述情况下,OneUser 将设置为 5、4、3、2、1。然后将 TwoUser 设置为 5、4、3、2、1。然后 OneUser 将设置在 C、B、A、2、1 上。其中一些是重复工作,如第 3 行(在已设置后设置为 2 和 1)。

我不需要为每个单独的文件夹设置权限,而是需要将它组合在一起,以便它可以像这样设置它,而不是设置权限 23 次,这可以在 8 中完成。

OneUser,Twouser on 5,4,3<BR>
OneUser on C<BR>
OneUser,ThreeUser on B,A<BR>
OneUser,TwoUser,ThreeUser on 2,1

我想做以下两件事之一:

  1. 将列表导出为 csv,如下所示:

    OneUser;Twouser,\\Server\Share\1\2\3\4\5 OneUser;Twouser,\\Server\Share\1\2\3\4\

等等。

或者使用下面的脚本,对于每组唯一的文件夹/用户,修改 $objACE 和 $objACL 以包含每个文件夹的唯一用户

$objACE1 = New-Object System.Security.AccessControl.FileSystemAccessRule(**Domain\OneUser**, $colRights, $InheritanceFlag, $PropagationFlag, $objType<BR>) 
$objACE2 = New-Object System.Security.AccessControl.FileSystemAccessRule(**Domain\TwoUser**, $colRights, $InheritanceFlag, $PropagationFlag, $objType) 
$objACL.AddAccessRule($objACE1)<BR>
$objACL.AddAccessRule($objACE2)

本质上,我需要在每个文件夹调用 Set-Acl 之前为每个文件夹添加所有对象,因此我只为每个文件夹应用一次权限。我还需要排除结束文件夹(权限已经存在)并告诉它在哪里停止。

有人对如何轻松完成此任务有任何想法吗?

这部分脚本是最重要的,包含我设置适当权限所需的所有设置。

#parameters for setting proper traverse/list access to 'This folder only' of parent tree
$colRights = [System.Security.AccessControl.FileSystemRights]"ReadAndExecute,Synchronize" 

#turns off inheritance for this permission
$InheritanceFlag = [System.Security.AccessControl.InheritanceFlags]::None 

#ensures 'this folder only' setting of permissions - will not force propogation
$PropagationFlag = [System.Security.AccessControl.PropagationFlags]::None 

#specifies that this is an allow access type
$objType = [System.Security.AccessControl.AccessControlType]::Allow 

#reads in group/user from csv file to grant permissions for
$objUser = New-Object System.Security.Principal.NTAccount($UserName) 

#builds the new access control to program on parent folders
$objACE = New-Object System.Security.AccessControl.FileSystemAccessRule($objUser, $colRights, $InheritanceFlag, $PropagationFlag, $objType) 

#reads in current access control of current parent folder
$objACL = Get-ACL $Container 

#adds the access rule to current access controls of the current parent folder
$objACL.AddAccessRule($objACE) 

#writes out screen feedback on current status of the script
write-host Setting permissions on $Container for $Username

#Sets access controls on each applicable folder.  This does not affect existing permissions, only adds to them.
Set-ACL $container $objACL 

【问题讨论】:

  • 请退后一步,描述您要解决的实际问题,而不是您认为的解决方案。你想通过这样做来达到什么目的?你需要那个“偏移量”做什么?为什么不能简单地设置文件夹上 5 级的权限,其余的留给继承?

标签: powershell csv permissions


【解决方案1】:

好的,我的建议是制作一个哈希表来更好地组织您的信息。将您的密钥设置为文件夹,并将值设置为需要访问该文件夹的用户。通过解析 CSV 每一行上的文件夹并遍历它们,您可以构建文件夹列表。然后为每个文件夹检查它是否在哈希表中并将用户添加到该密钥,或者在需要时创建一个新密钥。然后遍历文件夹,并为每个文件夹添加一个 ACL 规则到哈希表中为该文件夹列出的每个用户的 ACL 对象。这是我将用来执行此操作的代码:

$Import = Import-Csv "C:\Path\To\File.csv"
$AllPaths = @{}
$Import | ?{$_.path -match "^(\\.*?)\\[^\\]*$"}|%{
    $Subs = $Matches[1].split('\')|Where{![string]::IsNullOrEmpty($_)}
    $RootPath = $Subs[0..($Subs.count - $_.Offset - 1)]
    For($i=[int]($Subs.count - 1);$i -ge ($Subs.count - $_.Offset);$i--){
        $CurPath = "\\{0}\{1}" -f ($RootPath -join '\'),($Subs[($RootPath.count)..$i] -join '\')
        If($AllPaths.Keys -contains $CurPath -and $AllPaths[$CurPath] -notcontains $_.User){
            $AllPaths[$CurPath]+=$_.User
        }elseif($AllPaths.Keys -notcontains $CurPath){
            $AllPaths.Add($CurPath,@($_.User))
        }
    }
}

ForEach($Container in $AllPaths.Keys){

    #parameters for setting proper traverse/list access to 'This folder only' of parent tree
    $colRights = [System.Security.AccessControl.FileSystemRights]"ReadAndExecute,Synchronize" 

    #turns off inheritance for this permission
    $InheritanceFlag = [System.Security.AccessControl.InheritanceFlags]::None 

    #ensures 'this folder only' setting of permissions - will not force propogation
    $PropagationFlag = [System.Security.AccessControl.PropagationFlags]::None 

    #specifies that this is an allow access type
    $objType = [System.Security.AccessControl.AccessControlType]::Allow 

    #reads in current access control of current parent folder
    $objACL = Get-ACL $Container 

    #Add an access rule for each user needing access to this folder to the ACL before writing the ACL back to the folder
    ForEach($UserName in $AllPaths[$Container]){

        #reads in group/user from csv file to grant permissions for
        $objUser = New-Object System.Security.Principal.NTAccount($UserName) 

        #builds the new access control to program on parent folders
        $objACE = New-Object System.Security.AccessControl.FileSystemAccessRule($objUser, $colRights, $InheritanceFlag, $PropagationFlag, $objType) 

        #adds the access rule to current access controls of the current parent folder
        $objACL.AddAccessRule($objACE) 
    }

    #writes out screen feedback on current status of the script
    write-host "Setting permissions on $Container for $($AllPaths[$Container].Values -join ", ")"

    #Sets access controls on each applicable folder.  This does not affect existing permissions, only adds to them.
    Set-ACL $container $objACL 
}

使用您的示例数据,我能够编译以下文件夹列表,以及需要访问这些文件夹的相关用户:

PS C:\windows\system32> $AllPaths|ft -AutoSize

Name                     Value                                             
----                     -----                                             
\\Server\Share\1\2\3\4\5 {Domain\OneUser, Domain\TwoUser}                  
\\Server\Share\1\2\A     {Domain\OneUser, Domain\ThreeUser}                
\\Server\Share\1\2       {Domain\OneUser, Domain\TwoUser, Domain\ThreeUser}
\\Server\Share\1\2\A\B   {Domain\OneUser, Domain\ThreeUser}                
\\Server\Share\1         {Domain\OneUser, Domain\TwoUser, Domain\ThreeUser}
\\Server\Share\1\2\3\4   {Domain\OneUser, Domain\TwoUser}                  
\\Server\Share\1\2\3     {Domain\OneUser, Domain\TwoUser}                  
\\Server\Share\1\2\A\B\C {Domain\OneUser}                                  
\\Server\Share           {Domain\ThreeUser, Domain\TwoUser}    

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-08-13
    • 1970-01-01
    • 1970-01-01
    • 2015-05-15
    • 2019-03-09
    • 2020-09-05
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多