Renaming files by removing parts of the filename - windows

I'm trying to go through all the files within a folder and rename them so that the name becomes whatever is between the 2nd and 3rd _.
e.g.: 1_2_3_4.pdf becomes 3.pdf
Having looked around, I was able to find the link below which helps with a very similar issue - but I am unable to make it work for my specific issue. Would anyone minding helping with this?
Find character position and update file name

Use the Get-ChildItem cmdlet to retrieve all files and rename it using the Rename-Item cmdlet (together with a regex replace):
Get-ChildItem 'c:\your_folder' |
Rename-Item -NewName { '{0}{1}' -f ($_.Name -replace '.*?_.*?_([^_]+).*', '$1'), $_.Extension }

Related

Attempting to search and replace a few lines in an XML file in every user's appdata/roaming folder

I'm still kind of new to windows administration and very new to powershell so please forgive my ignorance. I wrote the following one-liner and I'm attempting to adapt it so that it can modify every existing user's FTRSettings.xml file on a PC. I'm worried that using the following path with a wildcard in place of the username would only replace the first file it finds.
C:\users\*\appdata\Roaming\FTR\GoldMain\FTRSettings.xml
Tested and working one liner executed from the appdata\Roaming\FTR\GoldMain\ directory.
((Get-Content -Path .\FTRSettings.xml -Raw) -replace '<Setting name="audioLevelsVisible" type="11">0</Setting>','<Setting name="audioLevelsVisible" type="11">-1</Setting>' -replace '<Setting name="inputLevelsVisible" type="11">0</Setting>','<Setting name="inputLevelsVisible" type="11">-1</Setting>' -replace '<Setting name="logSheetPaneViewState" type="11">0</Setting>','<Setting name="logSheetPaneViewState" type="11">-1</Setting>')
I was wondering if anyone could point me in the right direction.
To process each file individually:
Use Get-ChildItem with your wildcard-based path to find all matching files.
Loop over all matching files with ForEach-Object and perform the string replacement and updating for each file.
Note: I'm using a single -replace operation for brevity.
Get-ChildItem -Path C:\users\*\appdata\Roaming\FTR\GoldMain\FTRSettings.xml |
ForEach-Object {
$file = $_
($file | Get-Content -Raw) -replace 'foo', 'bar' |
Set-Content -Encoding utf8 -LiteralPath $file.FullName -WhatIf
}
Note: The -WhatIf common parameter in the command above previews the operation. Remove -WhatIf once you're sure the operation will do what you want.
Note the use of -Encoding to control the character encoding explicitly, because the original encoding is never preserved in PowerShell; instead, the cmdlet's own default applies - adjust as needed.

Use Powershell to delete ShellIconOverlayIdentifiers on Windows

