web-dev-qa-db-ja.com

1つの使いやすいbashコマンド(bashファイルに配置できる)ですべてのVirtualBox(迷走)VMをシャットダウンする

開発には vagrant を使用します。いくつかのVMをシャットダウンするのを忘れています。ホストマシンからログアウトすると、Ubuntuのシャットダウンプロセスがハングしたように見えます。

コマンドラインのフーを使って、すべての浮浪者ボックスを閉じるスクリプトを作成する方法はありますか?次のようなものですが、うまくいくものです。

for f in $HOME/vagrant;
do;
  cd $f
  vagrant halt
done;
70
Rick

Virtual Boxマシンのスクリプト可能なコントロールの場合、VBoxManageコマンドを使用できます。

  • 実行中のマシンのリスト(名前とUUIDを返します):

    VBoxManage list runningvms
    
  • VMを「休止」して実行を停止します(データの損失を防ぐために推奨)

    VBoxManage controlvm <name|uuid> savestate
    
  • VMのパワーオフ(ゲストのデータを失う可能性があるため推奨されません)

    VBoxManage controlvm <name|uuid> poweroff
    
  • ACPI対応のゲストOSでACPIを使用します(ゲストの正常なシャットダウンにはpoweroffより望ましい)

    VBoxManage controlvm <name|uuid> acpipowerbutton
    

次も参照してください: コマンドラインを使用してVirtualBoxでゲストOSを安全にシャットダウンする方法

OPからの更新

以下のこの選択された正解に基づいて、このbashスクリプト「$HOME/bin/stop-vagrant.sh」を追加しました。そのため、セッションで忘れてしまった可能性のあるすべての迷惑なVMを安全に停止できるようになりました。

vboxmanage list runningvms | sed -r 's/.*\{(.*)\}/\1/' | xargs -L1 -I {} VBoxManage controlvm {} savestate

コマンドの説明:

vboxmanage list runningvms |-VirtualBoxで実行中のすべてのvmsのリストを取得します

sed -r 's/.*\{(.*)\}/\1/' |-ID番号まで文字列を削除します

xargs -L1 -I {} VBoxManage controlvm {} savestate-開いている各ボックスで状態保存コマンドを実行します。

xargs

  • -L1-一度に1行取る
  • -I {}-次のコマンドのプレースホルダーとして{}を使用します
89
Takkat

もう1つの答えはVirtualboxを処理するのに最適ですが、Vagrantは仮想マシンを処理する独自のメカニズムを備えており、コメントの1つで述べたように、VirtualBoxだけでなく、現時点では単なるVMWareをサポートしていますが、後で知っています!

これは私のために働くようです:

vagrant global-status | awk '/running/{print $1}' | xargs -r -d '\n' -n 1 -- vagrant suspend

注:

これは1.6以降のVagrantバージョンで動作します。古いバージョンの場合、おそらくアップグレードする必要がありますが、できない場合は、Virtualboxに焦点を当てた他のオプションのいずれかが優れている可能性があります。

22
ThomasRedstone

これの私のメカニズム:

vagrant global-status | grep virtualbox | cut -c 1-9 | while read line; do echo $line; vagrant halt $line; done;

  • global-statusはすべてのボックスをリストします
  • virtualboxを含む行をフィルターします(ヘルプテキストを除外し、他のプロバイダーを使用している場合は中断します)
  • 最初の9文字(グローバルな一意のID)のみを表示するようにフィルターします
  • その入力から行を読み取ることはできますが、変数$ lineとして読み取ってください:
    • その$ lineを印刷する
    • vagrant halt $lineを実行して、そのグローバルな一意のIDの浮浪者を停止します

これは、vagrantで構成されたシャットダウンメカニズムも実行するため、上記のVirtualboxメソッドよりも優れています。

11
Aquarion

他の人がこの質問に答える場合:VirtualBoxを使用している人は、すでにこれを処理できます。ファイルの編集のみが必要です。

# Contents of /etc/default/virtualbox
# ...
# ...
# SHUTDOWN_USERS="foo bar"  
#   check for running VMs of user 'foo' and user 'bar'
#   'all' checks for all active users
# SHUTDOWN=poweroff
# SHUTDOWN=acpibutton
# SHUTDOWN=savestate
#   select one of these shutdown methods for running VMs
#   acpibutton and savestate causes the init script to wait
#   30 seconds for the VMs to shutdown

## My original values
# SHUTDOWN_USERS=""
# SHUTDOWN=poweroff

## My current values
SHUTDOWN_USERS="all"
SHUTDOWN=savestate

利点は、他の回答に投稿されたコマンドを実行するためにログアウトまたはinit.d striptを編集/作成する必要がないことです。欠点は、このソリューションがVirtualBoxに固有であるということです。

VirtualBox 4.3.18を使用したUbuntu 14.10でテスト済み。

すべてのクレジットは この投稿 に送られます。

他のいくつかの答えを組み合わせると、実行中のすべてのvirtualbox vagrantボックスが閉じられます:

vagrant global-status | awk '/virtualbox running/{ print $1 }' | xargs vagrant halt
4
Ryan

vagrant haltを使用しています。追加の引数なしで実行すると、Vagrantfileで定義されているすべてのマシンが停止します。

3
nomen

Vagrantコマンドを解析するスクリプトを作成している場合は、より一貫性のあるマシンフレンドリーな出力(--machine-readable)を解析することをお勧めします。

形式は次のとおりです。

timestamp,target,type,data...

カンマ区切りであるため、CSVファイルとしてインポートできます。

シェルでは、たとえば次のように解析するのがおそらく困難です。

for id in $(vagrant global-status --machine-readable | cut -d, -f5 | grep -B3 running | egrep -o "[0-9a-f]{7}"); do
    vagrant suspend $id;
done

参照: Vagrant-機械可読出力


ただし、標準出力を解析する方が簡単です。

while read id name provider state path; do
  [ "$state" = "running" ] && vagrant suspend $id;
done < <(vagrant global-status)

ところで理論的にはvagrantコマンドは、このGH post に従って一時停止するVMのリストの正規表現を受け入れる必要があります。次に例を示します。

vagrant suspend '*'

しかし、それは機能せず、修正するために保留中の bug#7221 があります。


関連するGitHubチケット:

1
kenorb

これはあなたのために働くかもしれないし、そうでないかもしれない;-)私のために働く

vagrant_halt_all.sh

#!/usr/bin/env bash
if [ -z "$1" ]
then
  OPTS=""
else
  # force close if any arg passed
  OPTS="-f"
fi

for i in $(vagrant global-status | grep running | awk '{print $1}'); do 
  DIR=$(vagrant global-status | grep running | awk '{print $5}')
  cd "$DIR";
  OUT=$(vagrant halt);
  echo "attempted to halt $i: $OUT"
done
0
brad parks