Your basic ITPro blog... What's going on at work, what I'm interested in.

Thursday, May 15, 2008

2008-05-15 PowerShell Exercise

UPDATE! Again, MoW shows me that I tend to make things a bit too complicated. Here he is turning my two-line script into a cool one-liner. I spent a few minutes trying to create a one-liner, but didn't get to it. But then, that's why I love reading MoW's blog! Whenever you can, learn from the master!

MoW's One Liner: del *.* -Exclude (dir | sort creationtime -desc)[0] -whatif

-------------------------
Today's Scripting Guys column shows the questioner how to delete all the files from a folder, except for the most-recently created file. Once again, this is the type of file-management solution that PowerShell is great for. In fact, I am guessing my solution is even more complex than it needs to be. But, this just speaks to my novice-ness. Still, PoSH beats VBScript once again!

Question

Hey, Scripting Guy! I have a folder that has about 50 files in it. How can I delete all those files except the one most-recently created?
-- GA

Hey, Scripting Guy! Solution

strComputer = "."

Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")

Set colFiles = objWMIService.ExecQuery _
    ("ASSOCIATORS OF {Win32_Directory.Name='C:\Logs'} Where " _
        & "ResultClass = CIM_DataFile")

dtmCurrentDate = #1/1/1980 8:00 AM#

For Each objFile In colFiles
    dtmFileDate = WMIDateStringToDate(objFile.CreationDate)
    If dtmFileDate > dtmCurrentDate Then   
        If strLatestFile <> "" Then
            strLatestFile = Replace(strLatestFile, "\", "\\")
            Set colOldFiles = objWMIService. _
                ExecQuery("Select * From CIM_DataFile Where Name = '" & strLatestFile & "'")

            For Each objOldFile in colOldFiles
                objOldFile.Delete
            Next
        End If

        strLatestFile = objFile.Name
        dtmCurrentDate = dtmFileDate
    Else
        objFile.Delete
    End If
Next

Function WMIDateStringToDate(dtmCreationDate)
    WMIDateStringToDate = CDate(Mid(dtmCreationDate, 5, 2) & "/" & _
        Mid(dtmCreationDate, 7, 2) & "/" & Left(dtmCreationDate, 4) _
            & " " & Mid (dtmCreationDate, 9, 2) & ":" & _
                Mid(dtmCreationDate, 11, 2) & ":" & Mid(dtmCreationDate, _
                    13, 2))
End Function

My PowerShell Solution

$files = Get-ChildItem | Sort-Object CreationTime -Descending
for ($x=1;$x -le $files.Count - 1; $x++) {Remove-Item $files[$x] -WhatIf}

NOTE: Remove the -WhatIf if you want to actually delete the files. This is another great PoSH feature. Most cmdlets have the -WhatIf tag. So, you can run the commend and see what it would do, without actually doing it. This is great to destructive cmdlets... such as Remove-Item.

No comments:

Additional Info

My photo
email: support (AT) mangrumtech (DOT) com
mobile: 480-270-4332