I am currently very annoyed by Dropbox and Nextcloud, which both battle the ShellIconOverlayIdentifier list. A problem which many people seem to have, when you search the internet.
Now I want to combine my annoyance with my intent to learn powershell (7.2.0).
I started with the following script, which shall retrieve all keys. And later I want to use regex via -match to find the entries I want to delete. For now I work with both Remove-Item -WhatIf and Get-ItemProperty to test it.
Currently my problem is that I can create my list as intended. But when I feed the list into the remove command I get that the path cannot be found. What am I doing wrong?
Push-Location -Path Registry::HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\ShellIconOverlayIdentifiers
$list = Get-ChildItem -Path .
$filteredList = $list -match "DropboxExt10"
$filteredList
# Remove-Item -WhatIf -Recurse $filteredList
Get-ItemProperty $filteredList
Pop-Location
The error is Cannot find path 'Microsoft.PowerShell.Core\Registry::HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\ShellIconOverlayIdentifiers\HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\ShellIconOverlayIdentifiers\ DropboxExt10' because it does not exist. Apparantly it adds the path as relative path to the current location. Why doesn't it interpret as an absolute path? When I ommit the push-location part it trys to add the registry path to my current working directory in which the script lives. But this is wrong as well.
Thanks for your help in advance.
Use one of the following:
$filteredList | Remove-Item -WhatIf -Recurse
# Alternatively:
Remove-Item -LiteralPath $filteredList.PSPath -WhatIf -Recurse
The above commands ensure that the registry items (keys) are bound by their full, provider-qualified paths to Remove-Item's -LiteralPath parameter, via their .PSPath property; in the case of registry paths, the path's provider prefix is Microsoft.PowerShell.Core\Registry:: (or, if identifying the originating module isn't also required, Registry::, as used in your Push-Location call)
What appears to be happening is that when the items are stringified - which is what happens when you pass them as a whole, as an argument (e.g. Remove-Item $filteredlist, which is the same as Remove-Item -Path $filteredlist), they lack the provider prefix and are represented as registry-native paths.
And given that a full registry-native path such as HKEY_LOCAL_MACHINE\... neither starts with a drive specification nor with \ or /, it is interpreted as a relative path, resulting in the symptom you saw.

Change multiple folder name from %-% to % (delete everything after the hyphen)

I have a folder containing multiple sub folders named like : 12345 - textfoldername
I want to rename all these sub folders by keeping just the first number (12345) and delete all the rest ( - textfoldername).
How can I build the windows script for that.
Thanks for your help !
With powershell, use Get-ChildItem to discover all the subfolders, then use Rename-Item to rename:
Get-ChildItem path\to\root\directory -Directory |Rename-Item -NewName {$_.Name -replace ' - .+$'}
The -replace operator with remove - and anything thereafter in the existing name (or, if - something isn't found, ignore it)

Powershell renaming special directories recursively

I got this folder structure
C:\Users\myUser\Desktop
including folders called
BL-100
BL-105
BL-108
and so on...
most BL-folders storing a file.xml, but not all.
So on Desktop are much folders starting with BL- and the most, but not all, storing a file.xml.
Now I want to search all folders which are starting with BL- and store a file.xml and rename those folders to RG-100, RG-105, RG-108 and so on
At the moment I got this script:
foreach($Directory in Get-ChildItem -Path C:\Users\myUser\Desktop -Recurse | Where-Object{($_.Name.Substring(0,3) -eq 'BL-')}){
}
This does not work and is showing me error: Exception calling "Substring" with "2" argument(s): "Index and length must refer to a location within the string. Parameter name: length"
Anyone can help please?
The error you're seeing is because SubString fails for some reason. The most likely reason would be if the string is not long enough; e.g. if you had a folder with a 1 character long name. To see what I mean, try running: '1'.Substring(0,2).
To avoid this, instead you could use the like operator. e.g.
foreach($Directory in (
Get-ChildItem -LiteralPath 'C:\Users\myUser\Desktop' -Recurse `
| Where-Object{($_.Name -like 'BL-*')}
)){
#...
}
Just do it:
Get-ChildItem "C:\Users\myuser\Desktop" -directory -Filter "BL-*"

Renaming Files with PowerShell

I need to rename a bunch of files at once in Windows PowerShell. I read the HTG article here and it helped a little.
My problem is that It will only rename files in the top of the directory, nothing deeper. For example: There is FOLDER A and inside FOLDERA is a document and FOLDER B. Inside FOLDER B is another document. Both folders and both documents need to be renamed. The way it is working now is that FOLDER A, the document in FOLDER A, and FOLDER B are being renamed, but not the document inside FOLDER B.
My current code is:
Dir | Rename-Item –NewName { $_.name –replace “ “,”_” }
Thanks for the help!
You need to specify the -Recurse parameter on Dir to get it to recurse e.g.:
Dir -recurse | Rename-Item -NewName {$_.Name -replace ' ','_'}
BTW this may run into a problem because you're renaming the folder (FOLDERB) that contains the document first but the item being piped that corresponds to the file in FOLDERB still has the old name. In this case, you want to rename from the bottom up. One very crude but effective (I think) way to do this is to sort the file items on their path length descending e.g.:
Dir -recurse | Sort {$_.FullName.Length} -Desc | Rename-Item {$_.Name -replace ' ','_'}

Resources