Virtualbox Windows tắt máy khách một cách duyên dáng


19

Tôi đang cố gắng tìm một giải pháp để tắt một cách duyên dáng bất kỳ máy ảo khách nào đang chạy trong VirtualBox Windows khi máy chủ bị tắt hoặc khởi động lại.

Có vẻ như tùy chọn an toàn nhất sẽ là kích hoạt lệnh "lưu trạng thái" khi máy chủ bắt đầu tắt, nhưng không rõ liệu máy chủ có đợi đủ lâu để VM hoàn thành việc lưu trạng thái và tắt nguồn hay không.

Có ai có một giải pháp mạnh mẽ cho vấn đề (dường như cơ bản) này không?


Cài đặt bổ sung khách? Điều đó không cung cấp các chức năng cần thiết?
Luke Luke REINSTATE MONICA của Canada

@CanadianLuke Nó không. :)
Matt Jenkins

Câu trả lời:


6

Tôi đã gặp một vấn đề tương tự và giải quyết nó bằng cách chạy VirtualBox như một dịch vụ:

http://vboxvmservice.sourceforge.net/

Với VBoxVMService, bạn có thể chọn cách bạn muốn máy tắt (Lưu trạng thái, tắt nguồn) và khởi động. Vì nó hoạt động như một dịch vụ, Windows sẽ tự động chờ nó tắt, trong quá trình tắt hệ thống.


Quá trình thiết lập không quá tự động trên Windows 10. Tôi phải tham khảo cách xử lý sự cố để xem có gì sai. Tuy nhiên, sau khi cấu hình đúng, phần mềm này thực hiện chính xác những gì tôi cần. Cảm ơn bạn cho bạn công việc tuyệt vời.
iuradz

3

Thật không may, điều đó dường như không thể xảy ra đối với các máy ảo được khởi động thông qua GUI VirtualBox. Mặc dù GUI có thể bắt sự kiện tắt máy chủ và phản ứng, dịch vụ VirtualBox bị chấm dứt: https://forums.virtualbox.org/viewtopic.php?p=278668#p278668

Nếu bạn không cần bảng điều khiển đồ họa, VBoxHeadlessTray hoặc VBoxVMService có thể là cách tốt nhất. Cả hai đều hỗ trợ lưu tự động và tiếp tục khi tắt máy chủ Windows và khởi động lại.

VirtualBox 5.0 giới thiệu chế độ khởi động "UI có thể tháo rời" . Chế độ này khởi động máy ảo không đầu với quy trình UI riêng. Hiệu suất đồ họa bị ảnh hưởng và tăng tốc 3D chưa được hỗ trợ. Nhưng có lẽ điều này có thể được kết hợp với VBoxHeadlessTray trong tương lai (VBoxHeadlessTray chưa hỗ trợ 5.0). Liên kết đến kho lưu trữ GitHub của VBoxHeadlessTrayyêu cầu kéo GitHub tương ứng để thêm hỗ trợ VirtualBox 5 .

Chỉnh sửa: VBoxVmService cũng không hỗ trợ chế độ có thể tháo rời mới kể từ phiên bản 5.0. Chỉ không đầu cho đến nay. Tôi đã thêm một yêu cầu tính năng cho điều đó.


Vì tôi không được phép chuyển nhiều hơn hai liên kết trên mỗi bài đăng, đây là các liên kết đến VBoxHeadlessTrayyêu cầu kéo GitHub tương ứng để thêm hỗ trợ VirtualBox 5.
Leo B

Tôi không trải nghiệm các vấn đề được nêu trong chủ đề. Xem câu trả lời của tôi về chủ đề này. Tôi có thể chạy máy chủ Windows tắt máy và bỏ đi. Tắt máy cho đến khi tất cả các máy ảo của tôi bị đóng và tôi đã thay đổi hành động mặc định để thực hiện tắt máy hoặc trạng thái lưu.
Kris Bahnsen

2

Tôi có 3 tập lệnh bó mà tôi sử dụng thay vì các nút nguồn startmenu.

do_shutdown.bat (tắt máy tính với thời gian chờ 10 giây, không cho thời gian 10 giây của vm để tiết kiệm, nhưng để cho phép tôi hủy tắt máy trong vòng 10 giây. Quá trình đếm ngược bắt đầu sau khi vm bị tắt)

"C:\VirtualBox\VBoxManage.exe" controlvm "Ubuntu Server" savestate
"C:\VirtualBox\VBoxManage.exe" controlvm "Ubuntu Minimal" savestate
shutdown /s /t 10

