using System;
using System.Collections;
using System.Collections.Generic;
using System.Text;
using Interop.VixCOM;
using System.IO;
namespace Vestris.VMWareLib
{
///
/// A collection of snapshots at any snapshot level.
///
public class VMWareSnapshotCollection : IEnumerable, IDisposable
{
///
/// Virtual machine handle.
///
protected IVM2 _vm = null;
///
/// Internal list of snapshots.
///
protected List _snapshots = null;
private VMWareSnapshot _parent = null;
///
/// Snapshot collection constructor.
///
/// Virtual machine.
/// Snapshot parent.
public VMWareSnapshotCollection(IVM2 vm, VMWareSnapshot parent)
{
_vm = vm;
_parent = parent;
}
///
/// The list of snapshots.
///
protected virtual List Snapshots
{
get
{
if (_snapshots == null)
{
_snapshots = new List();
}
return _snapshots;
}
}
///
/// Find a snapshot.
///
/// Path to a snapshot.
/// A snapshot, null if not found.
public VMWareSnapshot FindSnapshot(string pathToSnapshot)
{
string[] paths = pathToSnapshot.Split("\\".ToCharArray(), 2);
foreach (VMWareSnapshot snapshot in this)
{
// last snapshot in the path
if (snapshot.DisplayName == paths[0])
{
return (paths.Length == 1)
? snapshot
: snapshot.ChildSnapshots.FindSnapshot(paths[1]);
}
}
return null;
}
///
/// Find a snapshot by name. Unlike GetSnapshotByName this function
/// doesn't throw an exception when there're two snapshots of the same name, it returns
/// the first snapshot found.
///
/// Name of a snapshot.
/// The first snapshot that matches the name, null if not found.
public VMWareSnapshot FindSnapshotByName(string name)
{
foreach (VMWareSnapshot snapshot in this)
{
if (snapshot.DisplayName == name)
{
return snapshot;
}
VMWareSnapshot childSnapshot = snapshot.ChildSnapshots.FindSnapshotByName(name);
if (childSnapshot != null)
{
return childSnapshot;
}
}
return null;
}
///
/// Find all snapshots by name. This can return multiple snapshots
/// that have the same name.
///
/// Name of a snapshot.
/// The first snapshot that matches the name, null if not found.
public IEnumerable FindSnapshotsByName(string name)
{
List snapshots = new List();
foreach (VMWareSnapshot snapshot in this)
{
if (snapshot.DisplayName == name)
{
snapshots.Add(snapshot);
}
snapshots.AddRange(snapshot.ChildSnapshots.FindSnapshotsByName(name));
}
return snapshots;
}
///
/// Copy to an array of VMWareSnapshots.
///
/// Target array.
/// Array index.
public void CopyTo(VMWareSnapshot[] array, int arrayIndex)
{
Snapshots.CopyTo(array, arrayIndex);
}
///
/// Returns true if this virtual machine has the snapshot specified.
///
/// Snapshot.
/// True if the virtual machine contains the specified snapshot.
public bool Contains(VMWareSnapshot item)
{
return Snapshots.Contains(item);
}
///
/// Number of snapshots.
///
public int Count
{
get
{
return Snapshots.Count;
}
}
///
/// Returns true if the collection is read-only.
/// A collection of snapshots is never read-only.
///
public bool IsReadOnly
{
get
{
return false;
}
}
///
/// A snapshot collection enumerator.
///
/// Snapshots enumerator.
IEnumerator IEnumerable.GetEnumerator()
{
return Snapshots.GetEnumerator();
}
///
/// A snapshot collection enumerator.
///
/// Snapshots enumerator.
IEnumerator IEnumerable.GetEnumerator()
{
return Snapshots.GetEnumerator();
}
///
/// Add a snapshot to the list.
///
/// Snapshot to add.
public void Add(VMWareSnapshot snapshot)
{
if (snapshot.Parent != null && snapshot.Parent != _parent)
{
throw new InvalidOperationException("Snapshot already belongs to another collection.");
}
Snapshots.Add(snapshot);
}
///
/// Remove a snapshot from this collection, append orphaned children.
///
/// Snapshot to remove.
public void Remove(VMWareSnapshot snapshot)
{
if (_snapshots != null)
{
_snapshots.Remove(snapshot);
foreach (VMWareSnapshot childSnapshot in snapshot.ChildSnapshots)
{
childSnapshot.Parent = _parent;
_snapshots.Add(childSnapshot);
}
}
}
///
/// Remove all elements from the snapshot collection.
///
public void RemoveAll()
{
if (_snapshots != null)
{
foreach (VMWareSnapshot snapshot in _snapshots)
{
snapshot.Dispose();
}
_snapshots = null;
}
}
///
/// Dispose the collection.
///
public void Dispose()
{
RemoveAll();
_parent = null;
_vm = null;
}
}
}