Sobre o PowerShell Editions

Descrição breve

Diferentes edições do PowerShell são executadas em runtimes subjacentes diferentes.

Descrição longa

Do PowerShell 5.1, há várias edições do PowerShell que são executadas em um runtime diferente do .NET. A partir do PowerShell 6.2, há duas edições do PowerShell:

  • Área de trabalho, que é executada em .NET Framework. O PowerShell 4 e abaixo, bem como o PowerShell 5.1 em edições completas do Windows, como Windows Desktop, Windows Server, Windows Server Core e a maioria dos outros sistemas operacionais Windows são edição desktop. Esta é a edição original do PowerShell.
  • Core, que é executado no .NET Core. O PowerShell 6.0 e superior, bem como o PowerShell 5.1 em algumas edições reduzidas do Windows, como Windows Nano Server e Windows IoT, em que .NET Framework não está disponível.

Como a edição do PowerShell corresponde ao seu runtime do .NET, ele é o principal indicador de compatibilidade de módulos do .NET E do .NET API; algumas APIs do .NET, tipos ou métodos não estão disponíveis em runtimes do .NET e isso afeta scripts e módulos do PowerShell que dependem deles.

A $PSEdition variável automática

No PowerShell 5.1 e acima, você pode descobrir qual edição você está executando com a $PSEdition variável automática:

$PSEdition
Core

No PowerShell 4 e abaixo, essa variável não existe. $PSEdition ser nulo deve ser tratado como o mesmo que ter o valor Desktop.

Edição em $PSVersionTable

A $PSVersionTable variável automática também tem informações de edição no PowerShell 5.1 e acima:

$PSVersionTable
Name                           Value
----                           -----
PSVersion                      6.2.0-rc.1
PSEdition                      Core           # <-- Edition information
GitCommitId                    6.2.0-rc.1
OS                             Microsoft Windows 10.0.18865
Platform                       Win32NT
PSCompatibleVersions           {1.0, 2.0, 3.0, 4.0...}
PSRemotingProtocolVersion      2.3
SerializationVersion           1.1.0.1
WSManStackVersion              3.0

O PSEdition campo terá o mesmo valor que a $PSEdition variável automática.

O campo de manifesto do CompatiblePSEditions módulo

Os módulos do PowerShell podem declarar quais edições do PowerShell são compatíveis com o uso do CompatiblePSEditions campo do manifesto do módulo.

Por exemplo, um manifesto de módulo declarando compatibilidade com as Desktop duas edições Core do PowerShell:

@{
    ModuleVersion = '1.0'
    FunctionsToExport = @('Test-MyModule')
    CompatiblePSEditions = @('Desktop', 'Core')
}

Um exemplo de um manifesto de módulo com apenas Desktop compatibilidade:

@{
    ModuleVersion = '1.0'
    FunctionsToExport = @('Test-MyModule')
    CompatiblePSEditions = @('Desktop')
}

Omitir o CompatiblePSEditions campo de um manifesto de módulo terá o mesmo efeito que defini-lo, uma vez que Desktopos módulos criados antes desse campo foram introduzidos implicitamente para esta edição.

Para módulos não enviados como parte do Windows (ou seja, módulos que você grava ou instala na galeria), esse campo é somente informativo; O PowerShell não altera o CompatiblePSEditions comportamento com base no campo, mas o PSModuleInfo expõe no objeto (retornado por Get-Module) para sua própria lógica:

New-ModuleManifest -Path .\TestModuleWithEdition.psd1 -CompatiblePSEditions Desktop,Core -PowerShellVersion '5.1'
$ModuleInfo = Test-ModuleManifest -Path .\TestModuleWithEdition.psd1
$ModuleInfo.CompatiblePSEditions
Desktop
Core

Observação

O CompatiblePSEditions campo do módulo só é compatível com o PowerShell 5.1 e superior. A inclusão desse campo fará com que um módulo seja incompatível com o PowerShell 4 e abaixo. Como o campo é puramente informativo, ele pode ser omitido com segurança em versões posteriores do PowerShell.

No PowerShell 6.1, Get-Module -ListAvailable seu formatador foi atualizado para exibir a compatibilidade de edição de cada módulo:

Get-Module -ListAvailable

    Directory: C:\Users\me\Documents\PowerShell\Modules

