Powershell 5.1 launches any console command on new console window - windows

I have quite strange behavior happening on my powershell code. I pinned it down to these simple reproduceable steps.
Launch Powershell as Administrator.
Type cmd and confirm it opens cmd on the current Powershell terminal. Type exit to get out of the cmd console.
Run the following code:
Import-Module WebAdministration
cd iis:\apppools
new-item c:\temp\1 -itemType directory
Push-Location
cd c:\temp\1
Pop-Location
remove-item c:\temp\1
Type cmd and now you see it opens cmd on a new window.
Run cd c:\
Type cmd and now you see it opens cmd on a current window as expected.
Run cd iis:\apppools, and then cmd, and you see it opens on a current window as expected.
Why did #4 open in new window, and then why does cd c:\ fix the problem?
The real problem that I am dealing with is that when the console gets into the state of step #4, it launches any console command in a new window, so while I would expect the script to wait until the console command is finished, it launches the console command in a new window and move on to the next line without waiting for the console to finish.
Reproduceable on Powershell 5.1.14393.4350 (Windows 2016), 5.1.18362.1171 (Windows 10) and 5.1.19041.906 (Windows 10).

#Daniel's comment had the answer, and I am writing it here to comply with StackOverflow's rule:
When calling cmd from powershell, it tries to set path to the current path that you are in. However, iis: (env:, alias:, cert:, etc) are not available paths in cmd. So it will try to fallback to the latest folder you were in under cmd-accessible path (C:, D:\ etc.)
And when the folder does not exist, it appears that the failsafe for this in the code is to open a real cmd window instead.
This can be replicated without IIS, push-location and pop-location.
mkdir c:\temp\deleteme;
cd c:\temp\deleteme;
cd env:;
rm c:\temp\deleteme -Recurse;
cmd

#Daniel's comment had the answer:
When calling cmd from powershell, it tries to set path to the current path that you are in. However, iis: (env:, alias:, cert:, etc) are not available paths in cmd. So it will try to fallback to the latest folder you were in under cmd-accessible path (C:, D:\ etc.)
And when the folder does not exist, it appears that the failsafe for this in the code is to open a real cmd window instead.
This can be replicated without IIS, push-location and pop-location.
mkdir c:\temp\deleteme;
cd c:\temp\deleteme;
cd env:;
rm c:\temp\deleteme -Recurse;
cmd

Related

explorer command doesn't work in pwsh / Windows Powershell after upgrade to Windows 11

In situations where I need to quickly switch from Powershell to the Windows Explorer, I used to be able to launch Windows Explorer from whatever directory I happened to be in, like this:
PS > explorer .
(This is really just calling C:\Windows\explorer.exe.)
It worked fine until upgrading to Windows 11. Now it silently fails to do anything.
I've confirmed that, even while using the new Terminal app, the command still works in the Command Prompt. And in pwsh, the explorer alias is still pointing at C:\Windows\explorer.exe.
So why is it now broken in Powershell? And is there any work-around?
PS: I have confirmed that the following do not work either:
PS > & explorer . # Nothing
PS > C:\Windows\explorer.exe . # Nada
PS > & C:\Windows\explorer.exe . # Zilch
This is just a workaround, but as you confirmed it working, I'll turn it into an answer:
$shell = New-Object -ComObject Shell.Application
$shell.Open( $PWD.ProviderPath )
# Also works:
# $shell.Explore( $PWD.ProviderPath )
Create an instance of the Shell COM object and then call its methods Open or Explore to open the current directory, obtained from automatic variable $PWD, in Explorer.
As mklement0 points out, we have to use $PWD.ProviderPath as $PWD.Path may be based on a PowerShell-only drive, which external programs such as File Explorer don't know about.
You might also want to check the type of the provider to make sure you call the above code only for filesystem paths:
# As a demonstration, let $PWD point to a registry location
Set-Location HKCU:\Software
# The following if branch won't be entered
if( $PWD.Provider.Name -eq 'FileSystem' ) { ... }

Command prompt from C: drive, how to start executable in another drive?

