Move debian/changelog manipulation to gbp.deb.changelog.ChangeLog.
authorDaniel Dehennin <daniel.dehennin@baby-gnu.org>
Wed, 30 May 2012 19:30:45 +0000 (21:30 +0200)
committerGuido Günther <agx@sigxcpu.org>
Fri, 29 Mar 2013 12:08:23 +0000 (13:08 +0100)
spawn_dch switch gbp.command.wrappers.Command.

* gbp/deb/changelog.py (ChangeLog.spawn_dch): static method adapted from
  gbp.scripts.dch and converted to gbp.command_wrappers.Command.
  (add_entry): New method adapted from
  gbp.scripts.dch.add_changelog_entry.
  (add_section): New method adapted from
  gbp.scripts.dch.add_changelog_entry. Remove DebianGitRepository and
  options, this has nothing to do with changelog management.

* tests/test_Changelog.py: Test new methods.

* gbp/scripts/dch.py: Remove useless functions: system(), spawn_dch(),
  add_changelog_section() and add_changelog_entry().
  Update calls accordingly.
  (fixup_trailer): Use spawn_dch() method of ChangeLog class.
  (process_options): dch_options became a list.
  (main): Use add_section() and add_entry() methods of ChangeLog object.
  Take care of upstream version since ChangeLog.add_section() does not
  manage it anymore.
  Update exception handling, ChangeLog.spawn_dch() can raise
  "CommandExecFailed" exception.

Closes: #672954

gbp/deb/changelog.py
gbp/scripts/dch.py
tests/test_Changelog.py

index b1be400..2d2f016 100644 (file)
@@ -19,6 +19,7 @@
 import email
 import os
 import subprocess
+from gbp.command_wrappers import Command
 
 class NoChangeLogError(Exception):
     """No changelog found"""