ModuleType Version    Name                   PSEdition ExportedCommands
---------- -------    ----                   --------- ----------------
Script     1.4.0      Az                     Core,Desk
Script     1.3.1      Az.Accounts            Core,Desk {Disable-AzDataCollection, Disable-AzContextAutosave, E...
Script     1.0.1      Az.Aks                 Core,Desk {Get-AzAks, New-AzAks, Remove-AzAks, Import-AzAksCreden...

...

Script     4.4.0      Pester                 Desk      {Describe, Context, It, Should...}
Script     1.18.0     PSScriptAnalyzer       Desk      {Get-ScriptAnalyzerRule, Invoke-ScriptAnalyzer, Invoke-...
Script     1.0.0      WindowsCompatibility   Core      {Initialize-WinSession, Add-WinFunction, Invoke-WinComm...

Compatibilidade de edição para módulos que são enviados como parte do Windows

Para módulos que vêm como parte do Windows (ou são instalados como parte de uma função ou recurso), o PowerShell 6.1 e acima tratam o CompatiblePSEditions campo de forma diferente. Esses módulos são encontrados no diretório de módulos do sistema Windows PowerShell (%windir%\System\WindowsPowerShell\v1.0\Modules).

Para módulos carregados ou encontrados neste diretório, o PowerShell 6.1 e superior usa o CompatiblePSEditions campo para determinar se o módulo será compatível com a sessão atual e se comporta de acordo.

Quando Import-Module é usado, um módulo sem Core entrada CompatiblePSEditions não será importado e um erro será exibido:

Import-Module BitsTransfer
Import-Module : Module 'C:\WINDOWS\system32\WindowsPowerShell\v1.0\Modules\BitsT
ransfer\BitsTransfer.psd1' does not support current PowerShell edition 'Core'.
Its supported editions are 'Desktop'. Use 'Import-Module -SkipEditionCheck' to i
gnore the compatibility of this module.
At line:1 char:1
+ Import-Module BitsTransfer
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo          : ResourceUnavailable: (C:\WINDOWS\system32\u2026r\BitsT
ransfer.psd1:String) [Import-Module], InvalidOperationException
+ FullyQualifiedErrorId : Modules_PSEditionNotSupported,Microsoft.PowerShell.Com
mands.ImportModuleCommand

Quando Get-Module -ListAvailable é usado, os módulos sem Core entrada CompatiblePSEditions não serão exibidos:

Get-Module -ListAvailable BitsTransfer
# No output

Em ambos os casos, o -SkipEditionCheck parâmetro de comutador pode ser usado para substituir esse comportamento:

Get-Module -ListAvailable -SkipEditionCheck BitsTransfer
    Directory: C:\WINDOWS\system32\WindowsPowerShell\v1.0\Modules

ModuleType Version    Name             PSEdition ExportedCommands
---------- -------    ----             --------- ----------------
Manifest   2.0.0.0    BitsTransfer     Desk      {Add-BitsFile, Complete-BitsTransfer, Get-BitsTransfer,...

Aviso

Import-Module -SkipEditionCheck pode parecer ter êxito para um módulo, mas usar esse módulo corre o risco de encontrar uma incompatibilidade posteriormente; enquanto o carregamento do módulo é inicialmente bem-sucedido, um comando pode chamar posteriormente uma API incompatível e falhar espontaneamente.

Criação de módulos do PowerShell para compatibilidade cruzada de edição

Ao escrever um módulo do PowerShell para direcionar as edições e Core as Desktop edições do PowerShell, há coisas que você pode fazer para garantir a compatibilidade entre edições.

No entanto, a única maneira verdadeira de confirmar e validar continuamente a compatibilidade é gravar testes para seu script ou módulo e executá-los em todas as versões e edições do PowerShell com as quais você precisa de compatibilidade. Uma estrutura de teste recomendada para isso é o Pester.

Script do PowerShell

Como um idioma, o PowerShell funciona da mesma forma entre as edições; são os cmdlets, módulos e APIs .NET que você usa que são afetados pela compatibilidade da edição.

Geralmente, os scripts que funcionam no PowerShell 6.1 e superior funcionarão com Windows PowerShell 5.1, mas há algumas exceções.

O módulo PSScriptAnalyzer versão 1.18.0 tem regras como PSUseCompatibleCommands e PSUseCompatibleTypes que são capazes de detectar o uso possivelmente incompatível de comandos e APIs .NET em scripts do PowerShell.

Assemblies .NET

Se você estiver escrevendo um módulo binário ou um módulo que incorpore DLLs (assemblies .NET) gerados a partir do código-fonte, você deverá compilar no .NET Standard e no PowerShell Standard para validação de compatibilidade em tempo de compilação da compatibilidade do .NET e da API do PowerShell.

Embora essas bibliotecas sejam capazes de verificar alguma compatibilidade no momento da compilação, elas não poderão capturar possíveis diferenças comportamentais entre as edições. Para isso, você ainda deve escrever testes.

Confira também