powershellsessionconfigurationremoting

Powershell Core: Enter Powershell 5.1 Session


I have scripts that need PowerShell Core, but also need to use some ancient modules Microsoft won't bother to update for PowerShell Core (ActiveDirectory/GroupPolicy specifically), so it also needs to run some commands in PowerShell 5.1. Import-Module -UseWindowsPowerShell doesn't cut it, as it makes most information i need unaccessable through serialization.

So my idea was, use PSRemoting to make a new session running 5.1, and connect to this. Should be no problem using a session configuration that's targeting 5.1, right?

I quickly found out that there is no session configuration for 5.1 under Core by default. So i grabbed the default configuration for a 5.1 Session and tried to register it under Core:

$registerPSSessionConfigurationSplat = @{
    "RunAsPassword" = ""
    "ResourceUri" = "http://schemas.microsoft.com/powershell/microsoft.powershell"
    "Capability" = @("Shell")
    "PSVersion" = "5.1"
    "AutoRestart" = $false
    "ExactMatch" = $true
    "RunAsVirtualAccount" = $false
    "SDKVersion" = "2"
    "Uri" = "http://schemas.microsoft.com/powershell/microsoft.powershell"
    "MaxConcurrentCommandsPerShell" = "2147483647"
    "IdleTimeoutms" = "7200000"
    "ParentResourceUri" = "http://schemas.microsoft.com/powershell/microsoft.powershell"
    "RunAsUser" = ""
    "OutputBufferingMode" = "Block"
    "Architecture" = "64"
    "MaxMemoryPerShellMB" = "2147483647"
    "MaxProcessesPerShell" = "2147483647"
    "Filename" = "%windir%\\system32\\pwrshplugin.dll"
    "MaxShellsPerUser" = "2147483647"
    "MaxShells" = "2147483647"
    "SupportsOptions" = $true
    "lang" = "de-DE"
    "MaxIdleTimeoutms" = "2147483647"
    "xmlns" = "http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration"
    "Enabled" = $true
    "SecurityDescriptorSddl" = "O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;IU)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD)"
    "Name" = "Powershell.5.1"
    "ProcessIdleTimeoutSec" = "0"
    "MaxConcurrentUsers" = "2147483647"
    "UseSharedProcess" = $false
    "RunAsVirtualAccountGroups" = ""
    "XmlRenderingType" = "text"
    "Permission" = "NT-AUTORITÄT\\INTERAKTIV AccessAllowed", "VORDEFINIERT\\Administratoren AccessAllowed", "VORDEFINIERT\\Remoteverwaltungsbenutzer AccessAllowed"
}
Register-PSSessionConfiguration @registerPSSessionConfigurationSplat

It came back with this:

Cannot bind parameter 'PSVersion' to the target. Exception setting "PSVersion": "PowerShell remoting endpoint versioning is not supported on PowerShell Core.

Yea, thanks for nothing. I am out of ideas. What are my options to achieve my goal?

I have a workaround, sort of, by calling powershell.exe with the 5.1 specific code and parse the output, but that's likely prone to several formatting issues that might occur, and i would really like to avoid those.


Solution

  • If, from a PowerShell (Core) 7 session, you're looking to run code in a Windows PowerShell session locally, use the Windows PowerShell Compatibility feature:

    Caveat:

    A simple example:

    # ->, e.g.: '5.1.26100.2161'
    Invoke-Command -Session ($winPsSess = New-PSSession -UseWindowsPowerShell) {
      # Place all statements you want to be executed by *Windows PowerShell*
      # here.
      [string] $PSVersionTable.PSVersion
    }
    

    Note:


    As for your later comments:

    as i said, the Configuration "microsoft.powershell" doesn't exist for me on Core.

    While Get-PSSessionConfiguration (which must be run from an elevated session) reports available remoting end-point configurations, only in Windows PowerShell does it report the configurations for both PowerShell editions:


    once i figure out why Core isn't the default endpoint for remote sessions

    Indeed, using PowerShell remoting as of PowerShell (Core) 7.5.0 still targets Windows PowerShell on remote machines by default, unless overridden via a -ConfigurationName argument on the client side or via the $PSSessionConfigurationName preference variable.


    Optional reading: Why you should prefer the Windows PowerShell Compatibility feature to using PowerShell remoting for running Windows PowerShell code locally from a PowerShell 7 session:

    Note: I'm hazy on the lower-level details, but I'm hoping the big picture I'm painting is correct.

    The upshot: New-PSSession -UseWindowsPowerShell (the Windows PowerShell Compatibility feature) is preferable to loopback remoting for several reasons: