首页 > 解决方案 > Powershell用运行时传递的环境变量替换子字符串

问题描述

我正在获取配置文件的输入,并且需要用我在运行时传递的环境变量替换特定行。然而,结果字符串完全相同(没有变化)。我使用了 replace 关键字。

我已经通过单引号替换的行,这意味着它将按原样传递(字符串包含双引号中的某些值),然后是双引号中的预期字符串。

$File = Get-Content path of file
if (![string]::IsNullOrWhiteSpace($env:ai_logging_mode)) **this is the env variable**
{
    $file = $file | ForEach-Object { $_ -replace '<logger name="*" minlevel="Trace" writeTo="console" />', "<logger name=`"*`" minlevel=`"$env:ai_logging_mode`" writeTo=`"console`" />"};
}
Set-Content -Path path of the file -Value $file;

minlevel 的值不会改变。我已将值作为信息传递。结果应该像

<logger name="*" minlevel="Info" writeTo="console" />

然而结果还是

<logger name="*" minlevel="Trace" writeTo="console" />

标签: powershellreplace

解决方案


这里的问题源于没有转义正则表达式元字符。

Replace运算符执行正则表达式匹配并替换匹配的字符。*是正则表达式中的量词,它将匹配当前匹配字符( 之前的字符*)的零个或多个字符。*如果反斜杠转义,正则表达式将按字面意思匹配,变为\*. 您还可以Escape()对字符串使用 Regex 类中的方法,该方法将自动转义元字符。

$StringToReplace = '<logger name="\*" minlevel="Trace" writeTo="console" />'
$StringReplacement = "<logger name=`"*`" minlevel=`"$env:ai_logging_mode`" writeTo=`"console`" />"
$_ -replace $StringToReplace,$StringReplacement

要使用 Regex 类Escape()方法,您可以执行以下操作:

$StringToReplace = [regex]::Escape('<logger name="\*" minlevel="Trace" writeTo="console" />')
$StringReplacement = "<logger name=`"*`" minlevel=`"$env:ai_logging_mode`" writeTo=`"console`" />"
$_ -replace $StringToReplace,$StringReplacement

推荐阅读