do_Vboot.bat (khởi động lại ngay sau khi vm bị tắt)

"C:\VirtualBox\VBoxManage.exe" controlvm "Ubuntu Server" savestate
"C:\VirtualBox\VBoxManage.exe" controlvm "Ubuntu Minimal" savestate
shutdown /r /t 0

do_cattery.bat (cho phép tôi hủy tắt máy tính trong vòng 10 giây chờ đợi. Sau đó, nó sẽ khởi động lại vm một lần nữa, vì chúng đã tắt với do_shutdown.bat)

shutdown /a
C:\VirtualBox\VBoxManage.exe startvm "Ubuntu Minimal" --type headless
C:\VirtualBox\VBoxManage.exe startvm "Ubuntu Server" --type headless

Thay vì savestatebạn cũng có thể sử dụng một trong những điều sau đây

poweroff        - pulls the plug
                  (probably not a good idea...)

acpipowerbutton - presses the power off button for a clean shutdown
                  ("The system is going down for power off NOW!" to all consoles)

acpisleepbutton - tells the os to go to sleep
                  (probably just as bad as poweroff)

1
Cảm ơn, điều này thật thú vị. Thật không may, có những kịch bản tắt / khởi động lại không thủ công khác mà tôi cũng cần phải xử lý. Ví dụ: khởi động lại theo lịch trình của Windows Update hoặc các sự kiện tắt / tắt pin yếu.
Matt Jenkins

1
Ồ được thôi. Ngoài ra còn có các Group Policy Editor với "Scripts (Startup / Shutdown)" phần lifehacker.com/... Tôi đang sử dụng mà một cho một lệnh rất ngắn trên tắt máy (một cuộc gọi curl), vì vậy tôi không biết làm thế nào nó cư xử trên các kịch bản mất một thời gian để hoàn thành.
Daniel F

2

Xin lỗi tôi đến bữa tiệc muộn. Có một câu trả lời chính xác cho điều này, mặc dù nó đòi hỏi một số dòng lệnh-foo. Xem bài đăng chủ đề này để biết thêm thông tin: https://forums.virtualbox.org/viewtopic.php?f=6&t=53684#p285540

Lệnh bạn đang tìm kiếm là:

"C: \ Chương trình tập tin \ Oracle \ VirtualBox \ VBoxManage.exe" setextradata "TÊN VM" GUI / DefaultCloseAction Tắt máy

Đây là những gì tôi sử dụng trên nhiều máy ảo, đóng cửa sổ và nó tự động tắt máy an toàn. Tắt Windows và trong nỗ lực đóng mọi thứ, nó sẽ đợi các quá trình này hoàn tất.


1

Tôi đã có một câu hỏi tương tự và tìm thấy trang này. Tôi không muốn chạy VirtualBox như một dịch vụ, vì tôi có rất nhiều máy ảo để thử nghiệm và thường chọn các máy ảo khác nhau để chạy trong VirtualBox UI. Khi tôi tắt máy tính, thật khó chịu khi lưu thủ công trạng thái của từng VM. Sử dụng các tập lệnh để lưu tất cả các máy ảo đang chạy dường như là một giải pháp thiết thực trong trường hợp này. Để làm cho câu trả lời của Daniel F tổng quát hơn, tôi đã viết các tập lệnh này tự động lưu trạng thái của tất cả các máy ảo đang chạy mà không đặt tên rõ ràng.

saveRastyVMs.bat cho Windows:

set VBoxManageEXE="%ProgramFiles%\Oracle\VirtualBox\VBoxManage.exe"
set ListRunningVMS=%VboxManageEXE% list runningvms
for /f tokens^=2^,4^ delims^=^" %%p in ('%ListRunningVMS%') do %VBoxManageEXE% controlvm %%p savestate

echo all vms saved, you can shutdown now.

rem shutdown /s /t 10

saveRastyVMs.sh cho Linux:

#!/bin/bash
vboxmanage list runningvms | while read line; do
  #echo "VBoxManage controlvm $uuid savestate;"
  echo $line
  if [[ $line =~ \{(.*)\} ]]
  then
    vboxmanage controlvm ${BASH_REMATCH[1]} savestate
  fi
done

0

Tôi đã tạo một tập lệnh python có thể tạm dừng tất cả các máy ảo VirtualBox đang chạy và sau đó thiết lập hệ thống để chạy tập lệnh khi đăng xuất như một tác vụ theo lịch trình.

