在深层文件夹遍历中使用NTFSSecurity模块的Powershell内存耗尽

时间:2017-02-09 18:51:12

标签: powershell acl ntfs

我的任务是报告共享驱动器结构中每个文件夹的所有ACL。除此之外,我还需要查看返回的每个唯一组的成员资格。

我将NTFSSecurity模块与get-childitem2 cmdlet结合使用,以超过260个字符的路径长度限制。我遍历的路径是深度和长度的数百个文件夹,因为它超过了260个字符的限制。

我一直在敲打这个问题几个星期。我的第一个挑战是制作我的脚本来同时完成我的任务,但现在我认为这是我的问题......手头的问题是资源,特别是内存耗尽。一旦脚本进入其中一个深层文件夹,它就会消耗所有RAM并开始交换到磁盘,最终我的磁盘空间不足。

这是脚本:

$csvfile = 'C:\users\user1\Documents\acl cleanup\dept2_Dir_List.csv'

foreach ($record in Import-Csv $csvFile)
{

$Groups = get-childitem2 -directory -path $record.FullName -recurse | Get-ntfsaccess | where -property accounttype -eq -value group
$groups2 = $Groups | where -property account -notmatch -value '^builtin|^NT AUTHORITY\\|^Creator|^AD\\Domain'
$groups3 = $groups2 | select account -Unique

 $GroupMembers = ForEach ($Group in $Groups3) {
    (Get-ADGroup $Group.account.sid | get-adgroupmember | select Name, @{N="GroupName";e={$Group.Account}}

)}
$groups2 | select FullName,Account,AccessControlType,AccessRights,IsInherited | export-csv "C:\Users\user1\Documents\acl cleanup\Dept2\$($record.name).csv"
$GroupMembers | export-csv "C:\Users\user1\Documents\acl cleanup\Dept2\$($record.name)_GroupMembers.csv"
}   

注意:它读入的目录列表是从get-childitem2 -directory创建的顶级文件夹。 export-csv filename.csv

在运行期间,似乎没有正确刷新内存。这只是观察的猜测。在每次运行代码结束时,我认为变量应该被覆盖,但是内存不会下降,所以在我看来,由于内存没有回落,它没有正确释放它?就像我说的那样,猜测......我一直在阅读有关运行空间的内容,但我对如何使用此脚本实现它感到困惑。这是正确的方向吗?

提前感谢您的任何帮助......!

1 个答案:

答案 0 :(得分:0)

有趣的是你应该发布这个,因为我刚刚完成了我认为更好的脚本的修改版本。一位朋友转过身去了功能过滤器'这似乎在这里运作良好。我明天会在大目录上测试它,看看内存管理有多好,但到目前为止看起来很棒。

    #Define the function ‘filter’ here and call it ‘GetAcl’. Process is the keyword that tells the function to deal with each item in the pipeline one at a time
Function GetAcl {

            PROCESS {
            Get-NTFSAccess $_  | where -property accounttype -eq -value group | where -property account -notmatch -value '^builtin|^NT AUTHORITY\\|^Creator|^AD\\Domain'
                    }
                } 

#Import the directory top level paths
$Paths = import-csv 'C:\users\rknapp2\Documents\acl cleanup\dept2_Dir_List.csv'

#Process each line from the importcsv one at a time and run GetChilditem against it. 
#Notice the second part – I ‘|’ pipe the results of the GetChildItem to the function that because of the type of function it is, handles each item one at a time
#When done, pass results to Exportcsv and send it to a file name based on the path name. This puts each dir into its own file.
 ForEach ($Path in $paths) {
 (Get-ChildItem2 -path $path.FullName -Recurse -directory) | getacl | export-csv "C:\Users\rknapp2\Documents\acl cleanup\TestFilter\$($path.name).csv" }