@@ -214,3 +215,98 @@ class ChangeLog(object):
         Get sections in the changelog
         """
         return list(self.sections_iter)
+
+    @staticmethod
+    def spawn_dch(msg=[], author=None, email=None, newversion=False, version=None,
+                  release=False, distribution=None, dch_options=[]):
+        """
+        Spawn dch
+
+        @param author: committers name
+        @type author: C{str}
+        @param email: committers email
+        @type email: C{str}
+        @param newversion: start a new version
+        @type newversion: C{bool}
+        @param version: the verion to use
+        @type version: C{str}
+        @param release: finalize changelog for releaze
+        @type release: C{bool}
+        @param distribution: distribution to use
+        @type distribution: C{str}
+        @param dch_options: options passed verbatim to dch
+        @type dch_options: C{list}
+        """
+        env = {}
+        args = ['--no-auto-nmu']
+        if newversion:
+            if version:
+                try:
+                    args.append(version['increment'])
+                except KeyError:
+                    args.append('--newversion=%s' % version['version'])
+            else:
+                args.append('-i')
+        elif release:
+            args.extend(["--release", "--no-force-save-on-release"])
+            msg = None
+
+        if author and email:
+            env = {'DEBFULLNAME': author, 'DEBEMAIL': email}
+
+        if distribution:
+            args.append("--distribution=%s" % distribution)
+
+        args.extend(dch_options)
+        args.append('--')
+        if msg:
+            args.append('[[[insert-git-dch-commit-message-here]]]')
+        else:
+            args.append('')
+        dch = Command('dch', args, extra_env=env)
+        dch.call([])
+        if msg:
+            old_cl = open("debian/changelog", "r")
+            new_cl = open("debian/changelog.bak", "w")
+            for line in old_cl:
+                if line == "  * [[[insert-git-dch-commit-message-here]]]\n":
+                    print >> new_cl, "  * " + msg[0]
+                    for line in msg[1:]:
+                        print >> new_cl, "    " + line
+                else:
+                    print >> new_cl, line,
+            os.rename("debian/changelog.bak", "debian/changelog")
+
+    def add_entry(self, msg, author=None, email=None, dch_options=[]):
+        """Add a single changelog entry
+
+        @param msg: log message to add
+        @type msg: C{str}
+        @param author: name of the author of the log message
+        @type author: C{str}
+        @param email: email of the author of the log message
+        @type email: C{str}
+        @param dch_options: options passed verbatim to dch
+        @type dch_options: C{list}
+        """
+        self.spawn_dch(msg=msg, author=author, email=email, dch_options=dch_options)
+
+    def add_section(self, msg, distribution, author=None, email=None,
+                    version={}, dch_options=[]):
+        """Add a new section to the changelog
+
+        @param msg: log message to add
+        @type msg: C{str}
+        @param distribution: distribution to set for the new changelog entry
+        @type distribution: C{str}
+        @param author: name of the author of the log message
+        @type author: C{str}
+        @param email: email of the author of the log message
+        @type email: C{str}
+        @param version: version to set for the new changelog entry
+        @param version: C{dict}
+        @param dch_options: options passed verbatim to dch
+        @type dch_options: C{list}
+        """
+        self.spawn_dch(msg=msg, newversion=True, version=version, author=author,
+                       email=email, distribution=distribution, dch_options=dch_options)
index 86c0547..b31a67b 100644 (file)
@@ -35,72 +35,6 @@ user_customizations = {}
 snapshot_re = re.compile("\s*\*\* SNAPSHOT build @(?P<commit>[a-z0-9]+)\s+\*\*")
 
 
-def system(cmd):
-    try:
-        gbpc.Command(cmd, shell=True)()
-    except gbpc.CommandExecFailed:
-        raise GbpError
-
-
-def spawn_dch(msg=[], author=None, email=None, newversion=False, version=None,
-              release=False, distribution=None, dch_options=''):
-    """
-    Spawn dch
-
-    @param author: committers name
-    @param email: committers email
-    @param newversion: start a new version
-    @param version: the verion to use
-    @param release: finalize changelog for releaze
-    @param distribution: distribution to use
-    @param dch_options: options passed verbatim to dch
-    """
-    distopt = ""
-    versionopt = ""
-    env = ""
-
-    if newversion:
-        if version:
-            try:
-                versionopt = version['increment']
-            except KeyError:
-                versionopt = '--newversion=%s' % version['version']
-        else:
-            versionopt = '-i'
-    elif release:
-        versionopt = "--release --no-force-save-on-release"
-        msg = None
-
-    if author and email:
-        env = """DEBFULLNAME="%s" DEBEMAIL="%s" """ % (author, email)
-
-    if distribution:
-        distopt = "--distribution=%s" % distribution
-
-    cmd = '%(env)s dch --no-auto-nmu %(distopt)s %(versionopt)s %(dch_options)s ' % locals()
-    if msg:
-        cmd += '-- "[[[insert-git-dch-commit-message-here]]]"'
-    else:
-        cmd += '-- ""'
-    system(cmd)
-    if msg:
-        old_cl = open("debian/changelog", "r")
-        new_cl = open("debian/changelog.bak", "w")
-        for line in old_cl:
-            if line == "  * [[[insert-git-dch-commit-message-here]]]\n":
-                print >> new_cl, "  * " + msg[0]
-                for line in msg[1:]:
-                    print >> new_cl, "    " + line
-            else:
-                print >> new_cl, line,
-        os.rename("debian/changelog.bak", "debian/changelog")
-
-
-def add_changelog_entry(msg, author, email, dch_options):
-    """Add a single changelog entry"""
-    spawn_dch(msg=msg, author=author, email=email, dch_options=dch_options)
-
-
 def guess_version_from_upstream(repo, upstream_tag_format, cp):
     """
     Guess the version based on the latest version on the upstream branch
@@ -116,17 +50,6 @@ def guess_version_from_upstream(repo, upstream_tag_format, cp):
     return None
 
 
-def add_changelog_section(msg, distribution, repo, options, cp,
-                          author=None, email=None, version={}, dch_options=''):
-    """Add a new section to the changelog"""
-    if not version and not cp.is_native():
-        v = guess_version_from_upstream(repo, options.upstream_tag, cp)
-        if v:
-            version['version'] = v
-    spawn_dch(msg=msg, newversion=True, version=version, author=author,
-              email=email, distribution=distribution, dch_options=dch_options)
-
-
 def get_author_email(repo, use_git_config):
     """Get author and email from git configuration"""
     author = email = None
