如果ComputerName是localhost或'。',则将Powershell脚本作为本地脚本运行。

问题描述 投票:2回答:3

我有这个脚本,应该可以在远程和本地主机上运行。它接受-ComputerName作为带有'。'的参数。 (localhost)作为默认设置。

目前,我正在测试如何验证新的远程会话,并为此编写了一个小cmdlet。问题是,如果我使用“。”运行此脚本,或localhost作为ComputerName,脚本将尝试连接到我的计算机上的新远程会话。由于我未启用PSRemoting,因此无法使用。

这是我的测试脚本:

Function Test-PsRemoting {
[CmdletBinding()]
param(
    $ComputerName = ".",
    $Credentials    
)

$ErrorActionPreference = "Stop"

Test-Connection -ComputerName $ComputerName -Count 1 | 
    Format-List -Property PSComputerName,Address,IPV4Address,IPV6Address

Test-WSMan $ComputerName

$session = New-PSSession -ComputerName $ComputerName -Credential $Credentials
Invoke-Command -ComputerName $computername { 1 }
}

所有命令,Test-WSMan,New-PSSession和Invoke-Command都会失败,因为它们假设我想建立远程连接

如果$ ComputerName为',是否可以让Powershell在本地会话中运行命令。或localhost还是必须自己在if / else子句中处理?

该脚本旨在在本地和远程计算机上运行,​​并且我不希望启用PSRemoting成为在本地运行脚本的必要条件

powershell powershell-remoting
3个回答
2
投票

AFAIK没有$localsession变量。您可以使用if-tests:

Function Test-PsRemoting {
    [CmdletBinding()]
    param(
        $ComputerName = ".",
        $Credentials    
    )

    $ErrorActionPreference = "Stop"

    $remote = $ComputerName -notmatch '\.|localhost'
    $sc = { 1 }

    #If remote computer, test connection create sessions
    if($remote) {
        Test-Connection -ComputerName $ComputerName -Count 1 | 
            Format-List -Property PSComputerName,Address,IPV4Address,IPV6Address

        Test-WSMan $ComputerName

        $session = New-PSSession -ComputerName $ComputerName -Credential $Credentials
    }

    if($remote) {
        #If remote computer
        Invoke-Command -ComputerName $computername -ScriptBlock $sc
    } else { 
        #Localhost
        Invoke-Command -ScriptBlock $sc
    }

}

0
投票

[您似乎正在尝试检查PowerShell远程处理是否已在计算机上启用/正在工作。如果您不希望yoru函数在本地计算机上运行,​​则可以过滤掉本地计算机,或者让调用Test-PsRemoting的人将其传递给非本地计算机名称。如果他们确实通过了本地计算机,那么他们将得到未启用PowerShell Remoting的结果。

function Test-PsRemoting 
{
    [CmdletBinding()]
    param(
        [Parameter(Mandatory=$true)]
        [string[]]
        # The computers to check.
        $ComputerName,

        [Management.Automation.PSCredential
        # The credentials to use to connect to the computers.
        $Credentials    
    )

    # Filter out local computer names
    $ComputerName = $ComputerName | Where-Object { $_ -ne '.' -and $_ -ne $env:COMPUTERNAME }

    Test-Connection -ComputerName $ComputerName -Count 1 | 
        Format-List -Property PSComputerName,Address,IPV4Address,IPV6Address

    $credentialsParam = @{ }
    if( $Credentials )
    {
        $credentialsParam.Credentials = $Credentials
    }

    Test-WSMan -ComputerName $ComputerName @credentialsParam

    Invoke-Command -ComputerName $ComputerName { hostname } @credentialsParam
}

0
投票

响应其他人偶然发现的旧线程。 Frode的答案很好用,但是我也想分享自己的解决方案,因为它更易于维护。如果定义了ComputerName参数,则该函数将远程调用自身。

这不适用于所有脚本,您需要小心避免递归错误。这是一个简单的例子:

function Invoke-LocalOrRemote
{
    param
    (
        [string]$ExampleArgument,
        [string]$ComputerName
    )

    # Invoke the function remotely if a valid computer name is defined
    if ( $ComputerName -and ( Test-Connection $ComputerName -Count 1 -ErrorAction SilentlyContinue ) )
    {
        return Invoke-Command -ComputerName $ComputerName -ScriptBlock ${function:Invoke-LocalOrRemote} -ArgumentList $ExampleArgument
    }
    elseif ( $ComputerName ) { return "Error: Could not connect to remote computer '$ComputerName'" }

    # Actual function contents
    return "Function run with argument '$ExampleArgument' on computer '$($env:COMPUTERNAME)'"
}
© www.soinside.com 2019 - 2024. All rights reserved.