As discussed on debian-devel, different versions of these conffile handling
shell functions on the wiki are being copied into maintainer scripts
repeatedly, and adding a program to dpkg that handles things is a more
maintainable approach.
Note that in two places, parameters are required by dpkg-conffile that are
not currently used. I did this to future-proof calls to the program.
Perhaps in the future it will want to know the new conffile name in
`prep_mv`, or the package name in `mv`.
There is no copyright statement on the code in the wiki. (Which is being
copied into many packages .. without a copyright statment!) I looked at
the edit histories of both
http://wiki.debian.org/DpkgConffileHandling and
http://www.dpkg.org/dpkg/ConffileHandling, and it was originally written
by Scott, and was then modified by Guillem. This patch assumes that both
of them are willing to license it under GPL2+.
Signed-off-by: Joey Hess <joeyh@debian.org>
---
debian/changelog | 3 +
debian/copyright | 3 +-
debian/dpkg.install | 3 +
man/Makefile.am | 1 +
man/dpkg-conffile.8 | 132 ++++++++++++++++++++++++++++++++++++++++++++++
scripts/Makefile.am | 2 +
scripts/dpkg-conffile.sh | 94 ++++++++++++++++++++++++++++++++
7 files changed, 237 insertions(+), 1 deletions(-)
create mode 100644 man/dpkg-conffile.8
create mode 100755 scripts/dpkg-conffile.sh
diff --git a/debian/changelog b/debian/changelog
index 1eb6246..86c51e1 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -22,6 +22,9 @@ dpkg (1.14.17) UNRELEASED; urgency=low
* German (Helge Kreutzmann).
* Swedish (Peter Karlsson).
+ [ Joey Hess ]
+ * Add dpkg-conffile, based upon http://wiki.debian.org/DpkgConffileHandling
+
-- Guillem Jover <guillem@debian.org> Mon, 21 Jan 2008 10:11:55 +0200
dpkg (1.14.16.5) unstable; urgency=low
diff --git a/debian/copyright b/debian/copyright
index 8ea1e6d..ac15365 100644
--- a/debian/copyright
+++ b/debian/copyright
@@ -1,11 +1,12 @@
This is Debian's package maintenance system.
+Copyright © 2007 Guillem Jover <guillem@debian.org>
Copyright © 2006-2007 Frank Lichtenheld <djpig@debian.org>
Copyright © 2004-2005 Scott James Remnant <scott@netsplit.com>
Copyright © 2004-2005 Canonical Ltd.
Copyright © 1999-2002 Wichert Akkerman <wakkerma@debian.org>
Copyright © 1999-2001 Marcus Brinkmann <brinkmd@debian.org>
-Copyright © 2001 Joey Hess <joeyh@debian.org>
+Copyright © 2001,2008 Joey Hess <joeyh@debian.org>
Copyright © 1994-1999 Ian Jackson <ian@chiark.greenend.org.uk>
Copyright © 1999 Richard Kettlewell <rjk@sfere.greenend.org.uk>
Copyright © 1999 Ben Collins <bcollins@debian.org>
diff --git a/debian/dpkg.install b/debian/dpkg.install
index 2f54618..bd33273 100644
--- a/debian/dpkg.install
+++ b/debian/dpkg.install
@@ -7,6 +7,7 @@ usr/bin/dpkg
usr/bin/dpkg-deb
usr/bin/dpkg-query
usr/bin/dpkg-split
+usr/bin/dpkg-conffile
usr/lib/dpkg/mksplit
usr/sbin
usr/share/dpkg
@@ -21,6 +22,8 @@ usr/share/man/*/*/dpkg-query.1
usr/share/man/*/dpkg-query.1
usr/share/man/*/*/dpkg-split.1
usr/share/man/*/dpkg-split.1
+usr/share/man/*/*/dpkg-conffile.8
+usr/share/man/*/dpkg-conffile.8
usr/share/man/*/*/dpkg-statoverride.8
usr/share/man/*/dpkg-statoverride.8
usr/share/man/*/*/dpkg.cfg.5
diff --git a/man/Makefile.am b/man/Makefile.am
index 42b17af..c975329 100644
--- a/man/Makefile.am
+++ b/man/Makefile.am
@@ -78,6 +78,7 @@ dist_man_MANS = \
dpkg-architecture.1 \
dpkg-buildpackage.1 \
dpkg-checkbuilddeps.1 \
+ dpkg-conffile.8 \
dpkg-deb.1 \
dpkg-distaddfile.1 \
dpkg-divert.8 \
diff --git a/man/dpkg-conffile.8 b/man/dpkg-conffile.8
new file mode 100644
index 0000000..6bd8bf6
--- /dev/null
+++ b/man/dpkg-conffile.8
@@ -0,0 +1,132 @@
+.\" This is an -*- nroff -*- source file.
+.\" dpkg-conffile and this manpage are Copyright 2008 by Joey Hess.
+.\"
+.\" This is free software; see the GNU General Public Licence version 2
+.\" or later for copying conditions. There is NO warranty.
+.TH dpkg\-conffile 8 "2008-1-25" "Debian Project" "dpkg utilities"
+.SH NAME
+dpkg\-conffile \- graceful deletion or moving of conffiles
+.
+.SH SYNOPSIS
+.B dpkg\-conffile
+.I rm <package> <conffile>
+.P
+.B dpkg\-conffile
+.I prep_mv <package> <oldconffile> <newconffile>
+.P
+.B dpkg\-conffile
+.I mv <package> <oldconffile> <newconffile>
+.
+.SH DESCRIPTION
+When upgrading a package, dpkg will not automatically remove a conffile (a
+configuration filefor which dpkg should preserve user changes) if it is not
+present in the newer version. There are two principal reasons for this; the
+first is that the conffile could've been dropped by accident and the next
+version could restore it, users wouldn't want their changes thrown away.
+The second is to allow packages to transition files from a dpkg-maintained
+conffile to a file maintained by the package's maintainer scripts, usually
+with a tool like debconf or ucf.
+.P
+This means that if a package is intended to rename or remove a conffile,
+it must explicitly do do.
+.B dpkg\-conffile
+helps with graceful deletion and moving of conffiles.
+.
+.SH "REMOVING A CONFFILE"
+If a conffile is completely removed, it should be removed from disk,
+unless the user has modified it. If there are local modifications, they
+should be preserved. This can be accomplished by making the package's
+preinst script call
+.B dpkg\-conffile rm <conffile>
+.P
+Generally the preinst should check to only do so on install or upgrade,
+and only when upgrading from a version of the package that contained the
+conffile.
+.P
+Internally,
+.B dpkg\-conffile rm
+will first check to make sure the conffile actually exists on the disk, if the
+user has removed it already there's no point carrying on as everything's fine.
+It then checks to see whether the user has modified it from the package's
+version or not. It obtains the current md5sum, and compares that to
+one taken from the dpkg database. This is why
+.B dpkg\-conffile rm
+must be called from the preinst, as the old md5sum information is still
+available in the dpkg database at that point.
+.P
+If the user has not modified the conffile, it is simply removes from the disk.
+If they have, it is moved to a filename that can be easily identified by the
+user and ignored bytools such as run-parts.
+.
+.SH "MOVING A CONFFILE"
+If a conffile is moved from one location to another, you need to make sure you
+move across any changes the user has made. This may seem a simple change to the
+preinst script at first, however that will result in the user being prompted by
+dpkg to approve the conffile edits they have made. If you change the conffile
+format, that may be desirable, however often you can do that kind of checking
+yourself.
+.P
+.B dpkg\-conffile
+allows moving a conffile without triggering the dpkg question. To move
+a conffile, there are two steps. The preinst of the package, on install or
+upgrade from the version that contained the conffile in the old location,
+should call
+.B dpkg\-conffile prep_mv <package> <oldconffile> <newconffile>
+.P
+Much like removal, this first checks to make sure the old conffile
+exists on the disk and whether the user has changed it or not. If the user
+has not changed it, the old conffile is simply removed from disk. If the
+user has changed the conffile, it is left in place; its rename will be
+handled by the postinst script.
+.P
+The postinst of the package should call
+.B dpkg\-conffile mv <package> <oldconffile> <newconffile>
+.P
+This checks to see if the old conffile still exists on disk. If so,
+it must contain changes that should be preserved. The new conffile (as
+unpacked by dpkg) is moved to a .dpkg-new file, and the old conffile is
+moved into its place.
+.
+.SH EXAMPLES
+Removing a conffile, in a preinst script:
+
+ case "$1" in
+ install|upgrade)
+ if dpkg --compare-versions "$2" le "$LASTVERSION"; then
+ dpkg-conffile rm mypackage /etc/pkg/conf
+ fi
+ esac
+
+Preparing to rename a conffile, in a preinst script:
+
+ case "$1" in
+ install|upgrade)
+ if dpkg --compare-versions "$2" le "$LASTVERSION"; then
+ dpkg-conffile prep_mv mypackage /etc/pkg.conf /etc/pkg/conf
+ fi
+ esac
+
+Renaming the conffile, in a postinst script:
+
+ case "$1" in
+ configure)
+ if dpkg --compare-versions "$2" le "$LASTVERSION"; then
+ dpkg-conffile mv mypackage /etc/pkg_conf /etc/pkg/conf
+ fi
+ esac
+.P
+In the above examples, replace $LASTVERSION with the last version
+of the package to contain the old conffile.
+.
+.SH BUGS
+Arguably the need for this program at all is a bug in dpkg. If dpkg is
+ever changed to somehow handle conffile deletion and renaming on its own,
+this program could turn into a deprecated no-op.
+.SH SEE ALSO
+.BR dpkg (1),
+.
+.SH AUTHOR
+Copyright 2008 Joey Hess
+.sp
+This is free software; see the GNU General Public Licence version 2 or
+later for copying conditions. There is NO WARRANTY.
diff --git a/scripts/Makefile.am b/scripts/Makefile.am
index e27f294..8c24971 100644
--- a/scripts/Makefile.am
+++ b/scripts/Makefile.am
@@ -7,6 +7,7 @@ bin_SCRIPTS = \
dpkg-architecture \
dpkg-buildpackage \
dpkg-checkbuilddeps \
+ dpkg-conffile \
dpkg-distaddfile \
dpkg-genchanges \
dpkg-gencontrol \
@@ -34,6 +35,7 @@ EXTRA_DIST = \
dpkg-architecture.pl \
dpkg-buildpackage.pl \
dpkg-checkbuilddeps.pl \
+ dpkg-conffile.sh \
dpkg-distaddfile.pl \
dpkg-genchanges.pl \
dpkg-gencontrol.pl \
diff --git a/scripts/dpkg-conffile.sh b/scripts/dpkg-conffile.sh
new file mode 100755
index 0000000..9a1ce2d
--- /dev/null
+++ b/scripts/dpkg-conffile.sh
@@ -0,0 +1,94 @@
+#!/bin/sh
+# Copyright (C) 2005 Scott James Remnant (original implementation on www.dpkg.org)
+# Copyright (C) 2007 Guillem Jover (modifications on wiki.debian.org)
+# Copyright (C) 2008 Joey Hess <joeyh@debian.org> (this script)
+#
+# This is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License as published by the
+# Free Software Foundation; either version 2, or (at your option) any
+# later version.
+#
+# This is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the file
+# /usr/share/common-licenses/GPL for more details."
+
+set -e
+
+# Remove a no-longer used conffile
+rm_conffile() {
+ PKGNAME="$1"
+ CONFFILE="$2"
+ if [ -e "$CONFFILE" ]; then
+ md5sum="`md5sum \"$CONFFILE\" | sed -e \"s/ .*//\"`"
+ old_md5sum="`dpkg-query -W -f='${Conffiles}' $PKGNAME | sed -n -e \"\\\\' $CONFFILE'{s/ obsolete$//;s/.* //p}\"`"
+ if [ "$md5sum" != "$old_md5sum" ]; then
+ echo "Obsolete conffile $CONFFILE has been modified by you."
+ echo "Saving as $CONFFILE.dpkg-bak ..."
+ mv -f "$CONFFILE" "$CONFFILE".dpkg-bak
+ else
+ echo "Removing obsolete conffile $CONFFILE ..."
+ rm -f "$CONFFILE"
+ fi
+ fi
+}
+
+# Prepare to move a conffile without triggering a dpkg question
+prep_mv_conffile() {
+ PKGNAME="$1"
+ OLDCONFFILE="$2"
+ NEWCONFFILE="$3" # currently not used
+ if [ -e "$OLDCONFFILE" ]; then
+ md5sum="`md5sum \"$OLDCONFFILE\" | sed -e \"s/ .*//\"`"
+ old_md5sum="`dpkg-query -W -f='${Conffiles}' $PKGNAME | sed -n -e \"\\\\' $OLDCONFFILE'{s/ obsolete$//;s/.* //p}\"`"
+ if [ "$md5sum" = "$old_md5sum" ]; then
+ rm -f "$OLDCONFFILE"
+ fi
+ fi
+}
+
+# Move a conffile without triggering a dpkg question
+mv_conffile() {
+ PKGNAME="$1" # currently not used
+ OLDCONFFILE="$2"
+ NEWCONFFILE="$3"
+ if [ -e "$OLDCONFFILE" ]; then
+ echo "Preserving user changes to $NEWCONFFILE ..."
+ mv -f "$NEWCONFFILE" "$NEWCONFFILE".dpkg-new
+ mv -f "$OLDCONFFILE" "$NEWCONFFILE"
+ fi
+}
+
+usage() {
+ cat <<EOF >&2
+Usage:
+ dpkg-conffile rm <package> <conffile>
+ dpkg-conffile prep_mv <package> <oldconffile> <newconffile>
+ dpkg-conffile mv package <package> <oldconffile> <newconffile>
+EOF
+ exit 1
+}
+
+case "$1" in
+rm)
+ if [ -z "$2" ] || [ -z "$3" ]; then
+ usage
+ fi
+ rm_conffile "$2" "$3"
+;;
+prep_mv)
+ if [ -z "$2" ] || [ -z "$3" ] || [ -z "$4" ]; then
+ usage
+ fi
+ prep_mv_conffile "$2" "$3" "$4"
+;;
+mv)
+ if [ -z "$2" ] || [ -z "$3" ] || [ -z "$4" ]; then
+ usage
+ fi
+ mv_conffile "$2" "$3" "$4"
+;;
+*)
+ usage
+;;
+esac
--
1.5.3.8
--
see shy jo
Attachment:
signature.asc
Description: Digital signature