众所周知,您可以在复制文件夹的属性中以文件掩码的形式配置例外-然后该服务将不会复制与指定掩码匹配的文件。 但是并非所有人都知道文件具有“临时”属性,并且DFSR并非通过设计来处理此类文件。 如果不考虑这一点,尽管服务日志中的所有内容都会变得干净漂亮,但DFSR文件夹的内容可能会变得不同步,并且可能在最不适当的时刻出现。 问题本身及其解决方案已在Internet上进行了不止一次的分析,本文的目的是完成更早创建的解决方案,从而为其增加灵活性和便利性。 与谁相关-我在猫之下问。
Internet上已经多次讨论了该主题,例如,
官方博客 ,
此处和
Habré本身 。 因此,我不会重复自己,但我会直截了当。 原始解决方案是PowerShell脚本,该脚本可为给定文件夹中的所有文件重置“临时”属性。 以它为基础,我编写了自己的版本,该版本在目标服务器上找到复制的文件夹,并遍历每个文件夹,重置问题属性,然后将有关找到的文件的报告发送至电子邮件。 还增加了对
长路径的支持(需要PowerShell的第5版)。
为了使脚本正常工作,您需要DFS服务管理工具(默认情况下,它们与DFS复制角色一起安装)。 如果它们在目标服务器上不可用,请运行以下cmdlet:
Install-WindowsFeature RSAT-DFS-Mgmt-Con
这是脚本本身:
TempAttrFixer.ps1 Param( # [parameter(Mandatory=$false)][String]$OutDir ) $SMTPServer = "mail.mydomain.com" $MailFrom = "sender@mydomain.com" $MailTo = "recipient@mydomain.com" Function ConvertTo-LiteralPath { # LiteralPath Param( [parameter(Mandatory=$true)][String]$Path ) # UNC If ($Path.Substring(0,2) -eq "\\") { Return ("\\?\UNC" + $Path.Remove(0,1)) } Else { Return "\\?\$Path" } } $StartTime = Get-Date $Error.Clear() If (!$OutDir) { $OutDir = (Get-WmiObject Win32_OperatingSystem).SystemDrive +"\TempAttrFixer_Report" } # , $FoldersToScan = @(Get-DfsrMembership -ComputerName $env:COMPUTERNAME | Sort-Object GroupName, FolderName).ContentPath $LogFileName = "$env:COMPUTERNAME" + "_TempFiles_" + (Get-Date -Format "yyyy-MM-dd-HH-mm-ss") + ".csv" $LogFilePath = "$OutDir\$LogFileName" $Delimiter = "`t" $FilesCount = 0 If (!(Test-Path $OutDir -PathType Container)) { New-Item -ItemType Directory -Force -Path $OutDir | Out-Null } ForEach ($Folder in $FoldersToScan) { # PowerShell 5.1, LireralPath Write-Output "Scanning `"$Folder`"..." Get-ChildItem -LiteralPath (ConvertTo-LiteralPath $Folder) -Recurse | ForEach-Object -Process { if (($_.Attributes -band 0x100) -eq 0x100) { $FilesCount += 1 $Entry = $_.FullName + $Delimiter + $_.GetAccessControl().Owner + "`r`n" $Entry $Entry | Out-File -FilePath $LogFilePath -Encoding unicode -Append -NoNewline $_.Attributes = ($_.Attributes -band 0xFEFF) } } } $FinishTime = Get-Date $TimeSpan = $FinishTime - $StartTime Write-Output ("Done, errors: " + $Error.Count) $Encoding = [System.Text.Encoding]::Unicode If ($FilesCount -gt 0) { $MessageBody = $null $Subject = " " $MessageBody += " : $env:COMPUTERNAME`r`n" $MessageBody += " : " + $TimeSpan.ToString() + "`r`n" $MessageBody += " `"$LogFilePath`"`r`n" Send-MailMessage -SmtpServer $SMTPServer -From $MailFrom -Subject $Subject -Encoding $Encoding -To $MailTo -Body $MessageBody -Attachments $LogFilePath } Else { $MessageBody = $null $Subject = " " $MessageBody += " : $env:COMPUTERNAME`r`n" $MessageBody += " : " + $TimeSpan.ToString() + "`r`n" Send-MailMessage -SmtpServer $SMTPServer -From $MailFrom -Subject $Subject -Encoding $Encoding -To $MailTo -Body $MessageBody } #, - If ($Error.Count -gt 0) { $MessageBody = $null $Subject = " " $MessageBody += " : $env:COMPUTERNAME`r`n" $MessageBody += " : $env:UserName`r`n" $MessageBody += " :`r`n" $MessageBody += $Error[0] Send-MailMessage -SmtpServer $SMTPServer -From $MailFrom -Subject $Subject -Encoding $Encoding -To $MailTo -Body $MessageBody }
我们更正了负责电子邮件警报的变量的值,并将脚本添加到调度程序中:
powershell.exe -NoLogo -ExecutionPolicy Bypass -NoProfile -File "< >\TempAttrFixer.ps1"
从SYSTEM内运行任务最简单,但是如果您
的妄想症程度有所提高,并且已采取认真的信息安全方法,则可以使用一个单独的帐户,使其具有作为批处理作业登录的权限以及修改已复制文件夹中文件的权限。
您可以配置脚本以与zabbix或其他监视系统交互,而不是电子邮件报告(或附加报告)。 同样重要的是要了解该过程非常耗费资源,因此不要过于频繁地运行它。 处理10TB的数据大约需要一个小时,并且脚本每天晚上运行一次。
我和我的同事对具有临时属性的文件来自何处的问题很感兴趣。 因此,在每个报告中,连同文件的全名一样,将显示其NTFS所有者。 根据收集的数据,有可能发现在我们这种情况下,当从通过RDP转发的本地磁盘复制数据时,有时会将属性添加到文件中(我们正在积极使用远程桌面技术)。 但是文件最初可能是“有缺陷的”。 到目前为止,还没有找到更详细的信息。
如果您通过了简短的调查并在评论中分享您的经验,我将不胜感激。