-
Notifications
You must be signed in to change notification settings - Fork 8
Expand file tree
/
Copy pathGet-DuplicateFiles.ps1
More file actions
102 lines (76 loc) · 3.34 KB
/
Get-DuplicateFiles.ps1
File metadata and controls
102 lines (76 loc) · 3.34 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
function Get-DuplicateFiles {
<#
.SYNOPSIS
Performs a search for duplicate files in a given directory.
.DESCRIPTION
Performs a search for duplicate files in a given directory.
Items with the first CreationTime are considered originals, regardless of path.
.PARAMETER Path
Specify a path to search for duplicate files in, recursively.
Default starting directory is $ENV:USERPROFILE.
.EXAMPLE
Get-DuplicateFiles -Verbose
Provides start time, time taken, and total files scanned.
.EXAMPLE
Get-DuplicateFiles -Path "C:\Temp" -FullReport
Returns all files checked, including originals. A Status property will contain Original or Duplicate.
.EXAMPLE
Get-DuplicateFiles "C:\Users\MyProfile" | Where-Object {$_.Status -eq "Duplicate"} | Remove-Item
Removes duplicate items found.
.NOTES
Updated: 2018-07-20
Contributing Authors:
Anthony Phipps
LEGAL: Copyright (C) 2018
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
.LINK
https://github.com/TonyPhipps/Powershell
#>
[CmdletBinding()]
param(
[Parameter(ValueFromPipeline = $True, ValueFromPipelineByPropertyName = $True)]
$Path = $ENV:USERPROFILE,
[Parameter()]
[Switch]$FullReport
)
begin{
$DateScanned = Get-Date -Format "yyyy-MM-dd_hh.mm.ss.ff"
Write-Information -InformationAction Continue -MessageData ("Started {0} at {1}" -f $MyInvocation.MyCommand.Name, $DateScanned)
$Stopwatch = New-Object System.Diagnostics.Stopwatch
$Stopwatch.Start()
$Total = 0
}
process{
$FileArray = Get-ChildItem $Path -Recurse -File | Sort-Object CreationTime
$counter = 0
Foreach ($File in $FileArray){
$counter++
Write-Progress -Activity 'Calculating Hashes' -CurrentOperation $File.FullName -PercentComplete (($counter / $FileArray.count) * 100)
$File | Add-Member -MemberType NoteProperty -Name "Hash" -Value (Get-FileHash $File.FullName).Hash
$File | Add-Member -MemberType NoteProperty -Name "Status" -Value "Duplicate"
}
$GroupArray = $FileArray | Group-Object -Property Hash
ForEach ($Group in $GroupArray){
$Group.Group[0].Status = "Original"
}
$ReportArray = $GroupArray.Group
if(!$FullReport){
$ReportArray = $GroupArray.Group | Where-Object {$_.Status -eq "Duplicate"}
}
$Total = $Total + $FileArray.Count
$ReportArray
}
end{
$elapsed = $stopwatch.Elapsed
Write-Verbose ("Total Files Scanned: {0} `t Total time elapsed: {1}" -f $total, $elapsed)
}
}