PowerShell Gotcha: Relative Paths and .NET Methods

When you're calling PowerShell cmdlets, you can almost always specify a relative path beginning with ".\". However, if you use a path beginning with ".\" when calling a .NET method directly, it probably won't work as you intended. This is because PowerShell's idea of your current location is different than what the operating system and the .NET Framework see as the current working directory:

PS C:\Source\temp> [System.Environment]::CurrentDirectory
C:\Users\dwyatt

As an example, take the following code that tries to make a change to an XML file:

$xmlDoc = [xml](Get-Content .\MyXmlFile.xml)

$xmlDoc.someRootElement.someChildElement.Value = "New Value"

$xmlDoc.Save(".\MyXmlFile.xml")

The first line to load the XML file would work fine; Get-Content will replace ".\" with the current PowerShell location (C:\Source\temp\ , in my example) before calling any of the underlying .NET Framework methods to read the file.

The call to $xmlDoc.Save(), however, would save a copy of the file to "C:\Users\dwyatt\MyXmlFile.xml", because [System.Environment]::CurrentDirectory is currently set to "C:\Users\dwyatt".

There's an easy way to work around this problem. Instead of a period, the automatic PowerShell variable $PWD can be embedded in a string to specify a relative path when calling a .NET method:

PS C:\Source\temp> "$PWD"
C:\Source\temp

$xmlDoc.Save("$PWD\MyXmlFile.xml")
Posted in:
About the Author

Dave Wyatt

Dave Wyatt is a Microsoft MVP (PowerShell) and a member of PowerShell.org's Board of Directors.