aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarco Nenciarini <mnencia@debian.org>2010-05-18 18:06:24 +0200
committerGuido Günther <agx@sigxcpu.org>2011-05-08 18:55:52 +0200
commit2b1f71ad0a5811632834175b3549a4cfadcae970 (patch)
tree3001d16ef1a35e1ecf8c8bba01b277628d644bbc
parent65ea70f50aafba9bfd50ffd8372be81c64a7ee66 (diff)
Initial implementation of multi orig support
-rw-r--r--gbp/deb.py39
-rw-r--r--gbp/git.py10
-rwxr-xr-xgit-buildpackage51
3 files changed, 91 insertions, 9 deletions
diff --git a/gbp/deb.py b/gbp/deb.py
index b50abbd..df3e25e 100644
--- a/gbp/deb.py
+++ b/gbp/deb.py
@@ -161,6 +161,30 @@ def orig_file(cp, compression):
return "%s_%s.orig.tar.%s" % (cp['Source'], cp['Upstream-Version'], ext)
+def orig_components(main, filelist):
+ """Given an orig tarball name and a list of files, this method
+ finds component tarballs in the list that belong to the first one.
+ @return dict(component_name=file_name, ...)
+ """
+ (path, name) = os.path.split(main)
+ if not name:
+ return False
+
+ m = re.search(r'^(?P<source>.+).orig.tar.(gz|bz2)', name)
+ if not m:
+ return False
+
+ list = {}
+ pattern = re.compile(r'%s.orig-(?P<component>[\w-]+).tar.(gz|bz2)' % (m.group('source')))
+ for f in filelist:
+ (path, name) = os.path.split(f)
+ m = pattern.search(name)
+ if m:
+ list[m.group('component')]=f
+
+ return list
+
+
def is_native(cp):
"Is this a debian native package"
return [ True, False ]['-' in cp['Version']]
@@ -204,6 +228,21 @@ def symlink_orig(cp, compression, orig_dir, output_dir, force=False):
os.symlink(src, dst)
except OSError:
return False
+
+ if not os.access(orig_dir, os.F_OK):
+ return False
+ for f in orig_components(src, os.listdir(orig_dir)).values():
+ src = os.path.join(orig_dir, f)
+ dst = os.path.join(output_dir, f)
+ if not os.access(src, os.F_OK):
+ return False
+ try:
+ if os.access(dst, os.F_OK) and force:
+ os.unlink(dst)
+ os.symlink(src, dst)
+ except OSError:
+ return False
+
return True
def do_uscan():
diff --git a/gbp/git.py b/gbp/git.py
index 7743bdd..30a2bb0 100644
--- a/gbp/git.py
+++ b/gbp/git.py
@@ -136,6 +136,16 @@ class GitRepository(object):
else:
return []
+ def branch_files(self, branch):
+ """List files in a branch"""
+ out, ret = self.__git_getoutput('ls-tree', ['-z','--name-only', '-r', branch])
+ if ret:
+ raise GitRepositoryError, "Error listing files %d" % ret
+ if out:
+ return [ file for file in out[0].split('\0') if file ]
+ else:
+ return []
+
def commits(self, since=None, until=None, paths=None, options=None):
"""get commits from start to end touching pathds"""
diff --git a/git-buildpackage b/git-buildpackage
index 7f2b2d4..75362a6 100755
--- a/git-buildpackage
+++ b/git-buildpackage
@@ -23,6 +23,7 @@ import errno
import os, os.path
import pipes
import sys
+import re
import time
import gbp.deb as du
from gbp.git import (GitRepositoryError, GitRepository, build_tag)
@@ -82,12 +83,13 @@ def dump_tree(export_dir, treeish):
def move_old_export(target):
- """move a build tree away if it exists"""
+ """move a build tree away if it exists. This function also create the target directory"""
try:
os.mkdir(target)
except OSError, (e, msg):
if e == errno.EEXIST:
os.rename(target, "%s.obsolete.%s" % (target, time.time()))
+ os.mkdir(target) # this time it can't fail
def prepare_output_dir(dir):
@@ -113,6 +115,14 @@ def pristine_tar_build_orig(repo, cp, output_dir, options):
if not repo.has_branch(pt.branch):
print >>sys.stderr, 'Pristine-tar branch "%s" not found' % pt.branch
pt.checkout(os.path.join(output_dir, du.orig_file(cp, options.comp_type)))
+
+ # find all files in pristine-tar branch
+ filelist = [ os.path.splitext(f) for f in repo.branch_files(pt.branch) ]
+ filelist = [ f[0] for f in filelist if f[1] == '.id' ]
+
+ # now build the required extra files
+ for f in du.orig_components(du.orig_file(cp, options.comp_type), filelist).values():
+ pt.checkout(os.path.join(output_dir, f))
return True
else:
return False
@@ -155,13 +165,8 @@ def drop_index(repo):
if os.path.exists(wc_index):
os.unlink(wc_index)
-def extract_orig(orig_tarball, dest_dir):
- """extract orig tarball to export dir before exporting from git"""
- print "Extracting %s to '%s'" % (os.path.basename(orig_tarball), dest_dir)
-
- move_old_export(dest_dir)
- du.unpack_orig(orig_tarball, dest_dir, '')
-
+def remove_toplevel(dest_dir):
+ """remove leading directory of a tar archive"""
# Check if tarball extracts into a single folder or not:
tar_topdir = du.tar_toplevel(dest_dir)
if tar_topdir != dest_dir:
@@ -174,6 +179,33 @@ def extract_orig(orig_tarball, dest_dir):
# Remove that single folder:
os.rmdir(tar_topdir)
+def extract_orig(orig_tarball, dest_dir, filter):
+ """extract orig tarball to export dir before exporting from git"""
+ print "Extracting %s to '%s'" % (os.path.basename(orig_tarball), dest_dir)
+
+ # move_old_export(dest_dir) was pushed up to the caller because we need to
+ # be able to extract an orig_tarball without side effects
+
+ # Make sure the destination dir exists and is empty
+ RemoveTree(dest_dir)()
+ os.mkdir(dest_dir)
+
+ # unpack the main tarball
+ du.unpack_orig(orig_tarball, dest_dir, filter)
+
+ # make sure to remove the top level folder if there is only one
+ remove_toplevel(dest_dir)
+
+ # eventually unpack the additional tarballs
+ src_dir = os.path.dirname(orig_tarball)
+ for c, f in du.orig_components(orig_tarball, os.listdir(src_dir)).iteritems():
+ component_dir = os.path.join(dest_dir, c)
+ print "Extracting %s to '%s'" % (f, component_dir)
+ RemoveTree(component_dir)()
+ os.mkdir(component_dir)
+ du.unpack_orig(os.path.join(src_dir, f), component_dir, filter)
+ remove_toplevel(component_dir)
+
def main(argv):
changelog = 'debian/changelog'
retval = 0
@@ -333,7 +365,8 @@ def main(argv):
if options.overlay:
if du.is_native(cp):
raise GbpError, "Cannot overlay Debian native package"
- extract_orig(os.path.join(output_dir, du.orig_file(cp, options.comp_type)), tmp_dir)
+ move_old_export(tmp_dir)
+ extract_orig(os.path.join(output_dir, du.orig_file(cp, options.comp_type)), tmp_dir, '')
print "Exporting '%s' to '%s'" % (options.export, tmp_dir)
dump_tree(tmp_dir, tree)