Sabbir Ahmed
Sabbir Ahmed

Reputation: 75

Replace text between two string powershell

I have a question which im pretty much stuck on..

I have a file called xml_data.txt and another file called entry.txt

I want to replace everything between <core:topics> and </core:topics>

I have written the below script

$test = Get-Content -Path ./xml_data.txt
$newtest = Get-Content -Path ./entry.txt
$pattern = "<core:topics>(.*?)</core:topics>"
$result0 = [regex]::match($test, $pattern).Groups[1].Value
$result1 = [regex]::match($newtest, $pattern).Groups[1].Value
$test -replace $result0, $result1

When I run the script it outputs onto the console it doesnt look like it made any change.

Can someone please help me out

Note: Typo error fixed

Upvotes: 5

Views: 5548

Answers (1)

Wiktor Stribiżew
Wiktor Stribiżew

Reputation: 626802

There are three main issues here:

  • You read the file line by line, but the blocks of texts are multiline strings
  • Your regex does not match newlines as . does not match a newline by default
  • Also, the literal regex pattern must when replacing with a dynamic replacement pattern, you must always dollar-escape the $ symbol. Or use simple string .Replace.

So, you need to

  • Read the whole file in to a single variable, $test = Get-Content -Path ./xml_data.txt -Raw
  • Use the $pattern = "(?s)<core:topics>(.*?)</core:topics>" regex (it can be enhanced in case it works too slow by unrolling it to <core:topics>([^<]*(?:<(?!</?core:topics>).*)*)</core:topics>)
  • Use $test -replace [regex]::Escape($result0), $result1.Replace('$', '$$') to "protect" $ chars in the replacement, or $test.Replace($result0, $result1).

Upvotes: 4

Related Questions