0

WMI を使用して Windows 8 システムのエクスポートから Hyper-V システム定義をロードしようとしています。これまでのところ、私はこれを持っています:

var managementScope = new ManagementScope(@"root\virtualization\v2");
var invokeMethodOptions = new InvokeMethodOptions();
invokeMethodOptions.Timeout = new TimeSpan(0, 0, 10);
using (var managementService = WmiUtilities.GetVirtualMachineManagementService(managementScope)) {
    var inParameters = managementService.GetMethodParameters(@"ImportSystemDefinition");
    inParameters["SystemDefinitionFile"] = filePath;
    inParameters["SnapshotFolder"] = snapshotPath;
    inParameters["GenerateNewSystemIdentifier"] = false;
    ManagementBaseObject outParameters = managementService.InvokeMethod(@"ImportSystemDefinition", inParameters, invokeMethodOptions);
    foreach (var value in outParameters.Properties) {
        Console.WriteLine("{0}: {1}", value.Name, value.Value);
    }
    return (ManagementBaseObject) outParameters["ImportedSystem"];
}

これを実行すると4096、ジョブが正常に開始されたことを示すリターン コードが返され、ジョブの値が返されます。たとえば、次のようになります。

ImportedSystem: 
Job: \\COREI7\root\virtualization\v2:Msvm_ConcreteJob.InstanceID="B1DC90B6-14A1-42C0-924E-225660E6EC98"
ReturnValue: 4096

次の質問があります。

  1. このメソッドを同期的に実行することは可能ですか? どうすればそれを伝えることができますか? http://msdn.microsoft.com/en-us/library/hh850082(v=vs.85).aspxの MSDN ドキュメントは、それが可能であることを示唆しています (「操作が同期的に完了する場合」)。 . 私の推測では、これはメソッドを同期的に実行する方法に関する一般的な WMI の質問であり、その方法を見つけることができないようです。
  2. 非同期を強制されている場合、その特定のジョブを監視するにはどうすればよいですか? 私が見つけたものはすべて、プロセス イベントまたはイベント ログ イベントの監視に関するものですが、これらはどちらも私が対象としている特定の WQL イベントであり、一般的なジョブ イベントではないようです。

これらの質問が基本的すぎる場合は申し訳ありませんが、答えを見つけることができません。

ありがとう!

[編集]ManagementOperationObserverいつ完了したかを教えてくれる a を追加することを検討していますが、とにかくそうしているように見えるのに、なぜ非同期にする必要があるのか​​ は明らかではありません。

4

1 に答える 1

1

OK、それで私はこれを解決しました。

まず、ジョブはエラーで完了していました。それ4096は始まったが失敗したので終わっていなかったと私に言っていた。上記のコードからそれをすばやく取得する方法はまだわかりませんが、PowerShellで実験すると、それが起こっていることが明らかになりました。

次に、コードを完全に刷新しました。Visual Studioでサーバーエクスプローラーから厳密に型指定されたWMIクラスを生成することができます:http://msdn.microsoft.com/en-us/library/ms257357.aspx。これを2回実行して取得ROOT.virtualization.v2.Msvm_PlannedComputerSystem.csROOT.virtualization.v2.Msvm_VirtualSystemManagementService.cs、次のコードを実行できるようにします。これははるかに明確です。

var managementScope = new ManagementScope(@"root\virtualization\v2");
using (var managementService = new VirtualSystemManagementService(WmiUtilities.GetVirtualMachineManagementService(managementScope))) {
    PlannedComputerSystem importedSystem;
    ConcreteJob job;
    var importResults = managementService.ImportSystemDefinition(
        GenerateNewSystemIdentifier: false,
        SystemDefinitionFile: filePath,
        SnapshotFolder: snapshotPath,
        ImportedSystem: out importedSystem,
        Job: out job
    );
    if (importResults != 0) {
        MessageBox.Show(String.Format("Error on import of {0}: {1}", filePath, job.ErrorDescription));
    }
}

ImportSystemDefinition生成されたコードを少し変更して、より適切に型指定されたオブジェクトを呼び出しから戻す必要があることに注意してください。

ImportedSystem = null;
Job = null;
if (outParams == null) {
    return 0;
} else {
    if (outParams.Properties["ImportedSystem"].Value != null) {
        ImportedSystem = new PlannedComputerSystem(new ManagementObject(outParams.Properties["ImportedSystem"].Value.ToString()));
    }
    if (outParams.Properties["Job"].Value != null) {
        Job = new ConcreteJob(new ManagementObject(outParams.Properties["Job"].Value.ToString;
    }
    return Convert.ToUInt32(outParams.Properties["ReturnValue"].Value);
}
于 2012-12-18T19:35:25.503 に答える