Hi,
I have a script to detach CD/DVD for all VMs running on the specified datastore and print the result if successful or not.
My problem is for one of the VM, the script paused and I have the following "Virtual Machine Message" in vCenter:
"The guest operating system has locked the CD-ROM door and is probably using the CD-ROM, which can prevent the guest from recognizing media changes. If possible, eject the CD-ROM from inside the guest before disconnecting. Disconnect anyway and override the lock?"
The answer could be yes or no but I have to click manually.
How can I insert in my script to continue the process by answering yes or no automatically?
The VM is a Cisco VSG VM and has a CD/DVD attached that is connected and that connect at power on (ISO image is located on the VM folder).
My goal is to move all the VMs running on this datastore to another datastore and I would like to make sure no CD/DVD are attached to them.
I have noticed that when I move this particular Cisco VM to another datastore, the ISO image move at the same time. Not true for other VMs with Media attached to them (e.g. Windows VM with a Windows ISO image attached).
So what I would like is to detach CD/DVD from all VMs and if it's a Cisco VM, answer to the Virtual Machine Message in VC by yes or no for the script to continue.
Thank you for your help.
The script wait for the an answer to the question in VC.
If I open a new powershell script command window, I am able to answer VM questions with the following command:
get-VM | Get-VMQuestion | Set-VMQuestion -Option "No" -Confirm:$false
What I would like is to have the script continuing and answering the questions one by one automatically.
My problem is that the script stops and wait for an answer just before I can set up the answer to the question.
And before to run the command to set the CD/DVD to NoMedia, there is no question asked.
How can I script something like:
If (mycommand return question)
{
set answer to the question
run the command
}
Cheers.
I would like to bump this question as I cannot find an answer to this either.
Have a look at Answer the question!
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
LucD
I used your Set-CDDriveAndAnswer function, but since I have to powershell to all my vCenters through firewalls and with AD accounts in different domains for each, I found your version was causing me trouble with the Start-Job call, without adding a section to reconnect to the vCenter with creds. So I offer the following update that allows the operation to succeed sequentially in spite of the need to answer the vCenter question.
Function Set-CDDriveAndAnswer{
<#
.SYNOPSIS Unmounts a CD/DVD from a VM and answers an outstanding question
.DESCRIPTION The function will unmount a CD/DVD from a DVD.
If the unmount causes a question, the function will answer the question.
.NOTES Authors: Luc Dekens, David A. Stewart
.PARAMETER VM
The DisplayName of the VM
.PARAMETER Server
The vSphere Server on which the VM is located.
The default is $global:defaultviserver
.EXAMPLE
PS> Set-CDDriveAndAnswer -VM MyVM -Server $global:DefaultVIServer
.EXAMPLE
PS> Get-VM | Set-CDDriveAndAnswer
#>
[CmdletBinding()]
param(
[Parameter(Mandatory=$True,ValueFromPipeline=$True,ValueFromPipelinebyPropertyName=$True)]
[string[]]$VM
)
$objVM = Get-VM $VM
$vCenter = $objVM | %{$_.Uid.Substring($_.Uid.Indexof('@')+1).split(":")[0]}
$VMView = $objVM | Get-View
$driveName = "CD/DVD Drive 1"
$dev = $VMView.Config.Hardware.Device | where {$_.DeviceInfo.Label -eq $driveName}
If($dev){
$spec = New-Object VMware.Vim.VirtualMachineConfigSpec
$spec.deviceChange = New-Object VMware.Vim.VirtualDeviceConfigSpec[] (1)
$spec.deviceChange[0] = New-Object VMware.Vim.VirtualDeviceConfigSpec
$spec.deviceChange[0].operation = "edit"
$spec.deviceChange[0].device = $dev
$spec.deviceChange[0].device.backing = New-Object VMware.Vim.VirtualCdromIsoBackingInfo
$spec.deviceChange[0].device.Connectable = New-Object VMware.Vim.VirtualDeviceConnectInfo
$spec.deviceChange[0].device.Connectable.Connected = "false"
$spec.deviceChange[0].device.backing.fileName = ""
$VMView.ReconfigVM_Task($spec)
$maxPass = 30
$pass = 0
while($pass -lt $maxPass){
$question = ""
$question = Get-VM $VM -server $vCenter | Get-VMQuestion -QuestionText "*locked the CD-ROM*"
If($question){
Set-VMQuestion -VMQuestion $question -Option button.yes -Confirm:$False -ErrorAction SilentlyContinue | Out-Null
}
$pass++
IF(!(Get-VM $VM -server $vCenter | Get-CDDrive)){$pass = $maxPass}
}
}
}
Nice ![]()
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Been testing more. Depending on vCenter version the Answer options for the question have changed, therefore I added a change to capture and use the correct option.
Function Set-CDDriveAndAnswer{
<#
.SYNOPSIS Unmounts a CD/DVD from a VM and answers an outstanding question
.DESCRIPTION The function will unmount a CD/DVD from a DVD.
If the unmount causes a question, the function will answer the question.
.NOTES Authors: Luc Dekens, David A. Stewart
.PARAMETER VM
The DisplayName of the VM
.PARAMETER Server
The vSphere Server on which the VM is located.
The default is $global:defaultviserver
.EXAMPLE
PS> Set-CDDriveAndAnswer -VM MyVM -Server $global:DefaultVIServer
.EXAMPLE
PS> Get-VM | Set-CDDriveAndAnswer
#>
[CmdletBinding()]
param(
[Parameter(Mandatory=$True,ValueFromPipeline=$True,ValueFromPipelinebyPropertyName=$True)]
[string[]]$VM
)
$objVM = Get-VM $VM
$vCenter = $objVM | %{$_.Uid.Substring($_.Uid.Indexof('@')+1).split(":")[0]}
IF($objVM | Get-CDDrive | ?{$_.IsoPath -AND ($_.ConnectionState.Connected -match "True")}){
$VMView = $objVM | Get-View
$driveName = "CD/DVD Drive 1"
$dev = $VMView.Config.Hardware.Device | where {$_.DeviceInfo.Label -eq $driveName}
If($dev){
$spec = New-Object VMware.Vim.VirtualMachineConfigSpec
$spec.deviceChange = New-Object VMware.Vim.VirtualDeviceConfigSpec[] (1)
$spec.deviceChange[0] = New-Object VMware.Vim.VirtualDeviceConfigSpec
$spec.deviceChange[0].operation = "edit"
$spec.deviceChange[0].device = $dev
$spec.deviceChange[0].device.backing = New-Object VMware.Vim.VirtualCdromRemoteAtapiBackingInfo
$spec.deviceChange[0].device.backing.DeviceName = ""
$spec.deviceChange[0].device.backing.UseAutoDetect = "false"
$spec.deviceChange[0].device.Connectable = New-Object VMware.Vim.VirtualDeviceConnectInfo
$spec.deviceChange[0].device.Connectable.Connected = "false"
$VMView.ReconfigVM_Task($spec)
$maxPass = 30
$pass = 0
Write-Host -NoNewLine "$VM Pass.."
while($pass -lt $maxPass){
$question = ""
$question = Get-VM $VM -server $vCenter | Get-VMQuestion -QuestionText "*locked the CD-ROM*"
If($question){
$Option = ($question.Options | ?{$_.Summary -match "Yes"} | Select -ExpandProperty Label)
Set-VMQuestion -VMQuestion $question -Option "$Option" -Confirm:$False -ErrorAction SilentlyContinue | Out-Null
}
$pass++
Write-Host -NoNewLine "$pass.."
IF(!(Get-VM $VM -server $vCenter | Get-CDDrive | ?{$_.IsoPath -AND ($_.ConnectionState.Connected -match "True")})){$pass = $maxPass; Write-Host "CD/DVD clear on $VM"}
}
IF(Get-VM $VM -server $vCenter | Get-CDDrive | ?{$_.IsoPath -AND ($_.ConnectionState.Connected -match "True")}){Write-Host "CD/DVD still connected on $VM"}
}
}Else{Write-Host "CD/DVD Not connected on $VM"}
}
Thank you for this. I've done a few patches on my vCenters and I just got word that the original function wasn't working. I was about to start digging into fixing the code when I thought I should check back here to see if there were any updates. Thank you for the work. It's working as designed.
Cheers!