@@ -148,7 +71,7 @@ def fixup_trailer(repo, git_author, dch_options):
     creating the changelog
     """
     author, email = get_author_email(repo, git_author)
-    spawn_dch(msg='', author=author, email=email, dch_options=dch_options)
+    ChangeLog.spawn_dch(msg='', author=author, email=email, dch_options=dch_options)
 
 
 def snapshot_version(version):
@@ -221,7 +144,7 @@ def do_release(changelog, repo, cp, git_author, dch_options):
     if snapshot:
         cp['MangledVersion'] = release
         mangle_changelog(changelog, cp)
-    spawn_dch(release=True, author=author, email=email, dch_options=dch_options)
+    cp.spawn_dch(release=True, author=author, email=email, dch_options=dch_options)
 
 
 def do_snapshot(changelog, repo, next_snapshot):
@@ -289,15 +212,16 @@ def process_options(options, parser):
     if options.since and options.auto:
         parser.error("'--since' and '--auto' are incompatible options")
 
+    dch_options = []
     if options.multimaint_merge:
-        dch_options = "--multimaint-merge"
+        dch_options.append("--multimaint-merge")
     else:
-        dch_options = "--nomultimaint-merge"
+        dch_options.append("--nomultimaint-merge")
 
     if options.multimaint:
-        dch_options += " --multimaint"
+        dch_options.append("--multimaint")
     else:
-        dch_options += " --nomultimaint"
+        dch_options.append("--nomultimaint")
 
     get_customizations(options.customization_file)
     return dch_options
@@ -480,6 +404,12 @@ def main(argv):
         else:
             add_section = False
 
+        if add_section and not version_change and not cp.is_native():
+            # Get version from upstream if none provided
+            v = guess_version_from_upstream(repo, options.upstream_tag, cp)
+            if v:
+                version_change['version'] = v
+
         i = 0
         for c in commits:
             i += 1
@@ -493,18 +423,15 @@ def main(argv):
             if add_section:
                 # Add a section containing just this message (we can't
                 # add an empty section with dch)
-                add_changelog_section(distribution="UNRELEASED", msg=commit_msg,
-                                      version=version_change,
-                                      author=commit_author,
-                                      email=commit_email,
-                                      dch_options=dch_options,
-                                      repo=repo,
-                                      options=options,
-                                      cp=cp)
+                cp.add_section(distribution="UNRELEASED", msg=commit_msg,
+                               version=version_change,
+                               author=commit_author,
+                               email=commit_email,
+                               dch_options=dch_options)
                 # Adding a section only needs to happen once.
                 add_section = False
             else:
-                add_changelog_entry(commit_msg, commit_author, commit_email, dch_options)
+                cp.add_entry(commit_msg, commit_author, commit_email, dch_options)
 
 
         # Show a message if there were no commits (not even ignored
@@ -515,12 +442,9 @@ def main(argv):
         if add_section:
             # If we end up here, then there were no commits to include,
             # so we put a dummy message in the new section.
-            add_changelog_section(distribution="UNRELEASED", msg=["UNRELEASED"],
-                                  version=version_change,
-                                  dch_options=dch_options,
-                                  repo=repo,
-                                  options=options,
-                                  cp=cp)
+            cp.add_section(distribution="UNRELEASED", msg=["UNRELEASED"],
+                           version=version_change,
+                           dch_options=dch_options)
 
         fixup_trailer(repo, git_author=options.git_author,
                       dch_options=dch_options)
@@ -545,7 +469,7 @@ def main(argv):
             repo.commit_files([changelog], msg)
             gbp.log.info("Changelog has been committed for version %s" % version)
 
-    except (GbpError, GitRepositoryError, NoChangeLogError) as err:
+    except (gbpc.CommandExecFailed, GbpError, GitRepositoryError, NoChangeLogError) as err:
         if len(err.__str__()):
             gbp.log.err(err)
         ret = 1
index c67aaa0..5516d03 100644 (file)
@@ -223,3 +223,88 @@ def test_parse_sections():
     >>> cl.sections[1].version
     '0.5.31'
     """
