Signed-off-by: Simon Kobyda <skobyda(a)redhat.com>
---
data/org.libvirt.Domain.xml | 26 ++++
data/org.libvirt.DomainSnapshot.xml | 34 +++++
src/domain.c | 154 ++++++++++++++++++++
src/domainsnapshot.c | 216 ++++++++++++++++++++++++++++
tests/libvirttest.py | 12 ++
tests/meson.build | 1 +
tests/test_domain.py | 8 ++
tests/test_snapshot.py | 45 ++++++
tests/xmldata.py | 6 +
9 files changed, 502 insertions(+)
create mode 100755 tests/test_snapshot.py
diff --git a/data/org.libvirt.Domain.xml b/data/org.libvirt.Domain.xml
index b4ed495..3f108e7 100644
--- a/data/org.libvirt.Domain.xml
+++ b/data/org.libvirt.Domain.xml
@@ -350,6 +350,12 @@
<arg name="flags" type="u" direction="in"/>
<arg name="ifaces" type="a(ssa(isu))"
direction="out"/>
</method>
+ <method name="ListDomainSnapshots">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainLi...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshots" type="ao"
direction="out"/>
+ </method>
<method name="ManagedSave">
<annotation name="org.gtk.GDBus.DocString"
value="See
https://libvirt.org/html/libvirt-libvirt-domain.html#virDomainManagedSave...
@@ -589,6 +595,26 @@
value="See
https://libvirt.org/html/libvirt-libvirt-domain.html#virDomainShutdownFla...
<arg name="flags" type="u" direction="in"/>
</method>
+ <method name="SnapshotCurrent">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshot" type="o"
direction="out"/>
+ </method>
+ <method name="SnapshotCreateXML">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="xml" type="s" direction="in"/>
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshot" type="o"
direction="out"/>
+ </method>
+ <method name="SnapshotLookupByName">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="name" type="s" direction="in"/>
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshot" type="o"
direction="out"/>
+ </method>
<method name="Suspend">
<annotation name="org.gtk.GDBus.DocString"
value="See
https://libvirt.org/html/libvirt-libvirt-domain.html#virDomainSuspend&quo...
diff --git a/data/org.libvirt.DomainSnapshot.xml b/data/org.libvirt.DomainSnapshot.xml
index 8ba059f..9e9daac 100644
--- a/data/org.libvirt.DomainSnapshot.xml
+++ b/data/org.libvirt.DomainSnapshot.xml
@@ -3,5 +3,39 @@
<node name="/org/libvirt/domainsnapshot">
<interface name="org.libvirt.DomainSnapshot">
+ <method name="Delete">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ </method>
+ <method name="GetParent">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshot" type="o"
direction="out"/>
+ </method>
+ <method name="GetXMLDesc">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="xml" type="s" direction="out"/>
+ </method>
+ <method name="IsCurrent">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshot" type="b"
direction="out"/>
+ </method>
+ <method name="ListChildren">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainSn...
+ <arg name="flags" type="u" direction="in"/>
+ <arg name="domainSnapshots" type="ao"
direction="out"/>
+ </method>
+ <method name="Revert">
+ <annotation name="org.gtk.GDBus.DocString"
+ value="See
https://libvirt.org/html/libvirt-libvirt-domain-snapshot.html#virDomainRe...
+ <arg name="flags" type="u" direction="in"/>
+ </method>
</interface>
</node>
diff --git a/src/domain.c b/src/domain.c
index 10fa8de..a656c6a 100644
--- a/src/domain.c
+++ b/src/domain.c
@@ -1857,6 +1857,49 @@ virtDBusDomainInjectNMI(GVariant *inArgs,
virtDBusUtilSetLastVirtError(error);
}
+static void
+virtDBusDomainListDomainSnapshots(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomain) domain = NULL;
+ g_autoptr(virDomainSnapshotPtr) domainSnapshots = NULL;
+ guint flags;
+ GVariantBuilder builder;
+ GVariant *gdomainSnapshots;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domain = virtDBusDomainGetVirDomain(connect, objectPath, error);
+ if (!domain)
+ return;
+
+ if (!virtDBusConnectOpen(connect, error))
+ return;
+
+ if (virDomainListAllSnapshots(domain, &domainSnapshots, flags) < 0)
+ return virtDBusUtilSetLastVirtError(error);
+
+ g_variant_builder_init(&builder, G_VARIANT_TYPE("ao"));
+
+ for (gint i = 0; domainSnapshots[i]; i++) {
+ g_autofree gchar *path = NULL;
+ path = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ domainSnapshots[i],
+ connect->domainSnapshotPath);
+
+ g_variant_builder_add(&builder, "o", path);
+ }
+
+ gdomainSnapshots = g_variant_builder_end(&builder);
+ *outArgs = g_variant_new_tuple(&gdomainSnapshots, 1);
+}
+
static void
virtDBusDomainInterfaceAddresses(GVariant *inArgs,
GUnixFDList *inFDs G_GNUC_UNUSED,
@@ -2966,6 +3009,113 @@ virtDBusDomainShutdown(GVariant *inArgs,
virtDBusUtilSetLastVirtError(error);
}
+static void
+virtDBusDomainSnapshotCurrent(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autofree gchar *path = NULL;
+ g_autoptr(virDomain) domain = NULL;
+ g_autoptr(virDomainSnapshot) snapshot = NULL;
+ guint flags;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domain = virtDBusDomainGetVirDomain(connect, objectPath, error);
+ if (!domain)
+ return;
+
+ if (!virtDBusConnectOpen(connect, error))
+ return;
+
+ snapshot = virDomainSnapshotCurrent(domain, flags);
+ if (!snapshot)
+ return virtDBusUtilSetLastVirtError(error);
+
+ path = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ snapshot,
+ connect->domainSnapshotPath);
+
+ *outArgs = g_variant_new("(o)", path);
+}
+
+static void
+virtDBusDomainSnapshotCreateXML(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autofree gchar *path = NULL;
+ g_autoptr(virDomain) domain = NULL;
+ g_autoptr(virDomainSnapshot) snapshot = NULL;
+ guint flags;
+ const gchar *xml;
+
+ g_variant_get(inArgs, "(&su)", &xml, &flags);
+
+ domain = virtDBusDomainGetVirDomain(connect, objectPath, error);
+ if (!domain)
+ return;
+
+ if (!virtDBusConnectOpen(connect, error))
+ return;
+
+ snapshot = virDomainSnapshotCreateXML(domain, xml, flags);
+ if (!snapshot)
+ return virtDBusUtilSetLastVirtError(error);
+
+ path = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ snapshot,
+ connect->domainSnapshotPath);
+
+ *outArgs = g_variant_new("(o)", path);
+}
+
+static void
+virtDBusDomainSnapshotLookupByName(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autofree gchar *path = NULL;
+ g_autoptr(virDomain) domain = NULL;
+ g_autoptr(virDomainSnapshot) snapshot = NULL;
+ guint flags;
+ const gchar *name;
+
+ g_variant_get(inArgs, "(&su)", &name, &flags);
+
+ domain = virtDBusDomainGetVirDomain(connect, objectPath, error);
+ if (!domain)
+ return;
+
+ if (!virtDBusConnectOpen(connect, error))
+ return;
+
+ snapshot = virDomainSnapshotLookupByName(domain, name, flags);
+ if (!snapshot)
+ return virtDBusUtilSetLastVirtError(error);
+
+ path = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ snapshot,
+ connect->domainSnapshotPath);
+
+ *outArgs = g_variant_new("(o)", path);
+}
+
static void
virtDBusDomainSuspend(GVariant *inArgs G_GNUC_UNUSED,
GUnixFDList *inFDs G_GNUC_UNUSED,
@@ -3095,6 +3245,7 @@ static virtDBusGDBusMethodTable virtDBusDomainMethodTable[] = {
{ "HasManagedSaveImage", virtDBusDomainHasManagedSaveImage },
{ "InjectNMI", virtDBusDomainInjectNMI },
{ "InterfaceAddresses", virtDBusDomainInterfaceAddresses },
+ { "ListDomainSnapshots", virtDBusDomainListDomainSnapshots },
{ "ManagedSave", virtDBusDomainManagedSave },
{ "ManagedSaveRemove", virtDBusDomainManagedSaveRemove },
{ "MemoryPeek", virtDBusDomainMemoryPeek },
@@ -3132,6 +3283,9 @@ static virtDBusGDBusMethodTable virtDBusDomainMethodTable[] = {
{ "SetSchedulerParameters", virtDBusDomainSetSchedulerParameters },
{ "SetTime", virtDBusDomainSetTime },
{ "SetUserPassword", virtDBusDomainSetUserPassword },
+ { "SnapshotCurrent", virtDBusDomainSnapshotCurrent },
+ { "SnapshotCreateXML", virtDBusDomainSnapshotCreateXML },
+ { "SnapshotLookupByName", virtDBusDomainSnapshotLookupByName },
{ "Shutdown", virtDBusDomainShutdown },
{ "Suspend", virtDBusDomainSuspend },
{ "Undefine", virtDBusDomainUndefine },
diff --git a/src/domainsnapshot.c b/src/domainsnapshot.c
index c523c9e..f3571a1 100644
--- a/src/domainsnapshot.c
+++ b/src/domainsnapshot.c
@@ -1,13 +1,229 @@
#include "domainsnapshot.h"
+#include "domain.h"
#include "util.h"
#include <libvirt/libvirt.h>
+static virDomainSnapshotPtr
+virtDBusDomainSnapshotGetVirDomainSnapshot(virtDBusConnect *connect,
+ const gchar *objectPath,
+ GError **error)
+{
+ virDomainSnapshotPtr domSnap;
+
+ if (!virtDBusConnectOpen(connect, error))
+ return NULL;
+
+ domSnap = virtDBusUtilVirDomainSnapshotFromBusPath(connect->connection,
+ objectPath,
+ connect->domainSnapshotPath);
+ if (!domSnap) {
+ virtDBusUtilSetLastVirtError(error);
+ return NULL;
+ }
+
+ return domSnap;
+}
+
+static void
+virtDBusDomainSnapshotDelete(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ guint flags;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ if (virDomainSnapshotDelete(domainSnapshot, flags) < 0)
+ return virtDBusUtilSetLastVirtError(error);
+}
+
+static void
+virtDBusDomainSnapshotGetParent(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ g_autoptr(virDomainSnapshot) parent = NULL;
+ guint flags;
+ g_autoptr(virDomain) domain = NULL;
+ g_autofree gchar *parentPath = NULL;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ parent = virDomainSnapshotGetParent(domainSnapshot, flags);
+ if (!parent)
+ return virtDBusUtilSetLastVirtError(error);
+
+ domain = virDomainSnapshotGetDomain(domainSnapshot);
+ parentPath = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ parent,
+
connect->domainSnapshotPath);
+
+ *outArgs = g_variant_new("(o)", parentPath);
+}
+
+static void
+virtDBusDomainSnapshotGetXMLDesc(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ guint flags;
+ g_autofree gchar *xml = NULL;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ xml = virDomainSnapshotGetXMLDesc(domainSnapshot, flags);
+ if (!xml)
+ return virtDBusUtilSetLastVirtError(error);
+
+ *outArgs = g_variant_new("(s)", xml);
+}
+
+static void
+virtDBusDomainSnapshotIsCurrent(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ guint flags;
+ gint isCurrent;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ isCurrent = virDomainSnapshotIsCurrent(domainSnapshot, flags);
+ if (isCurrent < 0)
+ return virtDBusUtilSetLastVirtError(error);
+
+ *outArgs = g_variant_new("(b)", !!isCurrent);
+}
+
+static void
+virtDBusDomainSnapshotListAllChildren(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ g_autoptr(virDomainSnapshotPtr) snaps = NULL;
+ guint flags;
+ GVariantBuilder builder;
+ GVariant *gdomainSnapshots;
+ g_autoptr(virDomain) domain = NULL;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ if (virDomainSnapshotListAllChildren(domainSnapshot, &snaps, flags) < 0)
+ return virtDBusUtilSetLastVirtError(error);
+
+ g_variant_builder_init(&builder, G_VARIANT_TYPE("ao"));
+
+ domain = virDomainSnapshotGetDomain(domainSnapshot);
+ for (gint i = 0; snaps[i]; i++) {
+ g_autofree gchar *path = NULL;
+ path = virtDBusUtilBusPathForVirDomainSnapshot(domain,
+ snaps[i],
+ connect->domainSnapshotPath);
+
+ g_variant_builder_add(&builder, "o", path);
+ }
+
+ gdomainSnapshots = g_variant_builder_end(&builder);
+ *outArgs = g_variant_new_tuple(&gdomainSnapshots, 1);
+}
+
+static void
+virtDBusDomainSnapshotRevert(GVariant *inArgs,
+ GUnixFDList *inFDs G_GNUC_UNUSED,
+ const gchar *objectPath,
+ gpointer userData,
+ GVariant **outArgs G_GNUC_UNUSED,
+ GUnixFDList **outFDs G_GNUC_UNUSED,
+ GError **error)
+{
+ virtDBusConnect *connect = userData;
+ g_autoptr(virDomainSnapshot) domainSnapshot = NULL;
+ guint flags;
+
+ g_variant_get(inArgs, "(u)", &flags);
+
+ domainSnapshot = virtDBusDomainSnapshotGetVirDomainSnapshot(connect,
+ objectPath,
+ error);
+ if (!domainSnapshot)
+ return;
+
+ if (virDomainRevertToSnapshot(domainSnapshot, flags) < 0)
+ return virtDBusUtilSetLastVirtError(error);
+}
+
static virtDBusGDBusPropertyTable virtDBusDomainSnapshotPropertyTable[] = {
{ 0 }
};
static virtDBusGDBusMethodTable virtDBusDomainSnapshotMethodTable[] = {
+ { "Delete", virtDBusDomainSnapshotDelete },
+ { "GetParent", virtDBusDomainSnapshotGetParent },
+ { "GetXMLDesc", virtDBusDomainSnapshotGetXMLDesc },
+ { "IsCurrent", virtDBusDomainSnapshotIsCurrent },
+ { "ListChildren", virtDBusDomainSnapshotListAllChildren },
+ { "Revert", virtDBusDomainSnapshotRevert },
{ 0 }
};
diff --git a/tests/libvirttest.py b/tests/libvirttest.py
index a442196..dd181c2 100644
--- a/tests/libvirttest.py
+++ b/tests/libvirttest.py
@@ -112,6 +112,18 @@ class BaseTestClass():
"""
return self.node_device_create()
+ @pytest.fixture
+ def snapshot_create(self):
+ """ Fixture to create simple domain snapshot on the test driver
+
+ This fixture should be used in the setup of every test manipulating
+ with domain snaphots.
+ """
+ _, test_domain = self.get_test_domain()
+ path = test_domain.SnapshotCreateXML(xmldata.minimal_snapshot_xml, 0)
+ obj = self.bus.get_object('org.libvirt', path)
+ return dbus.Interface(obj, 'org.libvirt.DomainSnapshot')
+
@pytest.fixture
def storage_volume_create(self):
""" Fixture to create dummy storage volume on the test driver
diff --git a/tests/meson.build b/tests/meson.build
index b6d4bd5..0ad5cdb 100644
--- a/tests/meson.build
+++ b/tests/meson.build
@@ -22,6 +22,7 @@ test('test_util', test_exec, suite: 'unit')
python_tests = [
'test_connect.py',
'test_domain.py',
+ 'test_snapshot.py',
'test_interface.py',
'test_network.py',
'test_nodedev.py',
diff --git a/tests/test_domain.py b/tests/test_domain.py
index b5879b4..624d25b 100755
--- a/tests/test_domain.py
+++ b/tests/test_domain.py
@@ -2,6 +2,7 @@
import dbus
import libvirttest
+import xmldata
DBUS_EXCEPTION_MISSING_FUNCTION = 'this function is not supported by the connection
driver'
@@ -160,6 +161,13 @@ class TestDomain(libvirttest.BaseTestClass):
pinInfo = domain.GetVcpuPinInfo(0)
assert pinInfo == pinInfo_expected
+ def test_snapshot(self):
+ obj, domain = self.get_test_domain()
+ domain.SnapshotCreateXML(xmldata.minimal_snapshot_xml, 0)
+ assert isinstance(domain.SnapshotCurrent(0), dbus.ObjectPath)
+ assert isinstance(domain.SnapshotLookupByName("my_snapshot", 0),
dbus.ObjectPath)
+ assert isinstance(domain.ListDomainSnapshots(0), dbus.Array)
+
if __name__ == '__main__':
libvirttest.run()
diff --git a/tests/test_snapshot.py b/tests/test_snapshot.py
new file mode 100755
index 0000000..566f4a6
--- /dev/null
+++ b/tests/test_snapshot.py
@@ -0,0 +1,45 @@
+#!/usr/bin/env python3
+
+import dbus
+import libvirttest
+import pytest
+
+EXCEPTION_NO_PARENT = 'does not have a parent'
+
+
+(a)pytest.mark.usefixtures("snapshot_create")
+class TestSnapshot(libvirttest.BaseTestClass):
+ """ Tests for methods and properties of the Snapshot snapshot
+ """
+
+ def test_snapshot_delete(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ snapshot_obj.Delete(0)
+
+ def test_snapshot_get_parent(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ try:
+ snapshot_obj.GetParent(0)
+ except dbus.exceptions.DBusException as e:
+ if not any(EXCEPTION_NO_PARENT in arg for arg in e.args):
+ raise e
+
+ def test_snapshot_get_xml(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ assert isinstance(snapshot_obj.GetXMLDesc(0), dbus.String)
+
+ def test_snapshot_get_is_current(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ assert isinstance(snapshot_obj.IsCurrent(0), dbus.Boolean)
+
+ def test_snapshot_list_children(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ assert isinstance(snapshot_obj.ListChildren(0), dbus.Array)
+
+ def test_snapshot_revert(self, snapshot_create):
+ snapshot_obj = snapshot_create
+ snapshot_obj.Revert(0)
+
+
+if __name__ == '__main__':
+ libvirttest.run()
diff --git a/tests/xmldata.py b/tests/xmldata.py
index 8075052..0146ccf 100644
--- a/tests/xmldata.py
+++ b/tests/xmldata.py
@@ -54,6 +54,12 @@ minimal_node_device_xml = '''
</device>
'''
+minimal_snapshot_xml = '''
+<domainsnapshot>
+ <name>my_snapshot</name>
+</domainsnapshot>
+'''
+
minimal_storage_pool_xml = '''
<pool type='dir'>
<name>foo</name>
--
2.21.0