Add reboot cap for windows
This commit introduces a proper reboot cap for Windows guests. Once it initiates a reboot on the guest, it calls out to the wait_for_reboot cap to block on until the guest is finished rebooting.
This commit is contained in:
parent
54c8ebc31a
commit
142a6898bc
|
@ -4,8 +4,6 @@ module VagrantPlugins
|
|||
module GuestWindows
|
||||
module Cap
|
||||
module ChangeHostName
|
||||
MAX_REBOOT_DURATION = 120
|
||||
|
||||
def self.change_host_name(machine, name)
|
||||
change_host_name_and_wait(machine, name, machine.config.vm.graceful_halt_timeout)
|
||||
end
|
||||
|
@ -20,9 +18,6 @@ module VagrantPlugins
|
|||
script = <<-EOH
|
||||
$computer = Get-WmiObject -Class Win32_ComputerSystem
|
||||
$retval = $computer.rename("#{name}").returnvalue
|
||||
if ($retval -eq 0) {
|
||||
shutdown /r /t 5 /f /d p:4:1 /c "Vagrant Rename Computer"
|
||||
}
|
||||
exit $retval
|
||||
EOH
|
||||
|
||||
|
@ -31,24 +26,7 @@ module VagrantPlugins
|
|||
error_class: Errors::RenameComputerFailed,
|
||||
error_key: :rename_computer_failed)
|
||||
|
||||
|
||||
wait_remaining = MAX_REBOOT_DURATION
|
||||
begin
|
||||
# Don't continue until the machine has shutdown and rebooted
|
||||
if machine.guest.capability?(:wait_for_reboot)
|
||||
machine.guest.capability(:wait_for_reboot)
|
||||
else
|
||||
@logger.debug("No wait_for_reboot capability, sleeping for #{sleep_timeout} instead...")
|
||||
# use graceful_halt_timeout only if guest cannot wait for reboot
|
||||
sleep(sleep_timeout)
|
||||
end
|
||||
rescue Vagrant::Errors::MachineGuestNotReady => e
|
||||
raise if wait_remaining < 0
|
||||
@logger.warn("Machine not ready, cannot wait for reboot yet. Trying again")
|
||||
sleep(5)
|
||||
wait_remaining -= 5
|
||||
retry
|
||||
end
|
||||
machine.guest.capability(:reboot)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,21 +1,50 @@
|
|||
require "log4r"
|
||||
|
||||
module VagrantPlugins
|
||||
module GuestWindows
|
||||
module Cap
|
||||
class Reboot
|
||||
def self.wait_for_reboot(machine)
|
||||
# Technically it should be possible to make it work with SSH
|
||||
# too, but we don't yet.
|
||||
return if machine.config.vm.communicator != :winrm
|
||||
MAX_REBOOT_RETRY_DURATION = 120
|
||||
|
||||
def self.reboot(machine)
|
||||
@logger = Log4r::Logger.new("vagrant::windows::reboot")
|
||||
reboot_script = "shutdown /r /t 5 /f /d p:4:1 /c \"Vagrant Reboot Computer\""
|
||||
|
||||
comm = machine.communicate
|
||||
|
||||
script = File.expand_path("../../scripts/reboot_detect.ps1", __FILE__)
|
||||
script = File.read(script)
|
||||
while machine.communicate.execute(script, error_check: false) != 0
|
||||
if comm.test(script, error_check: false, shell: :powershell)
|
||||
@logger.debug("Issuing reboot command for guest")
|
||||
comm.execute(reboot_script, shell: :powershell)
|
||||
else
|
||||
@logger.debug("A reboot is already in progress")
|
||||
end
|
||||
|
||||
@logger.debug("Waiting for machine to finish rebooting")
|
||||
|
||||
wait_remaining = MAX_REBOOT_RETRY_DURATION
|
||||
begin
|
||||
wait_for_reboot(machine)
|
||||
rescue Vagrant::Errors::MachineGuestNotReady, WinRM::WinRMHTTPTransportError => e
|
||||
raise if wait_remaining < 0
|
||||
@logger.warn("Machine not ready, cannot start reboot yet. Trying again")
|
||||
sleep(5)
|
||||
wait_remaining -= 5
|
||||
retry
|
||||
end
|
||||
end
|
||||
|
||||
def self.wait_for_reboot(machine)
|
||||
script = File.expand_path("../../scripts/reboot_detect.ps1", __FILE__)
|
||||
script = File.read(script)
|
||||
while machine.communicate.execute(script, error_check: false, shell: :powershell) != 0
|
||||
sleep 10
|
||||
end
|
||||
|
||||
# This re-establishes our symbolic links if they were
|
||||
# created between now and a reboot
|
||||
machine.communicate.execute("net use", error_check: false)
|
||||
machine.communicate.execute("net use", error_check: false, shell: :powershell)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -64,6 +64,11 @@ module VagrantPlugins
|
|||
Cap::Reboot
|
||||
end
|
||||
|
||||
guest_capability(:windows, :reboot) do
|
||||
require_relative "cap/reboot"
|
||||
Cap::Reboot
|
||||
end
|
||||
|
||||
guest_capability(:windows, :choose_addressable_ip_addr) do
|
||||
require_relative "cap/choose_addressable_ip_addr"
|
||||
Cap::ChooseAddressableIPAddr
|
||||
|
|
|
@ -17,6 +17,12 @@ describe "VagrantPlugins::GuestWindows::Cap::Reboot" do
|
|||
allow(config).to receive(:vm).and_return(vm)
|
||||
end
|
||||
|
||||
describe ".reboot" do
|
||||
before do
|
||||
allow(vm).to receive(:communicator).and_return(:winrm)
|
||||
end
|
||||
end
|
||||
|
||||
describe "winrm communicator" do
|
||||
before do
|
||||
allow(vm).to receive(:communicator).and_return(:winrm)
|
||||
|
@ -24,15 +30,15 @@ describe "VagrantPlugins::GuestWindows::Cap::Reboot" do
|
|||
|
||||
describe ".wait_for_reboot" do
|
||||
it "runs reboot detect script" do
|
||||
expect(communicator).to receive(:execute).with(/# Function/, { error_check: false }).and_return(0)
|
||||
expect(communicator).to receive(:execute).with(/# Function/, { error_check: false, shell: :powershell }).and_return(0)
|
||||
allow(communicator).to receive(:execute)
|
||||
|
||||
described_class.wait_for_reboot(machine)
|
||||
end
|
||||
|
||||
|
||||
it "fixes symlinks to network shares" do
|
||||
allow(communicator).to receive(:execute).and_return(0)
|
||||
expect(communicator).to receive(:execute).with('net use', { error_check: false })
|
||||
expect(communicator).to receive(:execute).with('net use', { error_check: false, shell: :powershell })
|
||||
|
||||
described_class.wait_for_reboot(machine)
|
||||
end
|
||||
|
@ -45,8 +51,9 @@ describe "VagrantPlugins::GuestWindows::Cap::Reboot" do
|
|||
end
|
||||
|
||||
describe ".wait_for_reboot" do
|
||||
it "does not execute Windows reboot detect script" do
|
||||
expect(communicator).to_not receive(:execute)
|
||||
it "does execute Windows reboot detect script" do
|
||||
expect(communicator).to receive(:execute).with(/# Function/, { error_check: false, shell: :powershell }).and_return(0)
|
||||
expect(communicator).to receive(:execute).with('net use', { error_check: false, shell: :powershell })
|
||||
described_class.wait_for_reboot(machine)
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Reference in New Issue