Search code examples
powershellloopsdirectoryrename

Include folder name in file name as part of a loop


I try to get the directory name as part of a filename. The problem is that I want to do this for each file in a different separate folder, which does not seem to work.

What I have come to thus far is that I am able to get a list of subfolders ($GetAllActionTargetSubFolders) that each contain one or more files. In each of the subfolders, the files are combined into one file with the name 'temp'. Now, what does not work is, I want to rename this combined 'temp' file that is in each of the subfolders and want to include the subfolder name as such: FoldernameA_Consolidated202209161304.rpt (instead of temp.rpt)

I thought that the '$_.Directory.Name' would give me the directory name, but then I get this error message:

Rename-Item : Could not find a part of the path.
At line:5 char:125
+ ... de *temp* | Rename-Item  -NewName {$_.Directory.Name + "_Consolidated ...
+                 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : WriteError: (\\networkdrive\R...ctions\temp.rpt:String) [Rename-Item], DirectoryNotFoundException
    + FullyQualifiedErrorId : RenameItemIOError,Microsoft.PowerShell.Commands.RenameItemCommand

This is the script that I have thus far:

#get a list of all sub directories:

$ActionTargetFolder = "\\networkdrive\2_ActionData_Prep\"
$GetAllActionTargetSubFolders = Get-ChildItem -Path $ActionTargetFolder -Recurse | Where-Object { $_.PSIsContainer -eq $true} 

#for each sub directory, make 1 file that contains all lines from the files that are in that specific sub directory:

ForEach ($foldername in $GetAllActionTargetSubFolders.FullName) {Get-ChildItem  $foldername -Recurse -File -Include *.rpt | get-content | sort | get-unique | Out-File -FilePath "$($foldername)\temp.rpt"-Force } 

#rename the 'temp' file that is created and include the sub-directory name, text and date/time:

ForEach ($foldername in $GetAllActionTargetSubFolders.FullName) {Get-ChildItem $foldername -Recurse -File -Include *temp* | Rename-Item  -NewName {$_.Directory.Name + "_Consolidated" + $((Get-Date).ToString('yyyyMMddhhmm')) + ".rpt"}} 

I hope someone could help me with this


Solution

  • As Cid already commented, there is no need to create a file with name temp.rpt first and rename it afterwards.

    By naming the file as you want it straight away, you don't need that second loop.

    Also, when using Get-ChildItem and want it to filter for just one extension, you should use -Filter instead of -Include because this works a lot faster.

    Try:

    # get a list of all sub directories:
    $ActionTargetFolder = "\\networkdrive\2_ActionData_Prep\"
    $GetAllActionTargetSubFolders = Get-ChildItem -Path $ActionTargetFolder -Directory -Recurse
    
    # for each sub directory, make 1 file that contains all lines from the files that are in that specific sub directory:
    foreach ($folder in $GetAllActionTargetSubFolders) {
        # create the full path and filename for the output
        $outFile = Join-Path -Path $folder.FullName -ChildPath ('{0}_Consolidated_{1:yyyyMMddHHmm}.rpt' -f $folder.Name, (Get-Date))
        $content = $folder | Get-ChildItem -File -Filter '*.rpt' | Get-Content
        $content | Sort-Object -Unique | Set-Content -Path $outFile
    }