Hi guys. As the title says i’m trying to alter text in a .txt file with names taken from another .txt file. I have zero experience using powershell but so far this is what i’m doing.
I’m gathering the names of folders in a directory and outputting to a .txt file like this
And then I want to search for keywords in another .txt file called placeholder.txt and replace keywords (TEST-1, TEST-2, etc) with the names of the folders in names.txt. I think I want to do something like this
I thought the first name in the names.txt file would be matched with the first keyword but it’s not really important to match them, only that each keyword is replaced by one folder name.
The idea is you have the same number of folders, keys, and items in placeholder.txt. To make things easier, you can convert all of those contents to arrays and access the same index from each array as you iterate.
Thanks for the reply. I tried your suggestion but nothing changes in placeholder.txt. I’m not sure what -directory -name is for? Also my placeholder.txt file doesn’t have folders, only keywords (test-1, test-2 etc) which I want to replace and sometimes there will be more keywords than names in the names.txt file.
# Test folder, if this is a real important folder on your system - change this.
$myfolder = 'C:\Temp\Test'
New-Item -Path C:\Temp -Name Test -ItemType Directory -ErrorAction SilentlyContinue | Out-Null
# Capture the string 'C:\Temp\Test\placeholder.txt' in this variable.
$placeholder = Join-Path $myfolder placeholder.txt
# Create text file with test-1 through test-50 in it
1..50 | ForEach-Object {"Test-$_"} | Out-File $placeholder -Encoding utf8
# Just to know it's there...
Get-Content $placeholder | Select-Object -First 5
# Make 50 folders
1..50 | ForEach-Object {New-Item -Path $myfolder -Name "Folder-$_" -ItemType Directory} | Out-Null
# This is your line to make the names.txt
Get-ChildItem $myfolder -Directory | ForEach-Object { $_.Name } | Out-File .\names.txt
# Make a nice list we can manipulate of those names
[System.Collections.Generic.List[string]]$names = Get-Content .\names.txt
# Take one line from placeholder.txt, get a random folder name, remove that name from the list (so we do each once) and process all 50 lines capturing to a variable
$replacedvalues = Get-Content $placeholder | foreach {
$randomfolder = Get-Random -Count 1 -InputObject $names
$names.Remove($randomfolder) | Out-Null
Write-Host "Replacing $_ with $randomfolder`n$($names.Count) names remaining..." -ForegroundColor Cyan
$_ -replace $_,$randomfolder # In this basic example we could've just output $randomfolder, but since you said "replace"
}
# Cleanup
Remove-Item $myfolder -Recurse -Force
# The updated list is contained in $replacedvalues, so write it to the original placeholder file
$replacedvalues | Out-File $placeholder -Encoding utf8
Get-Content $placeholder | Select-Object -First 5
Get-ChildItem-Directory parameter only returns directories and skips files. The -Name parameter only returns the Name attribute of each item. So there is no need to use Foreach-Object { $_.Name }. If you are creating names.txt with this code, I don’t see why you cannot just store the Get-ChildItem results in a variable.
The for loop will continue to loop through all items in the placeholder.txt file. Using the modulus operator %, we can conceivably iterate $i to its [int32] limit and still stay within the index range of the given arrays.
I think that I have explained what I am trying to do poorly. I have a HTML template (placeholder.txt) which has a whole bunch of placeholder/keywords (TEST-1, TEST-2, TEST-3…TEST-50 etc) which I can find and replace with the name of a folder.
This script does almost exactly what I want to do but I have to manually change “TEST-1” and “EXAMPLE” for each folder in .\myfolder\ and run it multiple times
I just want to read the names of the folders and then find/replace all instances of one of the placeholders/keywords starting with Test-1 and then Test-2 etc in the template with the name of a folder.