Shell – PowerShell -replace old,new — multiple replacements possible

powershell

I need to use PowerShell 5.1 to read a file, make edits to it, and write the results to another file. I've been studying https://stackoverflow.com/questions/45540444/grep-and-sed-not-working-in-powershell and have been able to adapt the information there to something close to what I want, which is currently the following:

PowerShell -ExecutionPolicy Bypass -Command "(Get-Content $$source_file -Raw) -replace 'AAA','BBB' | Out-File -filepath output_file"

That works, but I have two issues for which I haven't yet found an answer:

  1. Because the instruction above is part of a recipe in a Makefile which must use cmd.exe as its shell (otherwise I'd just use sed), I need to phrase the instruction as-is, i.e. with the actual PowerShell command being passed as a character string between two double quotes. Using single quotes around the values of the -replace arguments works, but in the real life problem I need to pass variables, so I have to use double quotes so that the variable references can be expanded. I read elsewhere that to include a double quote in a powershell instruction just to use two double quotes in a row, but when I do so I get an error message that I must use a value expression after the -replace operator.

Here is the version that doesn't work:

PowerShell -ExecutionPolicy Bypass -Command "(Get-Content $$source_file -Raw) -replace ""AAA"",""BBB"" | Out-File -filepath output_file"

So my first question is, how can I include a variable name in the value expression in a way that will allow it to be expanded to its real value?

My second question is, I need to make more than one edit to the file. Since the -replace operator seems to be tied to the Get-Content commandlet, I tried the following:

PowerShell -ExecutionPolicy Bypass -Command "(Get-Content $$source_file -Raw) -replace 'AAA','BBB' -replace 'CCC','DDD' | Out-File -filepath output_file"

The presence of the second -replace expression raised an error exception. So if I need to make several edits to the source file on the fly before the final version is written back to the file system, is there a simple way to do it other than sending the entire file through a new Get-Content pipe again for every edit?

Thank you.

Best Answer

It would help to see the error you get.

Here it works with two replace in a cmd window.

Alternatively you can try the .replace('AAA','BBB') method.

> type test.txt
blah AAA
Blubb CCC

> PowerShell -ExecutionPolicy Bypass -C "(Get-Content .\test.txt -Raw) -replace 'AAA','BBB' -replace 'CCC','DDD' "

blah BBB
Blubb DDD

> PowerShell -ExecutionPolicy Bypass -C "(Get-Content .\test.txt -Raw).replace('AAA','BBB').replace('CCC','DDD')"
blah BBB
Blubb DDD
Related Question