locked
Renaming Subdirectories with Datestamp RRS feed

  • Question

  • I have a main directory that has hundreds of subfolders with varied names. Each subfolder has its own subfolders whose names are dates in the following format:
    M_D_YYYY

    Problems:
    (1) I need the Year to be first, so that folders from different years are in order when sorted by name, i.e. all 2017 folders come before all 2018 folders
    (2) I need Months and dates that are only 1 digit should have a 0 in front of them, so that 2017_04_20 comes after 2017_04_19 and not 2017_4_20 coming after 2017_4_2 when sorted by name.

    So, basically, I need it in the following format:
    YYYY_MM_DD

    What is the best way to solve in Windows 10, either using Power Shell or Bath File.

    Thanks.


    Monday, December 24, 2018 11:21 AM

Answers

  • Try it with dashes instead of backslashes:

    Get-ChildItem d:\test7\* -Directory |
        ForEach-Object{
            # Rename subfolders
            Write-Host $_ -Fore green
            if ($_.BaseName -match '^\d{1,2}_\d{1,2}_\d{4}$') {
                $newname = ([datetime]($_.BaseName -replace '_','-')).ToString('yyyy_MM_dd')
                Rename-Item -Path $_ -NewName $newname -Verbose
            } else {
                Write-Host 'Match Not Found' -Fore yellow
            }
        }
    
    



    \_(ツ)_/


    Monday, December 24, 2018 11:15 PM
  • I think I found it:

    get-childitem -Include 2017_03* -Recurse -force | Remove-Item -Force –Recurse

    • Marked as answer by Phoenix Tech2 Tuesday, December 25, 2018 8:45 AM
    Tuesday, December 25, 2018 8:14 AM

All replies

  • Use Rename-Item and Get-ChildItem

    help rename-item -online

    help get-childitem -online

    Start by getting the root folders:

    Get-ChildItem c:\folders -Directory |
        ForEach-Object{
            # Rename subfolders
            Get-ChildItem $_ -Directory |
                ForEach-Object{
                    if ($_.BaseName -match '^\d{1,2}_\d{1,2}_\d{4}$') {
                        $newname = ([datetime]$_.BaseName).ToString('yyyy_MM_dd')
                        Rename-Item -Path $_ -NewName $newname -Verbose
                    }
                }
        }


    \_(ツ)_/






    • Edited by jrv Monday, December 24, 2018 12:08 PM
    • Proposed as answer by BOfH-666 Monday, December 24, 2018 2:16 PM
    Monday, December 24, 2018 11:58 AM
  • Thanks for the suggestion. But, I am getting an error similar to the following recursively:

    Cannot convert value "5_30_2017" to type "System.DateTime". Error: "String was not recognized as a valid DateTime."
    At C:\f9b\rename_date_folders.ps1:7 char:21
    + ...             $newname = ([datetime]$_.BaseName).ToString('yyyy_MM_dd') ...
    +                 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
        + CategoryInfo          : InvalidArgument: (:) [], RuntimeException
        + FullyQualifiedErrorId : InvalidCastParseTargetInvocationWithFormatProvider

    Rename-Item : Cannot bind argument to parameter 'NewName' because it is null.
    At C:\f9b\rename_date_folders.ps1:8 char:51
    +                     Rename-Item -Path $_ -NewName $newname -Verbose
    +                                                   ~~~~~~~~
        + CategoryInfo          : InvalidData: (:) [Rename-Item], ParameterBindingValidationException
        + FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,Microsoft.PowerShell.Commands.RenameItemC
       ommand

    Any advice?


    Monday, December 24, 2018 1:40 PM
  • Simple:  Use -replace to alter the format.

     ([datetime]($_.BaseName -replace '_','\')).ToString('yyyy_MM_dd')


    \_(ツ)_/

    • Proposed as answer by BOfH-666 Monday, December 24, 2018 2:17 PM
    Monday, December 24, 2018 2:03 PM
  • I changed the line to:

                        $newname = ([datetime]($_.BaseName -replace '_','/')).ToString('yyyy_MM_dd')

    And error similar to this now shows recursively:

    Rename-Item : Cannot rename because item at '5_3_2017' does not exist.
    At C:\f9b\rename_date_folders.ps1:8 char:21
    +                     Rename-Item -Path $_ -NewName $newname -Verbose
    +                     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

    .... when clearly 5_3_2017 does exist.....

    Monday, December 24, 2018 10:54 PM
  • Works fine for me.  What does "error similar" mean.

    \_(ツ)_/

    Monday, December 24, 2018 11:05 PM
  • Try it with dashes instead of backslashes:

    Get-ChildItem d:\test7\* -Directory |
        ForEach-Object{
            # Rename subfolders
            Write-Host $_ -Fore green
            if ($_.BaseName -match '^\d{1,2}_\d{1,2}_\d{4}$') {
                $newname = ([datetime]($_.BaseName -replace '_','-')).ToString('yyyy_MM_dd')
                Rename-Item -Path $_ -NewName $newname -Verbose
            } else {
                Write-Host 'Match Not Found' -Fore yellow
            }
        }
    
    



    \_(ツ)_/


    Monday, December 24, 2018 11:15 PM
  • Thanks for the match not found option, because all the subfolders showed up with this... What I need is the subfolders of the subfolders. So, I changed it to:

    Get-ChildItem c:\f9b\*\* -Directory |

    .... and that seems to have worked....

    Thanks, all!
    Tuesday, December 25, 2018 3:19 AM
  • I have a related question....

    Now that I have renamed all the subfolders of subfolders:

    Is there a quick way to delete all subfolders that begin with 2017_03, including their contents... I am trying using search and manually deleting the results, but it keeps on crashing....


    Tuesday, December 25, 2018 3:50 AM
  • I think I found it:

    get-childitem -Include 2017_03* -Recurse -force | Remove-Item -Force –Recurse

    • Marked as answer by Phoenix Tech2 Tuesday, December 25, 2018 8:45 AM
    Tuesday, December 25, 2018 8:14 AM