+
+def test_add_section():
+    """
+    Test if we can add a section to an existant changelog
+
+    Methods tested:
+         - L{gbp.deb.changelog.ChangeLog.__init__}
+         - L{gbp.deb.changelog.ChangeLog._parse}
+         - L{gbp.deb.changelog.ChangeLog.add_section}
+         - L{gbp.deb.changelog.ChangeLog.spawn_dch}
+
+    >>> import os
+    >>> import tempfile
+    >>> import shutil
+    >>> import gbp.deb.changelog
+    >>> olddir = os.path.abspath(os.path.curdir)
+    >>> testdir = tempfile.mkdtemp(prefix='gbp-test-changelog-')
+    >>> testdebdir = os.path.join(testdir, 'debian')
+    >>> testclname = os.path.join(testdebdir, "changelog")
+    >>> os.mkdir(testdebdir)
+    >>> clh = open(os.path.join(testdebdir, "changelog"), "w")
+    >>> clh.write(cl_debian)
+    >>> clh.close()
+    >>> os.chdir(testdir)
+    >>> os.path.abspath(os.path.curdir) == testdir
+    True
+    >>> cl = gbp.deb.changelog.ChangeLog(filename=testclname)
+    >>> cl.add_section(msg=["Test add section"], distribution=None, author="Debian Maintainer", email="maint@debian.org")
+    >>> cl = gbp.deb.changelog.ChangeLog(filename=testclname)
+    >>> cl.version
+    '0.5.33'
+    >>> cl.debian_version
+    '0.5.33'
+    >>> cl['Distribution']
+    'UNRELEASED'
+    >>> 'Test add section' in cl['Changes']
+    True
+    >>> os.chdir(olddir)
+    >>> os.path.abspath(os.path.curdir) == olddir
+    True
+    >>> shutil.rmtree(testdir, ignore_errors=True)
+    """
+
+def test_add_entry():
+    """
+    Test if we can add an entry to an existant changelog
+
+    Methods tested:
+         - L{gbp.deb.changelog.ChangeLog.__init__}
+         - L{gbp.deb.changelog.ChangeLog._parse}
+         - L{gbp.deb.changelog.ChangeLog.add_entry}
+         - L{gbp.deb.changelog.ChangeLog.spawn_dch}
+
+    >>> import os
+    >>> import tempfile
+    >>> import shutil
+    >>> import gbp.deb.changelog
+    >>> olddir = os.path.abspath(os.path.curdir)
+    >>> testdir = tempfile.mkdtemp(prefix='gbp-test-changelog-')
+    >>> testdebdir = os.path.join(testdir, 'debian')
+    >>> testclname = os.path.join(testdebdir, "changelog")
+    >>> os.mkdir(testdebdir)
+    >>> clh = open(os.path.join(testdebdir, "changelog"), "w")
+    >>> clh.write(cl_debian)
+    >>> clh.close()
+    >>> os.chdir(testdir)
+    >>> os.path.abspath(os.path.curdir) == testdir
+    True
+    >>> cl = gbp.deb.changelog.ChangeLog(filename=testclname)
+    >>> cl.add_section(msg=["Test add section"], distribution=None, author="Debian Maintainer", email="maint@debian.org")
+    >>> cl.add_entry(msg=["Test add entry"], author="Debian Maintainer", email="maint@debian.org")
+    >>> cl = gbp.deb.changelog.ChangeLog(filename=testclname)
+    >>> cl.version
+    '0.5.33'
+    >>> cl.debian_version
+    '0.5.33'
+    >>> cl['Distribution']
+    'UNRELEASED'
+    >>> 'Test add entry' in cl['Changes']
+    True
+    >>> os.chdir(olddir)
+    >>> os.path.abspath(os.path.curdir) == olddir
+    True
+    >>> shutil.rmtree(testdir, ignore_errors=True)
+    """