diff --git a/CHANGES.txt b/CHANGES.txt index 76aeed259..453fccbab 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -1,3 +1,12 @@ +v1.0.2: + +Changes since 1.0.0dev + +* tests - Use GIT_* envvars for author and committer +* Call higher level merge_base() to compare branches +* Add tests for _compare_branches() +* Skip create tag during finish if it already exists - The previous comparison of the merge base to either of the branches was not correct. + v1.0.0dev --------- diff --git a/gitflow/__init__.py b/gitflow/__init__.py index 46408d314..ccda0bb8b 100644 --- a/gitflow/__init__.py +++ b/gitflow/__init__.py @@ -13,7 +13,7 @@ # Distributed under a BSD-like license. For full terms see the file LICENSE.txt # -VERSION = (1, 0, 1,) +VERSION = (1, 0, 2,) __version__ = ".".join(map(str, VERSION[0:3])) + "".join(VERSION[3:]) __author__ = "Christian Assing, Hartmut Goebel, Vincent Driessen" diff --git a/gitflow/branches.py b/gitflow/branches.py index 32f885266..45bc8eb2f 100644 --- a/gitflow/branches.py +++ b/gitflow/branches.py @@ -423,11 +423,15 @@ def finish(self, name, fetch=False, rebase=False, keep=False, # In case a previous attempt to finish this release branch # has failed, but the tag was set successful, we skip it # now. - # :todo: check: if tag exists, it must point to the commit - tag = gitflow.tag( - tagname, self.gitflow.master_name(), - **tagging_info) - to_push.append(tagname) + if tagname not in self.gitflow.repo.tags: + tag = gitflow.tag( + tagname, self.gitflow.master_name(), + **tagging_info) + to_push.append(tagname) + elif self.gitflow.repo.tags[tagname].commit != self.gitflow.master().commit: + # if tag exists, it must point to the commit + raise TagExistsError('Tag already exists and does not point to %s branch %s' + % (self.identifier, name)) # merge the master branch back into develop; this makes the # master branch - and the new tag (if provided) - a parent of diff --git a/tests/gitflow/test_branches.py b/tests/gitflow/test_branches.py index cb02fbffa..f6c4d453f 100644 --- a/tests/gitflow/test_branches.py +++ b/tests/gitflow/test_branches.py @@ -20,7 +20,8 @@ HotfixBranchManager, SupportBranchManager) from tests.helpers import (copy_from_fixture, remote_clone_from_fixture, - fake_commit, all_commits, set_gnupg_home) + fake_commit, write_file, + all_commits, set_gnupg_home) from tests.helpers.factory import create_git_repo __copyright__ = "2010-2011 Vincent Driessen; 2012-2013 Hartmut Goebel; 2015 Christian Assing" @@ -1066,8 +1067,56 @@ def test_finish_release_unresolved_merge_conflict(self): self.assertRaises(GitCommandError, mgr.finish, '1.0') + @copy_from_fixture('release') + def test_finish_release_merge_conflict_tag(self): + """ + finish + tag with merge-conflicts on develop + """ + version_filename = 'VERSION' + new_version = '1.1\n' + + gitflow = GitFlow(self.repo).init() + fmgr = FeatureBranchManager(gitflow) + fmgr.finish('even') + fake_commit(self.repo, 'Overwrite version', + filename=version_filename, + change=new_version) + + # verify that the tag does not yet exist + # "v" comes form "versiontag" prefix in the gitflow config for the "release" fixture + self.assertNotIn('v1.0', self.repo.tags) + + mgr = ReleaseBranchManager(gitflow) + taginfo = dict( + message='Tagging version 1.0', + ) + self.assertRaises(MergeError, + mgr.finish, '1.0', tagging_info=taginfo) + + # verify that the tag exists, even though there was a failed merge + self.assertIn('v1.0', self.repo.tags) + + # resolve the conflict + # this is in favor of the change on develop + write_file(filename=version_filename, + append=False, + change=new_version) + gitflow.git.add(version_filename) + gitflow.git.commit('-F.git/MERGE_MSG') + # the release branch is still here + self.assertIn('rel/1.0', + [b.name for b in self.repo.branches]) + # finish the release again + # this should skip the tagging, since that part previously succeeded + mgr.finish('1.0', tagging_info=taginfo) + # now the release branch is gone + self.assertNotIn('rel/1.0', + [b.name for b in self.repo.branches]) + + # verify that the tag still exists + self.assertIn('v1.0', self.repo.tags) + # :todo: test-cases for finish with merge-conflicts on master - # :todo: test-cases for finish + tag with merge-conflicts on develop # :todo: test-cases for finish + tag with merge-conflicts on master diff --git a/tests/helpers/__init__.py b/tests/helpers/__init__.py index f6ebdcdf8..3795e53b8 100644 --- a/tests/helpers/__init__.py +++ b/tests/helpers/__init__.py @@ -177,16 +177,26 @@ def set_git_working_dir(repo, *args, **kwargs): return set_git_working_dir -@git_working_dir -def fake_commit(repo, message, append=True, filename='newfile.py'): +def write_file(filename, append, change): + """ + Write the contents of "change" into "filename" + + If "append", append to the end. Else, replace the contents. + """ if append: f = open(filename, 'a') else: f = open(filename, 'w') try: - f.write('This is a dummy change.\n') + f.write(change) finally: f.close() + + +@git_working_dir +def fake_commit(repo, message, append=True, + filename='newfile.py', change='This is a dummy change.\n'): + write_file(filename, append, change) repo.index.add([filename]) return repo.index.commit(message)