I have a Windows machine with the current user in C:\Users\User.
I have an executable in another drive, let's say at D:\Folder\MyProg.exe.
Opening command prompt, it starts in the directory C:\Users\User
I type the command: start D:\Folder\MyProg.exe or D:\Folder\MyProg.exe
The exe fails to open, with a pop-up: MyProg has encountered an error
In order to run start the .exe from command prompt, I have to cd to the other directory and then start the exe.
Opening command prompt, it starts in the directory C:\Users\User
I type the command: cd /d D:\Folder && start MyProg.exe
The exe successfully opens.
Is there a better way to, from C:, start an executable in another drive?
Reproducing
Windows 10 Pro, v1809 (I don't think the version really matters)
My real use case is industrial automation, but one can observe the same result with convert.exe (cnet download link)
As commented by #Mofi, I realized the answer is most likely this:
But some programs are not good coded. Such programs depend on files in directory of the program and do not use appropriate code to reference those files from within the program with program files path, but use instead a relative path
As he instructed in the next comment, start provides a /d parameter that lets you specify a startup directory. Thus, a concise command would be:
start "" /d D:\Folder MyProg.exe
Note: the "" is for the <Title> field. The .exe I am opening is a GUI application (not a console application), so it is not necessary in this case, I just included in case other viewers find this useful in their application.
I have a Windows machine with the current user in C:\Users\User.
I have an executable in another drive, let's say at D:\Folder\MyProg.exe.
Opening command prompt, it starts in the directory C:\Users\User I type the command: start D:\Folder\MyProg.exe The exe fails to open.
In order to run start the .exe from command prompt, I have to cd to the other directory and then start the exe.
Maybe not. Try:
PATH D:\Folder;%Path%
"D:\Folder\MyProg.exe"

How to setup Intellij idea terminal path with cmder but initiated with git bash.exe?

So I have installed both Cmder and Git bash, and my Cmder is setup in a way that to run git bash.exe inside.
Currently my Intellij idea's path for terminal is set to:
C:\Program Files\Git\bin\bash.exe, which works fine for bash.exe
However, one disadvantage for directly using bash.exe is that it will not automatically convert a windows directory, for example:
D:\Documents\Adobe, when I copy this after cd, it will be:
cd D:\Documents\Adobe instead of:
cd /d/Documents/Adobe which I will get in cmder.
I have looked up online, people shared about how to incorporate cmder in idea's terminal by using the path:
"cmd.exe" /k ""%CMDER_ROOT%\vendor\init.bat""
However, that is only using cmder as a coating for cmd.exe, not bash.exe as I want.
I have tried to replace with:
"C:\Program Files\Git\bin\bash.exe" /k ""%CMDER_ROOT%\vendor\init.bat"", it was not working.
also tried:
"C:\Program Files\Git\bin\sh.exe" --login -i /k ""%CMDER_ROOT%\vendor\init.bat""
and:
"C:\Program Files\Git\bin\sh.exe" /k ""%CMDER_ROOT%\vendor\init.bat""
All failed.
Any sugestons? Thanks!
Or if someone can show me how to change git bash.exe so that it can automatically translate the windows directory to Linux type, that would also work.
I don't think you can run git-bash in cmder AND from Intellij IDEA terminal.
I tried this: creating a task for git-bash in Cmder and try to use cmder.exe /TASK xxx in Intellij. I have the task, but it seems that Intellij does not support args after an executable in Terminal settings, so /TASK xxx is not parsable.
Then I changed path in Terminal settings to a BAT file, but terminal seems not support running it; I see terminal flashes and closes. Maybe only executable is allowed. Branch info is shown at the right of current path. I think it is convenient.
So, you have two options:
change terminal to git-bash.exe and get used to slash as path separator(and that is much saner than back slashes, trust me)
just configure Intellj Terminal to open cmder, with default task like this: cmd /k ""%ConEmuDir%\..\init.bat" ". This will open cmder in the current folder, and you also have git support. That is, stop using mingw64 and only ConEmu + clink. You have color support, Windows backslashes and so on. And you also can mix Win commands with bash syntax(with "Shell integration" ticked). This is what I am doing right now. Branch info is shown, lambda symbol as well. It is already perfect.

pushd in Windows Power Shell and Command Prompt

I have a batch script on my computer called cs.bat. When I enter cs in the command prompt, pushd takes me to a certain directory and leaves me there. In PowerShell, the command does the same thing but then brings me back into the starting directory.
Why is this the case? How can I make it so that I stay in the directory after typing 'cs' into power shell?
Powershell includes aliases for Pushd and Popd.
Get-Alias Pushd : pushd -> Push-Location
Get-Alias Popd : popd -> Pop-Location
You can then use Get-Help Push-Location -Full -Online to get the latest help for that cmdlet.
Then just make a script and test this behavior.
#Sample.ps1 script
#Get current DIR
dir
#push location to some location and DIR there.
Push-Location C:\Scripts\
dir
#at this point, your console will still be in the Push-Location directory
#simply run the Pop-Location cmdlet to switch back.
This is happening because your "cs.bat" runs in a different process (running cmd.exe) spawned by PowerShell (whereas batch files execute in the same instance when run from cmd). Current directory is a per-process concept, so changing it in one process has no effect on another.
Probably the simplest way to get around it is to write a "cs.ps1" script (or function), that would run in the PowerShell process.

How do I launch a Git Bash window with particular working directory using a script?

How can I launch a new Git Bash window with a specified working directory using a script (either Bash or Windows batch)?
My goal is to launch multiple Git Bash windows from a single script, each set to a different working directory. This way I can quickly get to work after booting the computer instead of having to open Git Bash windows and navigating each one to the correct working directory.
I am not asking how to change the default working directory, like this question does, but to launch one or more terminal windows with different working directories from a script.
Another option is to create a shortcut with the following properties:
Target should be:
"%SYSTEMDRIVE%\Program Files (x86)\Git\bin\sh.exe" --login
Start in is the folder you wish your Git Bash prompt to launch into.
Try the --cd= option. Assuming your GIT Bash resides in C:\Program Files\Git it would be:
"C:\Program Files\Git\git-bash.exe" --cd="e:\SomeFolder"
If used inside registry key, folder parameter can be provided with %1:
"C:\Program Files\Git\git-bash.exe" --cd="%1"
Git Bash uses cmd.exe for its terminal plus extentions from MSYS/MinGW which are provided by sh.exe, a sort of cmd.exe wrapper. In Windows you launch a new terminal using the start command.
Thus a shell script which launches a new Git Bash terminal with a specific working directory is:
(cd C:/path/to/dir1 && start sh --login) &
(cd D:/path/to/dir2 && start sh --login) &
An equivalent Windows batch script is:
C:
cd \path\to\dir1
start "" "%SYSTEMDRIVE%\Program Files (x86)\Git\bin\sh.exe" --login
D:
cd \path\to\dir2
start "" "%SYSTEMDRIVE%\Program Files (x86)\Git\bin\sh.exe" --login
To get the same font and window size as the Git Bash launched from the start menu, it is easiest to copy the start menu shortcut settings to the command console defaults (to change defaults, open cmd.exe, left-click the upper left icon, and select Defaults).
Let yet add up to the answer from #Drew Noakes:
Target:
"C:\Program Files\Git\git-bash.exe" --cd=C:\GitRepo
The cd param should be one of the options how to specify the working directory.
Also notice, that I have not any --login param there: Instead, I use another extra app, dedicated just for SSH keys: Pageant (PuTTY authentication agent).
Start in:
C:\GitRepo
The same possible way, as #Drew Noakes mentioned/shown here sooner, I use it too.
Shortcut key:
Ctrl + Alt + B
Such shortcuts are another less known feature in Windows. But there is a restriction: To let the shortcut take effect, it must be placed somewhere on the User's subdirectory: The Desktop is fine.
If you do not want it visible, yet still activatable, place this .lnk file i.e. to the quick launch folder, as that dir is purposed for such shortcuts. (no matter whether displayed on the desktop) #76080 #3619355
"\Application Data\Microsoft\Internet Explorer\Quick Launch\"
In addition, Win10 gives you an option to open git bash from your working directory by right-clicking on your folder and selecting GitBash here.
Windows 10
This is basically #lengxuehx's answer, but updated for Win 10, and it assumes your bash installation is from Git Bash for Windows from git's official downloads.
cmd /c (start /b "%cd%" "C:\Program Files\GitW\git-bash.exe") && exit
I ended up using this after I lost my context-menu items for Git Bash as my command to run from the registry settings. In case you're curious about that, I did this:
Create a new key called Bash in the shell key at HKEY_CLASSES_ROOT\Directory\Background\shell
Add a string value to Icon (not a new key!) that is the full path to your git-bash.exe, including the git-bash.exe part. You might need to wrap this in quotes.
Edit the default value of Bash to the text you want to use in the context menu
Add a sub-key to Bash called command
Modify command's default value to cmd /c (start /b "%cd%" "C:\Program Files\GitW\git-bash.exe") && exit
Then you should be able to close the registry and start using Git Bash from anywhere that's a real directory. For example, This PC is not a real directory.
This is the command which can be executed directly in Run dialog box (shortcut is win+R) and also works well saved as a .bat script:
cmd /c (start /d "/path/to/dir" bash --login) && exit
I'm not familiar with Git Bash but assuming that it is a git shell (such as git-sh) residing in /path/to/my/gitshell and your favorite terminal program is called `myterm' you can script the following:
(cd dir1; myterm -e /path/to/my/gitshell) &
(cd dir2; myterm -e /path/to/my/gitshell) &
...
Note that the parameter -e for execution may be named differently with your favorite terminal program.
Using Windows Explorer, navigate to any directory you want, type "cmd" in the address bar it will open Windows command prompt in that directory.
Along the same lines, if you have the git directory in your path, you can type "git-bash" in the address bar and a Git Shell will open in that directory.
If using Windows OS :
Right click on git terminal > Properties
Properties>Under shortcut tab>Start in:
add your folder target path like below image

Resources