Package: mini-dinstall
Version: 0.6.21
Severity: wishlist
Tags: patch
Hi,
regenerating the packages file can take up to several (>30) seconds when
there are lots of packages in an archive.
During this time every "apt-get update" fails (there are several errors,
most of the time apt-get complains a about a bad Packages.gz, since it's
not a valid gzipped file). The attached patch now generates the
Packages{,.gz} as Packages.new.{,.gz} and moves them into place after
the regeneration. This has the advantage that apt-get doesn't run into
an error code.
If you have several hundred or thousand machines each of them pulling
from a repository via cron the chances of several machines hitting the
Packges.gz during the update process is quiet high...I've seen this
many times. Does the patch look o.k.?
Cheers,
-- Guido
-- System Information:
Debian Release: testing/unstable
APT prefers unstable
APT policy: (500, 'unstable'), (500, 'stable')
Architecture: powerpc (ppc)
Shell: /bin/sh linked to /bin/bash
Kernel: Linux 2.6.13-rc3-agx0
Locale: LANG=de_DE.UTF-8, LC_CTYPE=de_DE.UTF-8 (charmap=UTF-8)
Versions of packages mini-dinstall depends on:
ii apt-utils 0.6.40.1 APT utility programs
ii python 2.3.5-3 An interactive high-level object-o
ii python-apt 0.6.13.1 Python interface to libapt-pkg
mini-dinstall recommends no packages.
-- no debconf information
--- mini-dinstall.agx 2005-08-24 13:49:06.000000000 +0200
+++ mini-dinstall 2005-08-24 14:13:35.000000000 +0200
@@ -19,7 +19,7 @@
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
import os, sys, re, glob, getopt, time, traceback, gzip, getpass, socket
-import signal, threading, select, Queue, SocketServer
+import shutil, signal, threading, select, Queue, SocketServer
import logging, logging.handlers
#logging.basicConfig()
import apt_pkg
@@ -1047,19 +1047,25 @@
os.exit(1)
os.close(outfd)
stdout = os.fdopen(infd)
- packagesfile = open(os.path.join(dir, name), 'w')
- zpackagesfile = gzip.GzipFile(os.path.join(dir, name + '.gz'), 'w')
+ packagesfilename = os.path.join(dir, name)
+ newpackagesfilename = packagesfilename + '.new'
+ zpackagesfilename = packagesfilename + '.gz'
+ newzpackagesfilename = newpackagesfilename + '.gz'
+ newpackagesfile = open(newpackagesfilename, 'w')
+ newzpackagesfile = gzip.GzipFile(newzpackagesfilename, 'w')
buf = stdout.read(8192)
while buf != '':
- packagesfile.write(buf)
- zpackagesfile.write(buf)
+ newpackagesfile.write(buf)
+ newzpackagesfile.write(buf)
buf = stdout.read(8192)
stdout.close()
(pid, status) = os.waitpid(pid, 0)
if not (status is None or (os.WIFEXITED(status) and
os.WEXITSTATUS(status) == 0)):
raise DinstallException("apt-ftparchive exited with status code
%d" % (status,))
- packagesfile.close()
- zpackagesfile.close()
+ newpackagesfile.close()
+ newzpackagesfile.close()
+ shutil.move(newpackagesfilename, packagesfilename)
+ shutil.move(newzpackagesfilename, zpackagesfilename)
def _make_packagesfile(self, dir):
self._make_indexfile(dir, 'packages', 'Packages')