summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJulian Andres Klode <jak@debian.org>2014-03-17 14:39:25 +0100
committerJulian Andres Klode <jak@debian.org>2014-03-17 15:36:57 +0100
commit3c9e1b4fce9a587436965c495f5e43f96e115207 (patch)
treefddbd7cbd952c50fb08dd281ebc60d8ac4dfb6cd
parentb9844054663142c3e8dad1a6e1b3612c7db2054b (diff)
downloadpython-apt-3c9e1b4fce9a587436965c495f5e43f96e115207.tar.gz
Support all compressors for data.tar/control.tar (Closes: #718330)
This makes our support very flexible, and open for future additions of new compression algorithms. debfile_extract_tar() is almost identical to ExtractTarMember() of apt's debDebFile.
-rw-r--r--python/arfile.cc72
-rw-r--r--tests/data/test_debs/data-tar-xz.debbin626 -> 680 bytes
-rw-r--r--tests/data/test_debs/data-tar.debbin0 -> 20672 bytes
-rw-r--r--tests/test_debfile.py6
-rw-r--r--tests/test_paths.py8
5 files changed, 55 insertions, 31 deletions
diff --git a/python/arfile.cc b/python/arfile.cc
index 8f45e658..3284ff7c 100644
--- a/python/arfile.cc
+++ b/python/arfile.cc
@@ -523,6 +523,45 @@ static PyObject *_gettar(PyDebFileObject *self, const ARArchive::Member *m,
return tarfile;
}
+/*
+ * Mostly copy-paste from APT
+ */
+static PyObject *debfile_get_tar(PyDebFileObject *self, const char *Name)
+{
+ // Get the archive member
+ const ARArchive::Member *Member = NULL;
+ const ARArchive &AR = *self->Object;
+ std::string Compressor;
+
+ std::vector<APT::Configuration::Compressor> compressor =
+ APT::Configuration::getCompressors();
+ for (std::vector<APT::Configuration::Compressor>::const_iterator c =
+ compressor.begin(); c != compressor.end(); ++c) {
+ Member = AR.FindMember(std::string(Name).append(c->Extension).c_str());
+ if (Member == NULL)
+ continue;
+ Compressor = c->Binary;
+ break;
+ }
+
+ if (Member == NULL)
+ Member = AR.FindMember(std::string(Name).c_str());
+
+ if (Member == NULL) {
+ std::string ext = std::string(Name) + ".{";
+ for (std::vector<APT::Configuration::Compressor>::const_iterator c =
+ compressor.begin(); c != compressor.end(); ++c) {
+ if (!c->Extension.empty())
+ ext.append(c->Extension.substr(1));
+ }
+ ext.append("}");
+ _error->Error(("Internal error, could not locate member %s"),
+ ext.c_str());
+ return HandleErrors();
+ }
+
+ return _gettar(self, Member, Compressor.c_str());
+}
static PyObject *debfile_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
@@ -532,34 +571,13 @@ static PyObject *debfile_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
return NULL;
// DebFile
- self->control = _gettar(self, self->Object->FindMember("control.tar.gz"),
- "gzip");
- if (!self->control)
- return PyErr_Format(PyExc_SystemError, "No debian archive, missing %s",
- "control.tar.gz");
-
- // try all compression types
- std::vector<std::string> types = APT::Configuration::getCompressionTypes();
- for (std::vector<std::string>::const_iterator t = types.begin();
- t != types.end(); ++t) {
- std::string member = std::string("data.tar.").append(*t);
- std::string comp = _config->Find(std::string("Acquire::CompressionTypes::").append(*t));
- self->data = _gettar(self, self->Object->FindMember(member.c_str()),
- comp.c_str());
- if (self->data)
- break;
- }
- // no data found, we need to
- if (!self->data) {
- std::string error;
- for (std::vector<std::string>::const_iterator t = types.begin();
- t != types.end(); ++t)
- error.append(*t + ",");
- return PyErr_Format(PyExc_SystemError,
- "No debian archive, missing data.tar.{%s}",
- error.c_str());
- }
+ self->control = debfile_get_tar(self, "control.tar");
+ if (self->control == NULL)
+ return NULL;
+ self->data = debfile_get_tar(self, "data.tar");
+ if (self->data == NULL)
+ return NULL;
const ARArchive::Member *member = self->Object->FindMember("debian-binary");
if (!member)
diff --git a/tests/data/test_debs/data-tar-xz.deb b/tests/data/test_debs/data-tar-xz.deb
index fc15f597..9dd4d670 100644
--- a/tests/data/test_debs/data-tar-xz.deb
+++ b/tests/data/test_debs/data-tar-xz.deb
Binary files differ
diff --git a/tests/data/test_debs/data-tar.deb b/tests/data/test_debs/data-tar.deb
new file mode 100644
index 00000000..d8e4a988
--- /dev/null
+++ b/tests/data/test_debs/data-tar.deb
Binary files differ
diff --git a/tests/test_debfile.py b/tests/test_debfile.py
index ec3bf518..21255517 100644
--- a/tests/test_debfile.py
+++ b/tests/test_debfile.py
@@ -120,6 +120,12 @@ Description: testpackage for gdebi - contains usr/bin/binary for file reading
deb = apt.debfile.DebPackage("./data/test_debs/data-tar-xz.deb")
self.assertEqual(deb.filelist, ["./", "usr/", "usr/bin/"])
+ @unittest.skipIf(apt_pkg.version_compare(apt_pkg.VERSION, "0.9.15.4~") < 0,
+ "APT too old for uncompressed control.tar/data.tar")
+ def test_uncompressed_data(self):
+ deb = apt.debfile.DebPackage("./data/test_debs/data-tar.deb")
+ self.assertEqual(deb.filelist, ["./", "usr/", "usr/bin/"])
+
def test_check_exception(self):
deb = apt.debfile.DebPackage("./data/test_debs/data-tar-xz.deb")
self.assertRaises(AttributeError, lambda: deb.missing_deps)
diff --git a/tests/test_paths.py b/tests/test_paths.py
index 62ea1665..51d22f49 100644
--- a/tests/test_paths.py
+++ b/tests/test_paths.py
@@ -53,8 +53,8 @@ class TestPath(unittest.TestCase):
self.assertTrue(archive[b"debian-binary"])
self.assertTrue(archive[u"debian-binary"])
- tar = archive.gettar(u"control.tar.gz", "gzip")
- tar = archive.gettar(b"control.tar.gz", "gzip")
+ tar = archive.gettar(u"control.tar.xz", "xz")
+ tar = archive.gettar(b"control.tar.xz", "xz")
tar.extractall(self.dir_unicode)
tar.extractall(self.dir_bytes)
@@ -63,8 +63,8 @@ class TestPath(unittest.TestCase):
tar.extractdata(b"control")
tar.extractdata(u"control")
- apt_inst.TarFile(os.path.join(self.dir_unicode, u"control.tar.gz"))
- apt_inst.TarFile(os.path.join(self.dir_bytes, b"control.tar.gz"))
+ apt_inst.TarFile(os.path.join(self.dir_unicode, u"control.tar.xz"))
+ apt_inst.TarFile(os.path.join(self.dir_bytes, b"control.tar.xz"))
def test_configuration(self):
with open(self.file_unicode, 'w') as config: