Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Loops Powershell/PowerCLI循环、超时和退出_Loops_Powershell_Timeout_Powercli - Fatal编程技术网

Loops Powershell/PowerCLI循环、超时和退出

Loops Powershell/PowerCLI循环、超时和退出,loops,powershell,timeout,powercli,Loops,Powershell,Timeout,Powercli,以下是场景-我正在通过Powershell/PowerCLI(VMwares Powershell模块)远程启动VM,一旦启动VM,我将针对VM运行一系列cmdlet 目前我有以下代码: Start-VM "my VM Name" -runAsync $vm = Get-VM | where { $_.name -eq "my VM Name" } start-sleep -seconds 20 do { start-sleep -seconds 5 $toolsSta

以下是场景-我正在通过Powershell/PowerCLI(VMwares Powershell模块)远程启动VM,一旦启动VM,我将针对VM运行一系列cmdlet

目前我有以下代码:

Start-VM "my VM Name" -runAsync
$vm = Get-VM | where { $_.name -eq "my VM Name" }    

start-sleep -seconds 20
do {
    start-sleep -seconds 5
    $toolsStatus = ($VM | Get-View).Guest.ToolsStatus
} until ($toolsStatus -eq 'toolsOK')
哪种方法有效-虚拟机启动,循环将检查,直到VMware Tools向VMware报告(这意味着虚拟机已完全启动到操作系统中)

但是,这将无限期地运行,因此在VM无法成功引导的情况下,脚本将挂起。因此,我尝试添加一个计时器,以便在脚本运行超过5分钟时退出脚本:

Start-VM "My VM Name" -runAsync
$VM = Get-VM | where { $_.name -eq "My VM Name" }

$timeout = new-timespan -minutes 5
start-sleep -seconds 5
$toolsStatus = ($VM | Get-View).Guest.ToolsStatus
$sw = [diagnostics.stopwatch]::StartNew()
while ($sw.elapsed -lt $timeout) {
    if ($toolsStatus -eq 'toolsOK') {
        return
    }
    start-sleep -seconds 5
}
Exit
在5分钟后成功退出脚本。问题是,当我测试这个时,VM已经启动,我得到一个响应,表明VMtools已经响应,但是循环没有停止。它一直持续到超时,然后退出,而不是继续下一步


我以前从未使用过这种类型的循环,因此希望您能提供一些输入,因为我确信我已经接近了-但我错过了一些东西。

应该只是一个简单的逻辑修复。在最后的
while
循环中,使用
-和
添加两个表达式,并否定
$toolStatus

while ($sw.elapsed -lt $timeout -and $toolsStatus -ne 'toolsOK'){
    start-sleep -seconds 5
}

当一个变为false时,循环将结束。

您没有更新循环中的
$toolsStatus
,因此即使VM已启动,它也不会退出。只需将支票移到循环内即可

Start-VM "My VM Name" -runAsync
$VM = Get-VM | where { $_.name -eq "My VM Name" }

$timeout = new-timespan -minutes 5
start-sleep -seconds 5
$sw = [diagnostics.stopwatch]::StartNew()
while ($sw.elapsed -lt $timeout) {
    $toolsStatus = ($VM | Get-View).Guest.ToolsStatus
    if ($toolsStatus -eq 'toolsOK') {
        return
    }
    start-sleep -seconds 5
}
Exit

VMWare已经有了等待命令

Start-VM "My VM Name" -runAsync
$VM = Get-VM | where { $_.name -eq "My VM Name" } | Wait-Tools -TimeoutSeconds 180

我读过关于VMTools运行和操作系统未启动的问题。一旦Windows徽标出现,VMTools似乎报告正在运行,这可能会导致问题。我更喜欢使用Powershell命令ping机器,直到得到响应

$thisisaddress = (Get-NetIPAddress | where {$_.AddressFamily -eq "IPv4" -and $_.InterfaceAlias -eq "Ethernet"}).ipaddress

$pingMachine = New-Object System.Net.NetworkInformation.Ping

$timeout = new-timespan -Minutes 1
$sw = [diagnostics.stopwatch]::StartNew()
while ($sw.elapsed -lt $timeout -and $pingStatus.Status -ne 'Success'){
    $pingStatus = $pingMachine.Send($thisisaddress)
    $pingStatus
}

啊!!我以为我错过了什么东西——这修复了我的循环!我没有意识到它的存在!对于这个问题,我已经实现了您的解决方案,因为它更加优雅。然而,我已经将另一个答案标记为正确的,因为它解决了我原始脚本中的语法/逻辑错误(我觉得这对其他正在处理超时循环的人更有用)您对VM的搜索非常慢。对不起,它看起来很差。尝试以下度量命令{Get VM |其中{$$$$.name-eq“yourvmname”}}TotalSeconds:18.5221952度量命令{Get VM-name yourvmname}TotalSeconds:6.229672度量命令{Get view-viewtype VirtualMachine-filter@{“name”=“yourvmname”}TotalSeconds:1.2584678度量命令{Get view-viewtype VirtualMachine-property name-filter@{“name”=“yourvmname”}}总秒数:1.2559065