68

I have a PowerShell script located at D:\temp.

When I run this script, I want the current location of the file to be listed. How do I do this?

For example, this code would accomplish it in a DOS batch file; I am trying to convert this to a PowerShell script...

FOR /f "usebackq tokens=*" %%a IN ('%0') DO SET this_cmds_dir=%%~dpa
CD /d "%this_cmds_dir%"
2
  • 2
    Just an observation about how you're doing this in "DOS" (which I assume in this century you mean Windows). Wouldn't it be better just to do: CD "%~dp0"? Commented Feb 25, 2019 at 20:57
  • In a cmd.exe shell it can be done using CD /D "%~dp0". Commented Nov 1, 2019 at 18:56

4 Answers 4

148

PowerShell 3+

The path of a running scripts is:

$PSCommandPath

Its directory is:

$PSScriptRoot

PowerShell 2

The path of a running scripts is:

$MyInvocation.MyCommand.Path

Its directory is:

$PSScriptRoot = Split-Path $MyInvocation.MyCommand.Path -Parent
Sign up to request clarification or add additional context in comments.

8 Comments

Be careful using $PSSriptRoot. It that is a predefined variable within a module.
PowerShell team will finally introduce $PSScriptRoot in ordinary scripts - that is what I'm hoping for. When I discovered this variable I was really excited - thinking I could replace the $MyInvocation / Split-Path dance but nooo. :-) Folks who would also like to see this should vote: connect.microsoft.com/PowerShell/feedback/details/522951/…
That happened. If you're on PowerShell 2 and using this trick, make sure you write: if(!$PSScriptRoot){ $PSScriptRoot = Split-Path $MyInvocation.MyCommand.Path -Parent } so that it "just works" in PowerShell 3
I believe that Split-Path $script:MyInvocation.MyCommand.Path is generally preferred over Split-Path $MyInvocation.MyCommand.Path -Parent. See this post for more info: stackoverflow.com/questions/801967/…
Noteworthy: $PSScriptRoot and $PSCommandPath will be blank if typed into the scripting console in PowerShell ISE, or if executing the selected part of a script file only. It works if the entire script is run.
|
12

Roman Kuzmin answered the question imho. I'll just add that if you import a module (via Import-Module), you can access $PsScriptRoot automatic variable inside the module -- that will tell you where the module is located.

Comments

2

For what it's worth, I found that this works for me on PowerShell V5 in scripts and in PowerShell ISE:

try {
    $scriptPath = $PSScriptRoot
    if (!$scriptPath)
    {
        if ($psISE)
        {
            $scriptPath = Split-Path -Parent -Path $psISE.CurrentFile.FullPath
        } else {
            Write-Host -ForegroundColor Red "Cannot resolve script file's path"
            exit 1
        }
    }
} catch {
    Write-Host -ForegroundColor Red "Caught Exception: $($Error[0].Exception.Message)"
    exit 2
}

Write-Host "Path: $scriptPath"

HTH

P.S. Included full error handling. Adjust to your needs, accordingly.

Comments

0

Here is one example:

$ScriptRoot = ($ScriptRoot, "$PSScriptRoot" -ne $null)[0]
import-module $ScriptRoot\modules\sql-provider.psm1
Import-Module $ScriptRoot\modules\AD-lib.psm1 -Force

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.