在执行md5指纹时如何忽略不可用(损坏)的文件?

时间:2017-11-22 02:10:18

标签: windows powershell

下面的代码生成了md5和其他元数据指纹,但是在未知损坏的文件上崩溃(例如,文件,可以复制,大多数甚至打开,但不能进行散列或压缩[以掩盖其损坏] )。

问题:如何让这段代码跳过或忽略任何问题文件而只做其余的事情?想象一下8 TB的100万个文件。

Get-childitem -recurse -file | 
  Select-object @{n="Hash";e={get-filehash -algorithm MD5 -path $_.FullName |
  Select-object -expandproperty Hash}},lastwritetime,length,fullname |
  Export-csv "$((Get-Date).ToString("yyyyMMdd_HHmmss"))_filelistcsv_MD5_LWT_size_path_file.csv" -notypeinformation

1 个答案:

答案 0 :(得分:1)

试试这个:

$errLogPath = "$((Get-Date).ToString("yyyyMMdd_HHmmss"))_filelistcsv_MD5_LWT_size_path_file_ERROR.csv"

Get-childitem -recurse -file | 
  foreach-object {

    $file = $_

    try {
        $hash = Get-FileHash -Algorithm MD5 -path $file.FullName -ErrorAction Stop
        $file | Add-Member -MemberType NoteProperty -Name Hash -Value $hash.Hash -PassThru
    } catch {
        $file | 
            add-Member -MemberType NoteProperty -Name Exception -Value $_.Exception.Message -PassThru |
            Select-Object -Property Name, FullName, Exception |
            Export-Csv -Path $errLogPath -append -notypeinformation
    }
  } | 
  select-object -Property Hash, LastWriteTime, Length, FullName |
  Export-csv "$((Get-Date).ToString("yyyyMMdd_HHmmss"))_filelistcsv_MD5_LWT_size_path_file.csv" -notypeinformation

通过foreach-object cmdlet处理每个文件。 try...catch用于捕获异常,-ErrorAction Stop参数添加到get-FileHash以确保终止错误并触发捕获。

如果捕获到错误,则会将文件名,路径和异常消息输出到CSV文件。

编辑:添加进度条

$logPath = "$((Get-Date).ToString("yyyyMMdd_HHmmss"))_filelistcsv_MD5_LWT_size_path_file.csv"
$errLogPath = "$((Get-Date).ToString("yyyyMMdd_HHmmss"))_filelistcsv_MD5_LWT_size_path_file_ERROR.csv"

write-host "Counting files ..."

$maxFileCount = 0; get-childItem -recurse -file | % { $maxFileCount +=1 }

write-host "Hashing files ..."

$currFileCount = 0
Get-childitem -recurse -file | 
  foreach-object {

    $file = $_

    Write-Progress -Activity "Hashing Files" -Status ( "{0}/{1} - {2}" -f $currFileCount, $maxFileCount, $File.FullName ) -PercentComplete (($currFileCount++)/$maxFileCount*100)

    try {
        $hash = Get-FileHash -Algorithm MD5 -path $file.FullName -ErrorAction Stop
        $file | Add-Member -MemberType NoteProperty -Name Hash -Value $hash.Hash -PassThru
    } catch {
        $file | 
            add-Member -MemberType NoteProperty -Name Exception -Value $_.Exception.Message -PassThru |
            Select-Object -Property Name, FullName, Exception |
            Export-Csv -Path $errLogPath -append -notypeinformation
    }


  } | 
  select-object -Property Hash, LastWriteTime, Length, FullName |
  Export-csv -Path $logPath -notypeinformation