This script works, I want to condense it so if I add more lines to find and replace in the file I'm not being redundant.
Get-ChildItem C:\Users\JonSa\Desktop -Filter callcounts.xml | Foreach- Object{
(Get-Content $_.FullName) |
Foreach-Object {$_ -replace "#aXXXXX.ac1.vbspbx.com", ""} |
Set-Content $_.FullName
}
Get-ChildItem C:\Users\JonSa\Desktop -Filter callcounts.xml | Foreach- Object{
(Get-Content $_.FullName) |
Foreach-Object {$_ -replace "sip:", ""} |
Set-Content $_.FullName
}
I would like to accomplish this with fewer lines that leaves room for more arguments.
With only one file, don't use Get-ChildItem and a ForEach-Object
when using the -raw -parameter, you can apply the replace on the whole file
you can also append several -replace one after the other.
for the same replacement (here none) you can use an alternation | (OR)
an empty replacement can be omitted with the -replace operator (not so with the .replace() method)
$File = 'C:\Users\JonSa\Desktop\callcounts.xml'
(Get-Content $File -raw) -replace '#aXXXXX.ac1.vbspbx.com|sip:' |
Set-Content $File
Related
I have many folder
ex: folder1,folder2,folder3... about folder100
In those folder have many files
ex: 1.html,2.html,3.html,4.html...about 20.html
I want to replace some text in those all html file in all folder
but not all text i want to replace is same.
ex:(for 1.html, i want to replace ./1_files/style.css to style.css) and (for 2.html, i want to replace ./2_files/style.css to style.css)....
So i try something like this and it work well
Get-ChildItem "*\1.html" -Recurse | ForEach-Object -Process {
(Get-Content $_) -Replace './1_files/style.css', 'style.css' | Set-Content $_
}
Get-ChildItem "*\2.html" -Recurse | ForEach-Object -Process {
(Get-Content $_) -Replace './2_files/style.css', 'style.css' | Set-Content $_
}
Get-ChildItem "*\3.html" -Recurse | ForEach-Object -Process {
(Get-Content $_) -Replace './3_files/style.css', 'style.css' | Set-Content $_
}
Get-ChildItem "*\4.html" -Recurse | ForEach-Object -Process {
(Get-Content $_) -Replace './4_files/style.css', 'style.css' | Set-Content $_
}
but i have to write many of those code "\4.html" "\5.html" "*\6.html" ...
i try this but it do not work
Do {
$val++
Write-Host $val
$Fn = "$val.html"
Get-ChildItem "*\$Fn" -Recurse | ForEach-Object -Process {
(Get-Content $_) -Replace './$val_files/style.css', 'style.css' |
Set-Content $_
}
} while($val -ne 100)
Please show me correct way to do..loop replace
thanks you
Assuming all your subfolders can be found inside one source folder path, you can do below to do the replacement in all those files:
# the path where all subfolders and html files can be found
$sourcePath = 'X:\Wherever\Your\Subfolders\Are\That\Contain\The\Html\Files'
Get-ChildItem -Path $sourcePath -Filter '*.html' -Recurse -File |
# filter on html files that have a numeric basename
Where-Object {$_.BaseName -match '(\d+)'} | ForEach-Object {
# construct the string to repace and escape the regex special characters
$replace = [regex]::Escape(('./{0}_files/style.css' -f $matches[1]))
# get the content as one single multiline string so -replace works faster
(Get-Content -Path $_.FullName -Raw) -replace $replace, 'style.css' |
Set-Content -Path $_.FullName
}
I have a text file which contains the following
php_configuration=up21
sql_configuration=up22
apache_configuration=up23
java_script=down
html=down
I want to replace the up21, up22 and up23 with cat, dog and elephant and keep the remaining content of the file as it is.
But when I execute the below powershell script, it will replace the strings, but wont preserve the remaining content of the text file:
$a=Get-Content -Path C:\Users\Administrator\Desktop\Pow\loc.txt |Select-String -Pattern
"php_configuration"|ForEach-Object {$_ -Replace 'up21', 'cat'}
$b=Get-Content -Path C:\Users\Administrator\Desktop\Pow\loc.txt |Select-String -Pattern
"sql_configuration"|ForEach-Object {$_ -Replace 'up22', 'dog'}
$c=Get-Content -Path C:\Users\Administrator\Desktop\Pow\loc.txt |Select-String -Pattern
"apache_configuration"|ForEach-Object {$_ -Replace 'up23', 'elephant'}
$a, $b, $c| Set-Content -Path C:\Users\Administrator\Desktop\Pow\loc.txt
You can basically do like:
(Get-Content 'C:\Users\Administrator\Desktop\Pow\loc.txt') | Foreach-Object {
$_ -replace 'up21', 'cat' `
-replace 'up22', 'dog' `
-replace 'up23', 'elephant'
} | Set-Content 'C:\Users\Administrator\Desktop\Pow\loc.txt'
Is there a need to specify "php_configuration" etc.?
EDIT: Ok, after reading #T-Me's comment below, I have changed the answer. Not the prettiest but here you go.
(Get-Content 'C:\Users\Administrator\Desktop\Pow\loc.txt') | Foreach-Object {
if($_ | Select-string -Pattern "php_configuration"){$_ -replace 'up21', 'cat'}
elseif($_ | Select-String -Pattern "sql_configuration"){$_ -replace 'up22', 'dog'}
elseif($_ | Select-String -Pattern "apache_configuration"){$_ -replace 'up23', 'elephant'}
else {$_}
} | Set-Content 'C:\Users\Administrator\Desktop\Pow\loc.txt'
I have the following script:
$allFiles = Get-ChildItem "./" -Recurse | Where { ($_.Extension -eq ".ts")}
foreach($file in $allFiles)
{
# Find and replace the dash cased the contents of the files
(Get-Content $file.PSPath) |
Foreach-Object {$_ -replace "my-project-name", '$appNameDashCased$'} |
Set-Content $file.PSPath
# Find and replace the dash cased the contents of the files
(Get-Content $file.PSPath) |
Foreach-Object {$_ -replace "MyProjectName", '$appNameCamelCased$'} |
Set-Content $file.PSPath
# Find and replace the dash cased the contents of the files
(Get-Content $file.PSPath) |
Foreach-Object {$_ -replace "myProjectName", '$appNamePascalCased$'} |
Set-Content $file.PSPath
}
It takes a file and does some replacing, then saves the file. Then it takes the same file and does some more replacing then saves the file again. Then it does it one more time.
This works, but seems inefficient.
Is there a way to do all the replacing and then save the file once?
(If possible, I would prefer to keep the readable style of PowerShell.)
Sure, just chain your replaces inside the ForEach-Object block:
$allFiles = Get-ChildItem "./" -Recurse | Where { ($_.Extension -eq ".ts")}
foreach($file in $allFiles)
{
(Get-Content $file.PSPath) |
Foreach-Object {
# Find and replace the dash cased the contents of the files
$_ -replace "my-project-name", '$appNameDashCased$' `
-replace "MyProjectName", '$appNameCamelCased$' `
-replace "myProjectName", '$appNamePascalCased$'
} |
Set-Content $file.PSPath
}
This can be done, and is actually far simpler than what you're doing. You can chain the -Replace command as such:
$allFiles = Get-ChildItem "./" -Recurse | Where { ($_.Extension -eq ".ts")}
foreach($file in $allFiles)
{
# Find and replace the dash cased the contents of the files
(Get-Content $file.PSPath) -replace "my-project-name", '$appNameDashCased$' -replace "StringB", '$SecondReplacement$' -replace "StringC", '$ThirdReplacement$' | Set-Content $file.PSPath
}
I have a text (.txt) file with following content:
Car1
Car2
Car3
Car4
Car5
For changing Car1 for random text I used this script:
Get-ChildItem "C:\Users\boris.magdic\Desktop\q" -Filter *.TXT |
Foreach-Object{
$content = Get-Content $_.FullName
$content | ForEach-Object { $_ -replace "Car1", "random_text" } | Set-Content $_.FullName
}
This is working ok, but now I want to add one text line under Car2 in my text file.
How can I do that?
Just chain another -replace and use a new line!
Get-ChildItem "C:\Users\boris.magdic\Desktop\q" -Filter *.TXT |
Foreach-Object{
$file = $_.FullName
$content = Get-Content $file
$content | ForEach-Object { $_ -replace "Car1", "random_text" -replace "(Car2)","`$1`r`nOtherText" } | Set-Content $file
}
First thing is that | Set-Content $_.FullName would not work since the file object does not exist in that pipe. So one simple this to do it save the variable for use later in the pipe. You can also use the ForEach($file in (Get-ChildItem....)) construct.
The specific change to get what you want is the second -replace. We place what you want to match in brackets to that we can reference it in the replacement string with $1. We use a backtick to ensure PowerShell does not treat it as a variable.
We can remove some redundancy as well since -replace will work against the strings of file as a whole
Get-ChildItem "c:\temp" -Filter *.TXT |
Foreach-Object{
$file = $_.FullName
(Get-Content $file) -replace "Car1", "random_text" -replace "(Car2)","`$1`r`nOtherText" | Set-Content $file
}
While this does work with your sample text I want to point out that more complicated strings might require more finesse to ensure you make the correct changed and that the replacements we are using are regex based and do not need to be for this specific example.
.Replace()
So if you were just doing simple replacements then we can update your original logic.
Foreach-Object{
$file = $_.FullName
$content = Get-Content $_.FullName
$content | ForEach-Object { $_.replace("Car1", "random_text").replace("Car2","Car2`r`nOtherText")} | Set-Content $file
}
So that is just simple text replacement chained using the string method .Replace()
I am trying to remove all the lines from a text file that contains a partial string using the below PowerShell code:
Get-Content C:\new\temp_*.txt | Select-String -pattern "H|159" -notmatch | Out-File C:\new\newfile.txt
The actual string is H|159|28-05-2005|508|xxx, it repeats in the file multiple times, and I am trying to match only the first part as specified above. Is that correct? Currently I am getting empty as output.
Am I missing something?
Suppose you want to write that in the same file, you can do as follows:
Set-Content -Path "C:\temp\Newtext.txt" -Value (get-content -Path "c:\Temp\Newtext.txt" | Select-String -Pattern 'H\|159' -NotMatch)
Escape the | character using a backtick
get-content c:\new\temp_*.txt | select-string -pattern 'H`|159' -notmatch | Out-File c:\new\newfile.txt
Another option for writing to the same file, building on the existing answers. Just add brackets to complete the action before the content is sent to the file.
(get-content c:\new\sameFile.txt | select-string -pattern 'H`|159' -notmatch) | Set-Content c:\new\sameFile.txt
You don't need Select-String in this case, just filter the lines out with Where-Object
Get-Content C:\new\temp_*.txt |
Where-Object { -not $_.Contains('H|159') } |
Set-Content C:\new\newfile.txt
String.Contains does a string comparison instead of a regex so you don't need to escape the pipe character, and it's also faster
The pipe character | has a special meaning in regular expressions. a|b means "match either a or b". If you want to match a literal | character, you need to escape it:
... | Select-String -Pattern 'H\|159' -NotMatch | ...
This is probably a long way around a simple problem, it does allow me to remove lines containing a number of matches. I did not have a partial match that could be used, and needed it to be done on over 1000 files.
This post did help me get to where I needed to, thank you.
$ParentPath = "C:\temp\test"
$Files = Get-ChildItem -Path $ParentPath -Recurse -Include *.txt
$Match2 = "matchtext1"
$Match2 = "matchtext2"
$Match3 = "matchtext3"
$Match4 = "matchtext4"
$Match5 = "matchtext5"
$Match6 = "matchtext6"
$Match7 = "matchtext7"
$Match8 = "matchtext8"
$Match9 = "matchtext9"
$Match10 = "matchtext10"
foreach ($File in $Files) {
$FullPath = $File | % { $_.FullName }
$OldContent = Get-Content $FullPath
$NewContent = $OldContent `
| Where-Object {$_ -notmatch $Match1} `
| Where-Object {$_ -notmatch $Match2} `
| Where-Object {$_ -notmatch $Match3} `
| Where-Object {$_ -notmatch $Match4} `
| Where-Object {$_ -notmatch $Match5} `
| Where-Object {$_ -notmatch $Match6} `
| Where-Object {$_ -notmatch $Match7} `
| Where-Object {$_ -notmatch $Match8} `
| Where-Object {$_ -notmatch $Match9} `
| Where-Object {$_ -notmatch $Match10}
Set-Content -Path $FullPath -Value $NewContent
Write-Output $File
}
If you anyone having this issue while doing what suggested by Robert Brooker-
*These files have different encodings. Left file: Unicode (UTF-8) with signature. Right file: Unicode (UTF-8) without signature. You can resolve the difference by saving the right file with the encoding Unicode (UTF-8) with signature.* with Set-Content
use -Encoding UTF8
so like this
(get-content c:\new\sameFile.txt | select-string -pattern 'H`|159' -notmatch) | Set-Content c:\new\sameFile.txt -Encoding UTF8