summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Maw <richard.maw@codethink.co.uk>2013-11-11 18:01:47 +0000
committerRichard Maw <richard.maw@codethink.co.uk>2013-11-22 13:49:26 +0000
commit77d75eb06fa07c64b7e14c376fb6e3742ef33fb3 (patch)
tree4fb2ab6ee2d4f1ad72b99edd36daed1da93a37aa
parenta070b772a565a2803bb1ac4c63a1784cb249ecc3 (diff)
downloadmorph-77d75eb06fa07c64b7e14c376fb6e3742ef33fb3.tar.gz
GitDir: Add GitDirectory.commit_tree() method
This is used to create commit objects. This is used by build without commit to provide the behind-the-scenes history.
-rw-r--r--morphlib/gitdir.py20
-rw-r--r--morphlib/gitdir_tests.py33
2 files changed, 53 insertions, 0 deletions
diff --git a/morphlib/gitdir.py b/morphlib/gitdir.py
index 9020506a..aad507a6 100644
--- a/morphlib/gitdir.py
+++ b/morphlib/gitdir.py
@@ -17,6 +17,7 @@
import cliapp
+import itertools
import os
import morphlib
@@ -242,6 +243,25 @@ class GitDirectory(object):
return self._runcmd(['git', 'hash-object', '-t', 'blob',
'-w', '--stdin'], **kwargs).strip()
+ def commit_tree(self, tree, parent, message, **kwargs):
+ '''Create a commit'''
+ # NOTE: Will need extension for 0 or N parents.
+ env = {}
+ for who, info in itertools.product(('committer', 'author'),
+ ('name', 'email')):
+ argname = '%s_%s' % (who, info)
+ envname = 'GIT_%s_%s' % (who.upper(), info.upper())
+ if argname in kwargs:
+ env[envname] = kwargs[argname]
+ for who in ('committer', 'author'):
+ argname = '%s_date' % who
+ envname = 'GIT_%s_DATE' % who.upper()
+ if argname in kwargs:
+ env[envname] = kwargs[argname].isoformat()
+ return self._runcmd(['git', 'commit-tree', tree,
+ '-p', parent, '-m', message],
+ env=env).strip()
+
def init(dirname):
'''Initialise a new git repository.'''
diff --git a/morphlib/gitdir_tests.py b/morphlib/gitdir_tests.py
index a56df7c8..3063f5cf 100644
--- a/morphlib/gitdir_tests.py
+++ b/morphlib/gitdir_tests.py
@@ -16,6 +16,7 @@
# =*= License: GPL-2 =*=
+import datetime
import os
import shutil
import tempfile
@@ -178,3 +179,35 @@ class GitDirectoryContentsTests(unittest.TestCase):
with open(os.path.join(self.tempdir, 'blob'), 'r') as f:
sha1 = gd.store_blob(f)
self.assertEqual('test string', gd.get_blob_contents(sha1))
+
+ def test_commit_tree(self):
+ gd = morphlib.gitdir.GitDirectory(self.dirname)
+ parent = gd.resolve_ref_to_commit(gd.HEAD)
+ tree = gd.resolve_ref_to_tree(parent)
+ aname = 'Author Name'
+ aemail = 'author@email'
+ cname = 'Committer Name'
+ cemail = 'committer@email'
+ pseudo_now = datetime.datetime.fromtimestamp(683074800)
+
+ now_str = "683074800"
+ message= 'MESSAGE'
+ expected = [
+ "tree %(tree)s",
+ "parent %(parent)s",
+ "author %(aname)s <%(aemail)s> %(now_str)s +0000",
+ "committer %(cname)s <%(cemail)s> %(now_str)s +0000",
+ "",
+ "%(message)s",
+ "",
+ ]
+ expected = [l % locals() for l in expected]
+ commit = gd.commit_tree(tree, parent, message=message,
+ committer_name=cname,
+ committer_email=cemail,
+ committer_date=pseudo_now,
+ author_name=aname,
+ author_email=aemail,
+ author_date=pseudo_now,
+ )
+ self.assertEqual(expected, gd.get_commit_contents(commit).split('\n'))