1

I am trying to rename or remove part of a filename. I have a scheduled job that moves an updated file from one server to another. Once the file is moved it need to be renamed. For example: Filename_01-23-AB.exe to Filename.exe I want to remove everything from the "_" to the "." and leave the extension intact. I found the following code that should do this but I can't seem to get it to work. Am I headed down the right path here?

## Removes the build number from the filename of "Filename_XX-XX-XX.exe" leaving the new filename to be "Filename.exe" ##

$File = -Path "C:\Temp\TestPath\"

foreach ($File in gci *.exe) {
    $Fname = ($File.name).split('.')[0]  ## item before the '.' ##
    $Prefix = $Fname.split('_')[0] ## item before the '_' ##
    $Newname = $Prefix + '.exe'
    Rename-Item $file $Newname 
}

3 Answers 3

1

I've tried simplifying what you're tying to do:

pushd "C:\Temp\TestPath\"
dir | ? { $_.Name -like "*.exe" } | 
% { Rename-Item $_ "$($_.BaseName.split('_')[0])$($_.Extension)" }
popd

First, this changes the directory your PowerShell is looking at to your defined directory (pushd). Then it will get the contents of your directory, find all objects with the extension of .exe, and split the file's base name at the underscore. popd will then set the directory back to where-ever it was previous to running this script.

Sign up to request clarification or add additional context in comments.

Comments

1

I think this can be simplifyed even more using a regex to remove everything between the first underscore and the file extension:

$Path= 'C:\Temp\TestPath\'
Get-ChildItem $Path -Filter "*_*.exe" | foreach {
    $_ | Rename-Item -NewName ($_.Name -replace '(?=_).+(?=\.)')
}

This also works when the filename doesn't contain an underscore.

And here the regex demo.

5 Comments

"hello world".Split("_")[0] -eq 'hello world' :-)
Rename-Item : Source and destination path must be different. At line:3 char:21 + $_ | Rename-Item <<<< -NewName ($_.Name -replace '(?=_).+(?=\.)') + CategoryInfo : WriteError: (C:\Temp\TestPath\.#ext:String) [Rename-Item], IOException + FullyQualifiedErrorId : RenameItemIOError,Microsoft.PowerShell.Commands.RenameItemCommand
That's because you're finding files that doesn't contain an underscore. Filter out those first, ex. Get-childItem -Path $path -Filter "*_*.exe" | Foreach { ....
It may be worth mentioning that this solution will rename any files found, not just .exes.
You are right @FrodeF. I will also edit my answer and use your filter, thanks!
0

!not tested

try this

$path = 'C:\Temp\TestPath\'

gci $path *.exe | ? basename -match '_' | % {
    # if the file.txt already exists, rename it to file-1.txt and so on
    $num = 1
    $base = $_.basename.substring(0, $_.basename.indexof('_'))
    $ext = $_.extension
    $dir = $_.directory
    $newname = Join-Path $dir "$base$ext"
    while (Test-Path $newname) {
        $newname = Join-Path $dir "$base-$num$ext"
        $num++
    }

    # finally, rename the file
    ren $_.fullname $newname
}

2 Comments

Exception calling "Substring" with "2" argument(s): "Length cannot be less than zero. Parameter name: length" At line:6 char:34 + $base = $_.basename.substring <<<< (0, $_.basename.indexof('_')) + CategoryInfo : NotSpecified: (:) [], MethodInvocationException + FullyQualifiedErrorId : DotNetMethodException
updated. i believe that error may have been caused by attempting to rename a file that does not have an _ in the name

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.