Tôi không biết chính xác độ tin cậy của phương pháp này. Như những người khác đã lưu ý, có những giới hạn về thời gian hệ thống sẽ chờ đợi một nhiệm vụ Winlogon 7002 hoàn thành. Nhưng cá nhân tôi không gặp vấn đề gì với việc cung cấp các trạng thái lưu có thể sử dụng được ngay cả với nhiều máy ảo đang chạy trên 4 GB RAM VM tổng thể.

Dưới đây là các bước để thiết lập nó:

  1. Tải xuống và cài đặt Python 2.7.x từ python.org
  2. Tạo tệp kịch bản python ở đâu đó trên hệ thống của bạn bằng Notepad hoặc bất kỳ trình soạn thảo văn bản đơn giản nào khác (xem bên dưới)
  3. Mở lịch trình tác vụ
  4. Chọn hành động -> Tạo tác vụ cơ bản ... và sử dụng trình hướng dẫn để tạo tác vụ với các cài đặt sau
    • Tên bạn chọn
    • Bắt đầu tác vụ khi một sự kiện cụ thể được ghi lại
    • Nhật ký: Hệ thống
    • Nguồn: Winlogon
    • ID sự kiện: 7002
    • Bắt đầu một chương trình
    • Bên cạnh Chương trình / Tập lệnh , python.exeví dụ , nhập đường dẫn đầy đủ đếnc:\Python27\python.exe
    • Bên cạnh Thêm đối số , hãy nhập đường dẫn đầy đủ nơi bạn đặt tệp tập lệnh python, ví dụ tôi đặt tệp của tôi vào thư mục con của thư mục tài liệu của mình, vì vậy đây làC:\Users\rakslice\Documents\vboxsuspend\vboxsuspend.py
    • Chọn kết thúc.

Bây giờ máy ảo VirtualBox sẽ bị treo khi đăng xuất / khởi động lại / tắt máy.

Kịch bản python để thực hiện tắt máy dưới đây:

# A script to suspend all running VirtualBox VMs

import os

import subprocess

import sys


class VM(object):
    def __init__(self, name, uuid):
        self.name = name
        self.uuid = uuid

    def __repr__(self):
        return "VM(%r,%r)" % (self.name, self.uuid)


class VBoxRunner(object):
    def __init__(self):
        program_files = os.environ["ProgramW6432"]
        vbox_dir = os.path.join(program_files, "Oracle", "VirtualBox")
        self.vboxmanage_filename = os.path.join(vbox_dir, "VBoxManage.exe")

    def vbox_run(self, *args):
        subprocess.check_call([self.vboxmanage_filename] + list(args))

    def vbox_run_output(self, *args):
        return subprocess.check_output([self.vboxmanage_filename] + list(args))

    def list(self, running=True):
        if running:
            list_cmd = "runningvms"
        else:
            list_cmd = "vms"

        return [self.parse_vm_list_entry(x) for x in self.vbox_run_output("list", list_cmd).strip().split("\n")]

    def suspend_all(self):
        success = True
        stopped_some_vms = False
        vms = self.list(running=True)
        for vm in vms:
            if vm is None:
                continue
            # noinspection PyBroadException
            try:
                self.suspend_vm(vm)
            except:
                success = False
            else:
                stopped_some_vms = True
        if not stopped_some_vms:
            self.message("No running vms")
        return success

    @staticmethod
    def parse_vm_list_entry(x):
        """:type x: str"""
        if not x.startswith('"'):
            return None
        end_pos = x.find('"', 1)
        if end_pos == -1:
            return None
        name = x[1:end_pos]
        assert x[end_pos + 1: end_pos + 3] == " {"
        assert x.endswith("}")
        uuid = x[end_pos + 2:]

        return VM(name, uuid)

    @staticmethod
    def message(msg):
        print >>sys.stderr, msg

    def suspend_vm(self, vm):
        assert isinstance(vm, VM)
        self.vbox_run("controlvm", vm.uuid, "savestate")


def main():
    vr = VBoxRunner()
    success = vr.suspend_all()
    if not success:
        sys.exit(1)


if __name__ == "__main__":
    main()

1
Đề xuất của người khác về việc sử dụng tập lệnh bó mà bạn có thể chạy thủ công, những người hiểu biết và sau đó tắt máy là tuyệt vời nếu phù hợp với trường hợp sử dụng của bạn. Nhưng điều tôi thực sự muốn này là khởi động lại tự động Windows Update, sau khi máy ảo tôi đang làm việc bị tắt nguồn qua đêm bởi Windows Update khởi động lại trong hai ngày liên tiếp ...
rakslice
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.