PowerShell truly becomes powerful when it is made to handle tasks remotely. While this is amazing, stakeholders in many organisations may be opposed to the idea of remotely managing computers using PowerShell.

In most cases, security is the elephant in the room.

However, PowerShell is not some super-tool that increases your access within the environment; it just makes tasks easier by eliminating the unnecessary parts that you may have to deal with, if you were graphically performing the tasks. In fact, PowerShell remoting is not any less secure than any other remoting protocol, such as RDP. Also, some of the built-in security features within PowerShell make it as secure as things can get in the Windows world.

PowerShell remoting runs within the Windows Remote Management space; it uses the Web Services Management protocol for communication.

In this article, we introduce the following:

Prerequisites

The prerequisites aren’t complicated in any way. If you plan to use PowerShell remoting:

  1. The target computer should have remoting enabled
  2. Your account should have privileges to perform administrative activities on the target computer

What remoting actually is

In most cases when someone refers to remoting in PowerShell, they’re referring to having a session on the target computer, as though you’re sitting at the target computer. Therefore, if you do a Get-Process from within the remote session, PowerShell would actually list out the processes running on the remote computer.

Identity, authentication and authorisation

By default, the remote session would simply impersonate you on the target computer. If you want to use a different set of credentials, you need to explicitly supply the alternate credentials when starting the session1.

All of the actions you can perform on the target would be determined by what authorisation you have on the target computer.

How to

The first prerequisite is that the remote computer should have PowerShell Remoting enabled. To enable PowerShell Remoting, run the following command on the remote computer as an administrator.

Enable-PsRemoting

Of course, this command cannot be run using PowerShell on a remote computer—group policies and console connection are a couple of ways of doing this. Enabling PowerShell Remoting through group policies is perhaps the best bet. The other option you have is to configure your Windows build image to support PowerShell Remoting. The choice of options would vary based on your environment.

Once remoting is enabled on the target, there are a few ways of running commands remotely.

Using Invoke-Command

Invoke-Command simply runs the specified command on the remote computer. The syntax is simple:

Invoke-Command -ComputerName 'SERVER01', 'SERVER02' -ScriptBlock { Get-Service }

Invoke-Command can be used to run a command on multiple computers as well. The command mentioned within the ScriptBlock can run simultaneously on thirty-two computers. Your computer would send the command to the remote computers, and wait for a response from them. The output is combined on your local computer2 and displayed.

The issue with this method is that the computer name has to be specified every time you want to run a command on a remote computer.

Using Enter-PsSession

Sessions created with Enter-PsSession are persistent as long as you don’t exit the shell or the session itself. This way, you can run multiple commands on the remote computer without having to specify the computer name every time. As with Invoke-Command, this command also accepts alternate credentials.

Enter-PsSession -ComputerName 'SERVER01' -Credentials 'domain\username'

Once this session is entered into, you’d notice a change in the prompt; it would include the name of the remote computer. All commands you enter going forward would be run on the remote computer, until you exit from the session using exit.

Saved sessions

You can even save sessions if you’d like to reuse them within the current PowerShell process. You do this by saving the session in a variable.

$MySession = New-PsSession -ComputerName 'MyRemoteComputer' -Credential domain\username

Enter-PsSession $MySession

In fact, if you have a session saved, you can use the same information with Invoke-Command as well:

Invoke-Command -Session $MySession -ScriptBlock {Get-Process | Select-Object -First 10}

Judging what works best for the situation is the trick, here. If you plan to run a single command on one or more computers, you are better off doing this using Invoke-Command. If you plan to run multiple commands on a single computer, go with a PowerShell Remote session.

OpenSSH (PowerShell Core)

PowerShell Core is the new PowerShell. Windows PowerShell has attained the feature-complete status and is no more developed (it will only receive security fixes, if any, going forward). All development is now focused on the open-source PowerShell Core.

While Windows PowerShell uses WinRM, PowerShell Core uses the OpenSSH protocol at the transport layer for remoting. To use the cross-platform PowerShell Core for cross-platform administration, you would need OpenSSH.

The major plus with using OpenSSH is that you do not need to enable PowerShell Remoting per se, on the target computer, as long as it has OpenSSH. However, both the computers in question must have OpenSSH installed on them.

Configuring SSH

To enable remoting, you would need to configure authentication. This can be either of password-based authentication or public-key-based authentication. You are free to enable both; it is about what conventions your environment uses. The easiest method would be password-based authentication. This is done at $env:PROGRAMDATA\ssh\sshd_config in Windows and /etc/ssh/sshd_config in Linux. Set PasswordAuthentication and PubKeyAuthentication to yes.

Also, add the following Subsystem entry and restart the ssh* services:

Subsystem powershell <path-to-pwsh> -sshs -NoLogo -NoProfile

It is important to remember that PowerShell (or SSH for that matter) cannot override firewall configurations. Keep that in mind before attempting connections.

Once you have configured OpenSSH, the rest is the same as Windows-PowerShell-remoting. You can create sessions, save sessions, run commands in those sessions or even use Invoke-Command.

Go ahead and give PowerShell remoting a spin; you will get addicted to the efficiency.


  1. Authentication actually happens by means of a Kerberos token, not the credentials themselves ↩︎

  2. The process is known as de-serialisation ↩︎