123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731 |
- # test_porcelain.py -- porcelain tests
- # Copyright (C) 2013 Jelmer Vernooij <jelmer@samba.org>
- #
- # This program is free software; you can redistribute it and/or
- # modify it under the terms of the GNU General Public License
- # as published by the Free Software Foundation; version 2
- # of the License or (at your option) a later version.
- #
- # This program is distributed in the hope that it will be useful,
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- # GNU General Public License for more details.
- #
- # You should have received a copy of the GNU General Public License
- # along with this program; if not, write to the Free Software
- # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
- # MA 02110-1301, USA.
- """Tests for dulwich.porcelain."""
- from contextlib import closing
- from io import BytesIO
- import os
- import shutil
- import tarfile
- import tempfile
- from dulwich import porcelain
- from dulwich.diff_tree import tree_changes
- from dulwich.objects import (
- Blob,
- Tag,
- Tree,
- )
- from dulwich.repo import Repo
- from dulwich.tests import (
- TestCase,
- )
- from dulwich.tests.compat.utils import require_git_version
- from dulwich.tests.utils import (
- build_commit_graph,
- make_object,
- )
- class PorcelainTestCase(TestCase):
- def setUp(self):
- super(PorcelainTestCase, self).setUp()
- repo_dir = tempfile.mkdtemp()
- self.addCleanup(shutil.rmtree, repo_dir)
- self.repo = Repo.init(repo_dir)
- def tearDown(self):
- super(PorcelainTestCase, self).tearDown()
- self.repo.close()
- class ArchiveTests(PorcelainTestCase):
- """Tests for the archive command."""
- def test_simple(self):
- # TODO(jelmer): Remove this once dulwich has its own implementation of archive.
- require_git_version((1, 5, 0))
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1], [3, 1, 2]])
- self.repo.refs[b"refs/heads/master"] = c3.id
- out = BytesIO()
- err = BytesIO()
- porcelain.archive(self.repo.path, b"refs/heads/master", outstream=out,
- errstream=err)
- self.assertEqual(b"", err.getvalue())
- tf = tarfile.TarFile(fileobj=out)
- self.addCleanup(tf.close)
- self.assertEqual([], tf.getnames())
- class UpdateServerInfoTests(PorcelainTestCase):
- def test_simple(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"refs/heads/foo"] = c3.id
- porcelain.update_server_info(self.repo.path)
- self.assertTrue(os.path.exists(os.path.join(self.repo.controldir(),
- 'info', 'refs')))
- class CommitTests(PorcelainTestCase):
- def test_custom_author(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"refs/heads/foo"] = c3.id
- sha = porcelain.commit(self.repo.path, message=b"Some message",
- author=b"Joe <joe@example.com>", committer=b"Bob <bob@example.com>")
- self.assertTrue(isinstance(sha, bytes))
- self.assertEqual(len(sha), 40)
- class CloneTests(PorcelainTestCase):
- def test_simple_local(self):
- f1_1 = make_object(Blob, data=b'f1')
- commit_spec = [[1], [2, 1], [3, 1, 2]]
- trees = {1: [(b'f1', f1_1), (b'f2', f1_1)],
- 2: [(b'f1', f1_1), (b'f2', f1_1)],
- 3: [(b'f1', f1_1), (b'f2', f1_1)], }
- c1, c2, c3 = build_commit_graph(self.repo.object_store,
- commit_spec, trees)
- self.repo.refs[b"refs/heads/master"] = c3.id
- target_path = tempfile.mkdtemp()
- errstream = BytesIO()
- self.addCleanup(shutil.rmtree, target_path)
- r = porcelain.clone(self.repo.path, target_path,
- checkout=False, errstream=errstream)
- self.assertEqual(r.path, target_path)
- self.assertEqual(Repo(target_path).head(), c3.id)
- self.assertTrue(b'f1' not in os.listdir(target_path))
- self.assertTrue(b'f2' not in os.listdir(target_path))
- def test_simple_local_with_checkout(self):
- f1_1 = make_object(Blob, data=b'f1')
- commit_spec = [[1], [2, 1], [3, 1, 2]]
- trees = {1: [(b'f1', f1_1), (b'f2', f1_1)],
- 2: [(b'f1', f1_1), (b'f2', f1_1)],
- 3: [(b'f1', f1_1), (b'f2', f1_1)], }
- c1, c2, c3 = build_commit_graph(self.repo.object_store,
- commit_spec, trees)
- self.repo.refs[b"refs/heads/master"] = c3.id
- target_path = tempfile.mkdtemp()
- errstream = BytesIO()
- self.addCleanup(shutil.rmtree, target_path)
- with closing(porcelain.clone(self.repo.path, target_path,
- checkout=True,
- errstream=errstream)) as r:
- self.assertEqual(r.path, target_path)
- with closing(Repo(target_path)) as r:
- self.assertEqual(r.head(), c3.id)
- self.assertTrue('f1' in os.listdir(target_path))
- self.assertTrue('f2' in os.listdir(target_path))
- def test_bare_local_with_checkout(self):
- f1_1 = make_object(Blob, data=b'f1')
- commit_spec = [[1], [2, 1], [3, 1, 2]]
- trees = {1: [(b'f1', f1_1), (b'f2', f1_1)],
- 2: [(b'f1', f1_1), (b'f2', f1_1)],
- 3: [(b'f1', f1_1), (b'f2', f1_1)], }
- c1, c2, c3 = build_commit_graph(self.repo.object_store,
- commit_spec, trees)
- self.repo.refs[b"refs/heads/master"] = c3.id
- target_path = tempfile.mkdtemp()
- errstream = BytesIO()
- self.addCleanup(shutil.rmtree, target_path)
- r = porcelain.clone(self.repo.path, target_path,
- bare=True, errstream=errstream)
- self.assertEqual(r.path, target_path)
- self.assertEqual(Repo(target_path).head(), c3.id)
- self.assertFalse(b'f1' in os.listdir(target_path))
- self.assertFalse(b'f2' in os.listdir(target_path))
- def test_no_checkout_with_bare(self):
- f1_1 = make_object(Blob, data=b'f1')
- commit_spec = [[1]]
- trees = {1: [(b'f1', f1_1), (b'f2', f1_1)]}
- (c1, ) = build_commit_graph(self.repo.object_store, commit_spec, trees)
- self.repo.refs[b"refs/heads/master"] = c1.id
- target_path = tempfile.mkdtemp()
- errstream = BytesIO()
- self.addCleanup(shutil.rmtree, target_path)
- self.assertRaises(ValueError, porcelain.clone, self.repo.path,
- target_path, checkout=True, bare=True, errstream=errstream)
- class InitTests(TestCase):
- def test_non_bare(self):
- repo_dir = tempfile.mkdtemp()
- self.addCleanup(shutil.rmtree, repo_dir)
- porcelain.init(repo_dir)
- def test_bare(self):
- repo_dir = tempfile.mkdtemp()
- self.addCleanup(shutil.rmtree, repo_dir)
- porcelain.init(repo_dir, bare=True)
- class AddTests(PorcelainTestCase):
- def test_add_default_paths(self):
- # create a file for initial commit
- with open(os.path.join(self.repo.path, 'blah'), 'w') as f:
- f.write("\n")
- porcelain.add(repo=self.repo.path, paths=['blah'])
- porcelain.commit(repo=self.repo.path, message=b'test',
- author=b'test', committer=b'test')
- # Add a second test file and a file in a directory
- with open(os.path.join(self.repo.path, 'foo'), 'w') as f:
- f.write("\n")
- os.mkdir(os.path.join(self.repo.path, 'adir'))
- with open(os.path.join(self.repo.path, 'adir', 'afile'), 'w') as f:
- f.write("\n")
- porcelain.add(self.repo.path)
- # Check that foo was added and nothing in .git was modified
- index = self.repo.open_index()
- self.assertEqual(sorted(index), [b'adir/afile', b'blah', b'foo'])
- def test_add_file(self):
- with open(os.path.join(self.repo.path, 'foo'), 'w') as f:
- f.write("BAR")
- porcelain.add(self.repo.path, paths=["foo"])
- class RemoveTests(PorcelainTestCase):
- def test_remove_file(self):
- with open(os.path.join(self.repo.path, 'foo'), 'w') as f:
- f.write("BAR")
- porcelain.add(self.repo.path, paths=["foo"])
- porcelain.rm(self.repo.path, paths=["foo"])
- class LogTests(PorcelainTestCase):
- def test_simple(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- outstream = BytesIO()
- porcelain.log(self.repo.path, outstream=outstream)
- self.assertEqual(3, outstream.getvalue().count(b"-" * 50))
- def test_max_entries(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- outstream = BytesIO()
- porcelain.log(self.repo.path, outstream=outstream, max_entries=1)
- self.assertEqual(1, outstream.getvalue().count(b"-" * 50))
- class ShowTests(PorcelainTestCase):
- def test_nolist(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- outstream = BytesIO()
- porcelain.show(self.repo.path, objects=c3.id, outstream=outstream)
- self.assertTrue(outstream.getvalue().startswith(b"-" * 50))
- def test_simple(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- outstream = BytesIO()
- porcelain.show(self.repo.path, objects=[c3.id], outstream=outstream)
- self.assertTrue(outstream.getvalue().startswith(b"-" * 50))
- def test_blob(self):
- b = Blob.from_string(b"The Foo\n")
- self.repo.object_store.add_object(b)
- outstream = BytesIO()
- porcelain.show(self.repo.path, objects=[b.id], outstream=outstream)
- self.assertEqual(outstream.getvalue(), b"The Foo\n")
- class SymbolicRefTests(PorcelainTestCase):
- def test_set_wrong_symbolic_ref(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- self.assertRaises(ValueError, porcelain.symbolic_ref, self.repo.path, b'foobar')
- def test_set_force_wrong_symbolic_ref(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- porcelain.symbolic_ref(self.repo.path, b'force_foobar', force=True)
- #test if we actually changed the file
- with self.repo.get_named_file('HEAD') as f:
- new_ref = f.read()
- self.assertEqual(new_ref, b'ref: refs/heads/force_foobar\n')
- def test_set_symbolic_ref(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- porcelain.symbolic_ref(self.repo.path, b'master')
- def test_set_symbolic_ref_other_than_master(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]], attrs=dict(refs='develop'))
- self.repo.refs[b"HEAD"] = c3.id
- self.repo.refs[b"refs/heads/develop"] = c3.id
- porcelain.symbolic_ref(self.repo.path, b'develop')
- #test if we actually changed the file
- with self.repo.get_named_file('HEAD') as f:
- new_ref = f.read()
- self.assertEqual(new_ref, b'ref: refs/heads/develop\n')
- class DiffTreeTests(PorcelainTestCase):
- def test_empty(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- outstream = BytesIO()
- porcelain.diff_tree(self.repo.path, c2.tree, c3.tree, outstream=outstream)
- self.assertEqual(outstream.getvalue(), b"")
- class CommitTreeTests(PorcelainTestCase):
- def test_simple(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- b = Blob()
- b.data = b"foo the bar"
- t = Tree()
- t.add(b"somename", 0o100644, b.id)
- self.repo.object_store.add_object(t)
- self.repo.object_store.add_object(b)
- sha = porcelain.commit_tree(
- self.repo.path, t.id, message=b"Withcommit.",
- author=b"Joe <joe@example.com>",
- committer=b"Jane <jane@example.com>")
- self.assertTrue(isinstance(sha, bytes))
- self.assertEqual(len(sha), 40)
- class RevListTests(PorcelainTestCase):
- def test_simple(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- outstream = BytesIO()
- porcelain.rev_list(
- self.repo.path, [c3.id], outstream=outstream)
- self.assertEqual(
- c3.id + b"\n" +
- c2.id + b"\n" +
- c1.id + b"\n",
- outstream.getvalue())
- class TagCreateTests(PorcelainTestCase):
- def test_annotated(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- porcelain.tag_create(self.repo.path, b"tryme", b'foo <foo@bar.com>',
- b'bar', annotated=True)
- tags = self.repo.refs.as_dict(b"refs/tags")
- self.assertEqual(list(tags.keys()), [b"tryme"])
- tag = self.repo[b'refs/tags/tryme']
- self.assertTrue(isinstance(tag, Tag))
- self.assertEqual(b"foo <foo@bar.com>", tag.tagger)
- self.assertEqual(b"bar", tag.message)
- def test_unannotated(self):
- c1, c2, c3 = build_commit_graph(self.repo.object_store, [[1], [2, 1],
- [3, 1, 2]])
- self.repo.refs[b"HEAD"] = c3.id
- porcelain.tag_create(self.repo.path, b"tryme", annotated=False)
- tags = self.repo.refs.as_dict(b"refs/tags")
- self.assertEqual(list(tags.keys()), [b"tryme"])
- self.repo[b'refs/tags/tryme']
- self.assertEqual(list(tags.values()), [self.repo.head()])
- class TagListTests(PorcelainTestCase):
- def test_empty(self):
- tags = porcelain.tag_list(self.repo.path)
- self.assertEqual([], tags)
- def test_simple(self):
- self.repo.refs[b"refs/tags/foo"] = b"aa" * 20
- self.repo.refs[b"refs/tags/bar/bla"] = b"bb" * 20
- tags = porcelain.tag_list(self.repo.path)
- self.assertEqual([b"bar/bla", b"foo"], tags)
- class TagDeleteTests(PorcelainTestCase):
- def test_simple(self):
- [c1] = build_commit_graph(self.repo.object_store, [[1]])
- self.repo[b"HEAD"] = c1.id
- porcelain.tag_create(self.repo, b'foo')
- self.assertTrue(b"foo" in porcelain.tag_list(self.repo))
- porcelain.tag_delete(self.repo, b'foo')
- self.assertFalse(b"foo" in porcelain.tag_list(self.repo))
- class ResetTests(PorcelainTestCase):
- def test_hard_head(self):
- with open(os.path.join(self.repo.path, 'foo'), 'w') as f:
- f.write("BAR")
- porcelain.add(self.repo.path, paths=["foo"])
- porcelain.commit(self.repo.path, message=b"Some message",
- committer=b"Jane <jane@example.com>",
- author=b"John <john@example.com>")
- with open(os.path.join(self.repo.path, 'foo'), 'wb') as f:
- f.write(b"OOH")
- porcelain.reset(self.repo, "hard", b"HEAD")
- index = self.repo.open_index()
- changes = list(tree_changes(self.repo,
- index.commit(self.repo.object_store),
- self.repo[b'HEAD'].tree))
- self.assertEqual([], changes)
- class PushTests(PorcelainTestCase):
- def test_simple(self):
- """
- Basic test of porcelain push where self.repo is the remote. First
- clone the remote, commit a file to the clone, then push the changes
- back to the remote.
- """
- outstream = BytesIO()
- errstream = BytesIO()
- porcelain.commit(repo=self.repo.path, message=b'init',
- author=b'', committer=b'')
- # Setup target repo cloned from temp test repo
- clone_path = tempfile.mkdtemp()
- target_repo = porcelain.clone(self.repo.path, target=clone_path, errstream=errstream)
- target_repo.close()
- # create a second file to be pushed back to origin
- handle, fullpath = tempfile.mkstemp(dir=clone_path)
- os.close(handle)
- porcelain.add(repo=clone_path, paths=[os.path.basename(fullpath)])
- porcelain.commit(repo=clone_path, message=b'push',
- author=b'', committer=b'')
- # Setup a non-checked out branch in the remote
- refs_path = b"refs/heads/foo"
- self.repo[refs_path] = self.repo[b'HEAD']
- # Push to the remote
- porcelain.push(clone_path, self.repo.path, refs_path, outstream=outstream,
- errstream=errstream)
- # Check that the target and source
- with closing(Repo(clone_path)) as r_clone:
- # Get the change in the target repo corresponding to the add
- # this will be in the foo branch.
- change = list(tree_changes(self.repo, self.repo[b'HEAD'].tree,
- self.repo[b'refs/heads/foo'].tree))[0]
- self.assertEqual(r_clone[b'HEAD'].id, self.repo[refs_path].id)
- self.assertEqual(os.path.basename(fullpath), change.new.path.decode('ascii'))
- class PullTests(PorcelainTestCase):
- def test_simple(self):
- outstream = BytesIO()
- errstream = BytesIO()
- # create a file for initial commit
- handle, fullpath = tempfile.mkstemp(dir=self.repo.path)
- os.close(handle)
- filename = os.path.basename(fullpath)
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test',
- author=b'test', committer=b'test')
- # Setup target repo
- target_path = tempfile.mkdtemp()
- target_repo = porcelain.clone(self.repo.path, target=target_path,
- errstream=errstream)
- target_repo.close()
- # create a second file to be pushed
- handle, fullpath = tempfile.mkstemp(dir=self.repo.path)
- os.close(handle)
- filename = os.path.basename(fullpath)
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test2',
- author=b'test2', committer=b'test2')
- # Pull changes into the cloned repo
- porcelain.pull(target_path, self.repo.path, b'refs/heads/master',
- outstream=outstream, errstream=errstream)
- # Check the target repo for pushed changes
- with closing(Repo(target_path)) as r:
- self.assertEqual(r[b'HEAD'].id, self.repo[b'HEAD'].id)
- class StatusTests(PorcelainTestCase):
- def test_status(self):
- """Integration test for `status` functionality."""
- # Commit a dummy file then modify it
- fullpath = os.path.join(self.repo.path, 'foo')
- with open(fullpath, 'w') as f:
- f.write('origstuff')
- porcelain.add(repo=self.repo.path, paths=['foo'])
- porcelain.commit(repo=self.repo.path, message=b'test status',
- author=b'', committer=b'')
- # modify access and modify time of path
- os.utime(fullpath, (0, 0))
- with open(fullpath, 'wb') as f:
- f.write(b'stuff')
- # Make a dummy file and stage it
- filename_add = 'bar'
- fullpath = os.path.join(self.repo.path, filename_add)
- with open(fullpath, 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename_add)
- results = porcelain.status(self.repo)
- self.assertEqual(results.staged['add'][0], filename_add.encode('ascii'))
- self.assertEqual(results.unstaged, [b'foo'])
- def test_get_tree_changes_add(self):
- """Unit test for get_tree_changes add."""
- # Make a dummy file, stage
- filename = 'bar'
- with open(os.path.join(self.repo.path, filename), 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test status',
- author=b'', committer=b'')
- filename = 'foo'
- with open(os.path.join(self.repo.path, filename), 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- changes = porcelain.get_tree_changes(self.repo.path)
- self.assertEqual(changes['add'][0], filename.encode('ascii'))
- self.assertEqual(len(changes['add']), 1)
- self.assertEqual(len(changes['modify']), 0)
- self.assertEqual(len(changes['delete']), 0)
- def test_get_tree_changes_modify(self):
- """Unit test for get_tree_changes modify."""
- # Make a dummy file, stage, commit, modify
- filename = 'foo'
- fullpath = os.path.join(self.repo.path, filename)
- with open(fullpath, 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test status',
- author=b'', committer=b'')
- with open(fullpath, 'w') as f:
- f.write('otherstuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- changes = porcelain.get_tree_changes(self.repo.path)
- self.assertEqual(changes['modify'][0], filename.encode('ascii'))
- self.assertEqual(len(changes['add']), 0)
- self.assertEqual(len(changes['modify']), 1)
- self.assertEqual(len(changes['delete']), 0)
- def test_get_tree_changes_delete(self):
- """Unit test for get_tree_changes delete."""
- # Make a dummy file, stage, commit, remove
- filename = 'foo'
- with open(os.path.join(self.repo.path, filename), 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test status',
- author=b'', committer=b'')
- porcelain.rm(repo=self.repo.path, paths=[filename])
- changes = porcelain.get_tree_changes(self.repo.path)
- self.assertEqual(changes['delete'][0], filename.encode('ascii'))
- self.assertEqual(len(changes['add']), 0)
- self.assertEqual(len(changes['modify']), 0)
- self.assertEqual(len(changes['delete']), 1)
- # TODO(jelmer): Add test for dulwich.porcelain.daemon
- class UploadPackTests(PorcelainTestCase):
- """Tests for upload_pack."""
- def test_upload_pack(self):
- outf = BytesIO()
- exitcode = porcelain.upload_pack(self.repo.path, BytesIO(b"0000"), outf)
- outlines = outf.getvalue().splitlines()
- self.assertEqual([b"0000"], outlines)
- self.assertEqual(0, exitcode)
- class ReceivePackTests(PorcelainTestCase):
- """Tests for receive_pack."""
- def test_receive_pack(self):
- filename = 'foo'
- with open(os.path.join(self.repo.path, filename), 'w') as f:
- f.write('stuff')
- porcelain.add(repo=self.repo.path, paths=filename)
- self.repo.do_commit(message=b'test status',
- author=b'', committer=b'', author_timestamp=1402354300,
- commit_timestamp=1402354300, author_timezone=0, commit_timezone=0)
- outf = BytesIO()
- exitcode = porcelain.receive_pack(self.repo.path, BytesIO(b"0000"), outf)
- outlines = outf.getvalue().splitlines()
- self.assertEqual([
- b'005a9e65bdcf4a22cdd4f3700604a275cd2aaf146b23 HEAD\x00report-status '
- b'delete-refs side-band-64k',
- b'003f9e65bdcf4a22cdd4f3700604a275cd2aaf146b23 refs/heads/master',
- b'0000'], outlines)
- self.assertEqual(0, exitcode)
- class BranchListTests(PorcelainTestCase):
- def test_standard(self):
- self.assertEqual(set([]), set(porcelain.branch_list(self.repo)))
- def test_new_branch(self):
- [c1] = build_commit_graph(self.repo.object_store, [[1]])
- self.repo[b"HEAD"] = c1.id
- porcelain.branch_create(self.repo, b"foo")
- self.assertEqual(
- set([b"master", b"foo"]),
- set(porcelain.branch_list(self.repo)))
- class BranchCreateTests(PorcelainTestCase):
- def test_branch_exists(self):
- [c1] = build_commit_graph(self.repo.object_store, [[1]])
- self.repo[b"HEAD"] = c1.id
- porcelain.branch_create(self.repo, b"foo")
- self.assertRaises(KeyError, porcelain.branch_create, self.repo, b"foo")
- porcelain.branch_create(self.repo, b"foo", force=True)
- def test_new_branch(self):
- [c1] = build_commit_graph(self.repo.object_store, [[1]])
- self.repo[b"HEAD"] = c1.id
- porcelain.branch_create(self.repo, b"foo")
- self.assertEqual(
- set([b"master", b"foo"]),
- set(porcelain.branch_list(self.repo)))
- class BranchDeleteTests(PorcelainTestCase):
- def test_simple(self):
- [c1] = build_commit_graph(self.repo.object_store, [[1]])
- self.repo[b"HEAD"] = c1.id
- porcelain.branch_create(self.repo, b'foo')
- self.assertTrue(b"foo" in porcelain.branch_list(self.repo))
- porcelain.branch_delete(self.repo, b'foo')
- self.assertFalse(b"foo" in porcelain.branch_list(self.repo))
- class FetchTests(PorcelainTestCase):
- def test_simple(self):
- outstream = BytesIO()
- errstream = BytesIO()
- # create a file for initial commit
- handle, fullpath = tempfile.mkstemp(dir=self.repo.path)
- os.close(handle)
- filename = os.path.basename(fullpath)
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test',
- author=b'test', committer=b'test')
- # Setup target repo
- target_path = tempfile.mkdtemp()
- target_repo = porcelain.clone(self.repo.path, target=target_path,
- errstream=errstream)
- # create a second file to be pushed
- handle, fullpath = tempfile.mkstemp(dir=self.repo.path)
- os.close(handle)
- filename = os.path.basename(fullpath)
- porcelain.add(repo=self.repo.path, paths=filename)
- porcelain.commit(repo=self.repo.path, message=b'test2',
- author=b'test2', committer=b'test2')
- self.assertFalse(self.repo[b'HEAD'].id in target_repo)
- target_repo.close()
- # Fetch changes into the cloned repo
- porcelain.fetch(target_path, self.repo.path, outstream=outstream,
- errstream=errstream)
- # Check the target repo for pushed changes
- with closing(Repo(target_path)) as r:
- self.assertTrue(self.repo[b'HEAD'].id in r)
|