]> git.ipfire.org Git - thirdparty/snapper.git/commitdiff
- allow to configure snapshotting from zypp-plugin depending on package list (fate...
authorArvin Schnell <aschnell@suse.de>
Mon, 25 Nov 2013 10:49:26 +0000 (11:49 +0100)
committerArvin Schnell <aschnell@suse.de>
Mon, 25 Nov 2013 10:49:26 +0000 (11:49 +0100)
configure.ac
data/Makefile.am
data/zypp-plugin.conf [new file with mode: 0644]
doc/.gitignore
doc/Makefile.am
doc/snapper-zypp-plugin.conf.xml.in [new file with mode: 0644]
doc/snapper-zypp-plugin.xml.in [new file with mode: 0644]
package/snapper.changes
scripts/zypp-plugin.py
snapper.spec.in

index 9cee3029c3ba8a12ff9303e94187a7426ee25f18..44cee463e120072d07f3fc2094f6ac0b447ac997 100644 (file)
@@ -144,6 +144,8 @@ AC_OUTPUT(
        doc/snapper.xml:doc/snapper.xml.in
        doc/snapperd.xml:doc/snapperd.xml.in
        doc/snapper-configs.xml:doc/snapper-configs.xml.in
+       doc/snapper-zypp-plugin.xml:doc/snapper-zypp-plugin.xml.in
+       doc/snapper-zypp-plugin.conf.xml:doc/snapper-zypp-plugin.conf.xml.in
        doc/pam_snapper.xml:doc/pam_snapper.xml.in
        po/Makefile
        testsuite/Makefile
index 5dfbfb136547c8f4a5c6ddc0dfcdc18f0d418956..552382ce0b6ad4c6588ffef390780465043e2634 100644 (file)
@@ -3,7 +3,8 @@
 #
 
 EXTRA_DIST = sysconfig.snapper base.txt lvm.txt x11.txt snapper.logrotate      \
-       default-config org.opensuse.Snapper.conf org.opensuse.Snapper.service
+       default-config org.opensuse.Snapper.conf org.opensuse.Snapper.service   \
+       zypp-plugin.conf
 
 install-data-local:
        install -D -m 644 snapper.logrotate $(DESTDIR)/etc/logrotate.d/snapper
@@ -15,3 +16,4 @@ install-data-local:
        install -D -m 644 x11.txt $(DESTDIR)/etc/snapper/filters/x11.txt
        install -D -m 644 org.opensuse.Snapper.conf $(DESTDIR)/etc/dbus-1/system.d/org.opensuse.Snapper.conf
        install -D -m 644 org.opensuse.Snapper.service $(DESTDIR)/usr/share/dbus-1/system-services/org.opensuse.Snapper.service
+       install -D -m 644 zypp-plugin.conf $(DESTDIR)/etc/snapper/zypp-plugin.conf
diff --git a/data/zypp-plugin.conf b/data/zypp-plugin.conf
new file mode 100644 (file)
index 0000000..6ae47f6
--- /dev/null
@@ -0,0 +1,17 @@
+<?xml version="1.0" encoding="utf-8"?>
+<snapper-zypp-plugin-conf>
+
+  <!-- List of solvables. If the zypp commit transaction includes any solvable
+       listed below, snapper will create pre and post snapshots. If any of the
+       solvables is marked as important, the snapshots will also be marked as
+       important. The solvables names are matched with Unix shell-style
+       wildcards. -->
+  <solvables>
+    <solvable important="true">kernel-*</solvable>
+    <solvable important="true">glibc</solvable>
+    <solvable important="true">systemd</solvable>
+    <solvable important="true">udev</solvable>
+    <solvable>*</solvable>
+  </solvables>
+
+</snapper-zypp-plugin-conf>
index 4d3d9a60aa247b22e6a9fccd51d11f816b247977..d67edd82d248ae1329763d1a3686e2fb2a3300f2 100644 (file)
@@ -1,12 +1,18 @@
 snapper.xml
 snapperd.xml
 snapper-configs.xml
+snapper-zypp-plugin.xml
+snapper-zypp-plugin.conf.xml
 pam_snapper.xml
 snapper.8
 snapperd.8
 snapper-configs.5
+snapper-zypp-plugin.8
+snapper-zypp-plugin.conf.5
 pam_snapper.8
 snapper.html
 snapperd.html
 snapper-configs.html
+snapper-zypp-plugin.html
+snapper-zypp-plugin.conf.html
 pam_snapper.html
index 1e1d8e0efb376dad93e2e35d5b7db6846c8d69ad..22cd4b34b606981bc3b51b892efcf227aa514353 100644 (file)
@@ -2,7 +2,8 @@
 # Makefile.am for snapper/doc
 #
 
-man_MANS = snapper.8 snapperd.8 snapper-configs.5
+man_MANS = snapper.8 snapperd.8 snapper-configs.5 snapper-zypp-plugin.8        \
+       snapper-zypp-plugin.conf.5
 
 if HAVE_PAM
 man_MANS += pam_snapper.8
diff --git a/doc/snapper-zypp-plugin.conf.xml.in b/doc/snapper-zypp-plugin.conf.xml.in
new file mode 100644 (file)
index 0000000..2126d95
--- /dev/null
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="utf-8"?>
+<refentry id='snapper-zypp-plugin.conf5'>
+
+  <refentryinfo>
+    <date>2013-11-22</date>
+  </refentryinfo>
+
+  <refmeta>
+    <refentrytitle>snapper-zypp-plugin.conf</refentrytitle>
+    <manvolnum>5</manvolnum>
+    <refmiscinfo class='date'>2013-11-22</refmiscinfo>
+    <refmiscinfo class='version'>@VERSION@</refmiscinfo>
+    <refmiscinfo class='manual'>Filesystem Snapshot Management</refmiscinfo>
+  </refmeta>
+
+  <refnamediv>
+    <refname>snapper-zypp-plugin.conf</refname>
+    <refpurpose>Configuration file for snapper-zypp-plugin</refpurpose>
+  </refnamediv>
+
+  <refsect1 id='description'>
+    <title>DESCRIPTION</title>
+    <para>The file <filename>/etc/snapper/zypp-plugin.conf</filename> contains
+    the configuation for snapper-zypp-plugin.</para>
+
+    <para>The file uses XML syntax. For the structure look at the provided
+    default config.</para>
+  </refsect1>
+
+  <refsect1 id='homepage'>
+    <title>HOMEPAGE</title>
+    <para><ulink url='http://snapper.io/'>http://snapper.io/</ulink></para>
+  </refsect1>
+
+  <refsect1 id='authors'>
+    <title>AUTHORS</title>
+    <para>Arvin Schnell <email>aschnell@suse.de</email></para>
+  </refsect1>
+
+  <refsect1 id='see_also'>
+    <title>SEE ALSO</title>
+    <para>
+      <citerefentry><refentrytitle>snapper-zypp-plugin</refentrytitle><manvolnum>8</manvolnum></citerefentry>
+    </para>
+  </refsect1>
+
+</refentry>
diff --git a/doc/snapper-zypp-plugin.xml.in b/doc/snapper-zypp-plugin.xml.in
new file mode 100644 (file)
index 0000000..7ff9d9e
--- /dev/null
@@ -0,0 +1,58 @@
+<?xml version="1.0" encoding="utf-8"?>
+<refentry id='snapper-zypp-plugin8'>
+
+  <refentryinfo>
+    <date>2013-11-22</date>
+  </refentryinfo>
+
+  <refmeta>
+    <refentrytitle>snapper-zypp-plugin</refentrytitle>
+    <manvolnum>8</manvolnum>
+    <refmiscinfo class='date'>2013-11-22</refmiscinfo>
+    <refmiscinfo class='version'>@VERSION@</refmiscinfo>
+    <refmiscinfo class='manual'>Filesystem Snapshot Management</refmiscinfo>
+  </refmeta>
+
+  <refnamediv>
+    <refname>snapper-zypp-plugin</refname>
+    <refpurpose>Snapper plugin for libzypp</refpurpose>
+  </refnamediv>
+
+  <refsect1 id='description'>
+    <title>DESCRIPTION</title>
+    <para>With the snapper-zypp-plugin, snapper can create snapshots whenever
+    libzypp, and thus e.g. zypper, installs, updates or removes packages.</para>
+  </refsect1>
+
+  <refsect1 id='files'>
+    <title>FILES</title>
+    <variablelist>
+      <varlistentry>
+       <term><filename>/etc/snapper/zypp-plugin.conf</filename></term>
+       <listitem>
+         <para>Configuration file.</para>
+       </listitem>
+      </varlistentry>
+    </variablelist>
+  </refsect1>
+
+  <refsect1 id='homepage'>
+    <title>HOMEPAGE</title>
+    <para><ulink url='http://snapper.io/'>http://snapper.io/</ulink></para>
+  </refsect1>
+
+  <refsect1 id='authors'>
+    <title>AUTHORS</title>
+    <para>Arvin Schnell <email>aschnell@suse.de</email></para>
+  </refsect1>
+
+  <refsect1 id='see_also'>
+    <title>SEE ALSO</title>
+    <para>
+      <citerefentry><refentrytitle>snapper-zypp-plugin.conf</refentrytitle><manvolnum>5</manvolnum></citerefentry>,
+      <citerefentry><refentrytitle>snapper</refentrytitle><manvolnum>8</manvolnum></citerefentry>,
+      <citerefentry><refentrytitle>zypper</refentrytitle><manvolnum>8</manvolnum></citerefentry>
+    </para>
+  </refsect1>
+
+</refentry>
index 53f8502da4c1f771e9ff3db3e66522e01ce2eea1..bd64e8ea58115d37ab9cd7313c09849f5fcb73fe 100644 (file)
@@ -1,3 +1,9 @@
+-------------------------------------------------------------------
+Mon Nov 25 11:38:43 CET 2013 - aschnell@suse.de
+
+- allow to configure snapshotting from zypp-plugin depending on
+  package list (fate#316203)
+
 -------------------------------------------------------------------
 Mon Oct 21 10:24:43 CEST 2013 - aschnell@suse.de
 
index 4a69faed0ffad73092806849051134b29a2d834b..7c02ad70632f412bc98a518e5ec5bd8f92b1a966 100755 (executable)
 
 from os import readlink, getppid
 from os.path import basename
-from sys import stderr
+from fnmatch import fnmatch
+import logging
 from dbus import SystemBus, Interface
+import xml.dom.minidom as minidom
+import xml.parsers.expat as expat
+import json
 from zypp_plugin import Plugin
 
 
+
+class Solvable:
+
+    def __init__(self, name, important):
+        self.name = name
+        self.important = important
+
+    def __repr__(self):
+        return "name:%s important:%s" % (self.name, self.important)
+
+    def match(self, name):
+        return fnmatch(name, self.name)
+
+
+
+class Config:
+
+    def __init__(self):
+        self.solvables = []
+        self.loglevel = None
+        self.load_file("/etc/snapper/zypp-plugin.conf")
+
+
+    def load_file(self, filename):
+        try:
+            self.load_dom(minidom.parse(filename))
+        except IOError:
+            logging.error("failed to open %s" % filename)
+        except expat.ExpatError:
+            logging.error("failed to parse %s" % filename)
+        except:
+            logging.error("failed to load %s" % filename)
+
+
+    def load_dom(self, dom):
+        try:
+            for tmp1 in dom.getElementsByTagName("solvables"):
+                for tmp2 in tmp1.getElementsByTagName("solvable"):
+                    self.solvables.append(Solvable(tmp2.childNodes[0].data,
+                                                   tmp2.getAttribute("important") == "true"))
+        except:
+            pass
+
+
+
 class MyPlugin(Plugin):
 
+    def __init__(self):
+        Plugin.__init__(self)
+        self.num1 = self.num2 = None
+        self.description = ""
+        self.cleanup = "number"
+        self.userdata = {}
+
+
+    def parse_userdata(self, s):
+        userdata = {}
+        for kv in s.split(","):
+            k, v = kv.split("=", 1)
+            k = k.strip()
+            if not k:
+                raise ValueError
+            userdata[k] = v.strip()
+        return userdata
+
+
+    def get_userdata(self, headers):
+        try:
+            return self.parse_userdata(headers['userdata'])
+        except KeyError:
+            pass
+        except ValueError:
+            logging.error("invalid userdata")
+        return {}
+
+
+    def get_solvables(self, body):
+        tmp = json.loads(body)
+        tsl = tmp["TransactionStepList"]
+        solvables = set()
+        for ts in tsl:
+            solvables.add(ts["solvable"]["n"])
+        return solvables
+
+
+    def match_solvables(self, names):
+        found = important = False
+        for name in names:
+            for solvable in config.solvables:
+                if solvable.match(name):
+                    found = True
+                    important = important or solvable.important
+                    if found and important:
+                        return True, True
+        return found, important
+
+
+    def PLUGINBEGIN(self, headers, body):
+
+        logging.info("PLUGINBEGIN")
+
+        logging.debug("headers: %s" % headers)
+
+        self.description = "zypp(%s)" % basename(readlink("/proc/%d/exe" % getppid()))
+        self.userdata = self.get_userdata(headers)
+
+        self.ack()
+
+
+    def COMMITBEGIN(self, headers, body):
+
+        logging.info("COMMITBEGIN")
+
+        solvables = self.get_solvables(body)
+        logging.debug("solvables: %s" % solvables)
+
+        found, important = self.match_solvables(solvables)
+        logging.info("found: %s, important: %s" % (found, important))
+
+        if found or important:
+
+            self.userdata["important"] = "yes" if important else "no"
+
+            logging.info("creating pre snapshot")
+            self.num1 = snapper.CreatePreSnapshot("root", self.description, self.cleanup,
+                                                  self.userdata)
+
+        self.ack()
 
-  def parse_userdata(self, s):
-    ud = {}
-    for kv in s.split(","):
-      k, v = kv.split("=", 1)
-      k = k.strip()
-      if not k:
-        raise ValueError
-      ud[k] = v.strip()
-    return ud
 
+    def COMMITEND(self, headers, body):
 
-  def PLUGINBEGIN(self, headers, body):
+        logging.info("COMMITEND")
 
-    exe = basename(readlink("/proc/%d/exe" % getppid()))
+        if self.num1:
 
-    self.userdata = {}
+            logging.info("creating post snapshot")
+            self.num2 = snapper.CreatePostSnapshot("root", self.num1, "", self.cleanup,
+                                                   self.userdata)
 
-    try:
-      self.userdata = self.parse_userdata(headers['userdata'])
-    except KeyError:
-      pass
-    except ValueError:
-      stderr.write("invalid userdata")
+        self.ack()
 
-    self.num1 = snapper.CreatePreSnapshot("root", "zypp(%s)" % exe, "number", self.userdata)
 
-    self.ack()
+    def PLUGINEND(self, headers, body):
 
+        logging.info("PLUGINEND")
 
-  def PLUGINEND(self, headers, body):
+        self.ack()
 
-    self.num2 = snapper.CreatePostSnapshot("root", self.num1, "", "number", self.userdata)
 
-    self.ack()
 
+config = Config()
 
 bus = SystemBus()
 
index dda5cc72b58145a8807317a0588ee9d465b3c497..783c73fd7a634ae685b5a0b855ef640896945085 100644 (file)
@@ -99,7 +99,9 @@ rm -rf "$RPM_BUILD_ROOT"
 %defattr(-,root,root)
 %{prefix}/bin/snapper
 %{prefix}/sbin/snapperd
-%doc %{_mandir}/*/snapper*.*
+%doc %{_mandir}/*/snapper.8*
+%doc %{_mandir}/*/snapperd.8*
+%doc %{_mandir}/*/snapper-configs.5*
 %config(noreplace) %{_sysconfdir}/logrotate.d/snapper
 /etc/cron.hourly/suse.de-snapper
 /etc/cron.daily/suse.de-snapper
@@ -173,9 +175,10 @@ Authors:
 
 %package -n snapper-zypp-plugin
 Requires:       dbus-1-python
+Requires:       libzypp(plugin:commit)
+Requires:      python-xml
 Requires:       snapper = %version
 Requires:       zypp-plugin-python
-Requires:       libzypp(plugin:commit)
 Summary:        A zypp commit plugin for calling snapper
 Group:          System/Packages
 
@@ -189,12 +192,15 @@ Authors:
 
 %files -n snapper-zypp-plugin
 %defattr(-,root,root)
+%config(noreplace) %{_sysconfdir}/snapper/zypp-plugin.conf
 %if 0%{?suse_version} < 1210
 %dir /usr/lib/zypp
 %dir /usr/lib/zypp/plugins
 %dir /usr/lib/zypp/plugins/commit
 %endif
 /usr/lib/zypp/plugins/commit/snapper.py*
+%doc %{_mandir}/*/snapper-zypp-plugin.8*
+%doc %{_mandir}/*/snapper-zypp-plugin.conf.5*
 
 %package -n grub-snapper-plugin
 Requires:       python
@@ -236,6 +242,6 @@ Authors:
 /%{_lib}/security/pam_snapper.so
 %dir /usr/lib/pam_snapper
 /usr/lib/pam_snapper/*.sh
-%doc %{_mandir}/*/pam_snapper*.*
+%doc %{_mandir}/*/pam_snapper.8*
 
 %changelog