test_grafts.py 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205
  1. # test_grafts.py -- Tests for graftpoints
  2. #
  3. # SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
  4. # Dulwich is dual-licensed under the Apache License, Version 2.0 and the GNU
  5. # General Public License as public by the Free Software Foundation; version 2.0
  6. # or (at your option) any later version. You can redistribute it and/or
  7. # modify it under the terms of either of these two licenses.
  8. #
  9. # Unless required by applicable law or agreed to in writing, software
  10. # distributed under the License is distributed on an "AS IS" BASIS,
  11. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. # See the License for the specific language governing permissions and
  13. # limitations under the License.
  14. #
  15. # You should have received a copy of the licenses; if not, see
  16. # <http://www.gnu.org/licenses/> for a copy of the GNU General Public License
  17. # and <http://www.apache.org/licenses/LICENSE-2.0> for a copy of the Apache
  18. # License, Version 2.0.
  19. #
  20. """Tests for graftpoints."""
  21. import os
  22. import shutil
  23. import tempfile
  24. from dulwich.errors import ObjectFormatException
  25. from dulwich.objects import Tree
  26. from dulwich.repo import MemoryRepo, Repo, parse_graftpoints, serialize_graftpoints
  27. from . import TestCase
  28. def makesha(digit):
  29. return (str(digit).encode("ascii") * 40)[:40]
  30. class GraftParserTests(TestCase):
  31. def assertParse(self, expected, graftpoints) -> None:
  32. self.assertEqual(expected, parse_graftpoints(iter(graftpoints)))
  33. def test_no_grafts(self) -> None:
  34. self.assertParse({}, [])
  35. def test_no_parents(self) -> None:
  36. self.assertParse({makesha(0): []}, [makesha(0)])
  37. def test_parents(self) -> None:
  38. self.assertParse(
  39. {makesha(0): [makesha(1), makesha(2)]},
  40. [b" ".join([makesha(0), makesha(1), makesha(2)])],
  41. )
  42. def test_multiple_hybrid(self) -> None:
  43. self.assertParse(
  44. {
  45. makesha(0): [],
  46. makesha(1): [makesha(2)],
  47. makesha(3): [makesha(4), makesha(5)],
  48. },
  49. [
  50. makesha(0),
  51. b" ".join([makesha(1), makesha(2)]),
  52. b" ".join([makesha(3), makesha(4), makesha(5)]),
  53. ],
  54. )
  55. class GraftSerializerTests(TestCase):
  56. def assertSerialize(self, expected, graftpoints) -> None:
  57. self.assertEqual(sorted(expected), sorted(serialize_graftpoints(graftpoints)))
  58. def test_no_grafts(self) -> None:
  59. self.assertSerialize(b"", {})
  60. def test_no_parents(self) -> None:
  61. self.assertSerialize(makesha(0), {makesha(0): []})
  62. def test_parents(self) -> None:
  63. self.assertSerialize(
  64. b" ".join([makesha(0), makesha(1), makesha(2)]),
  65. {makesha(0): [makesha(1), makesha(2)]},
  66. )
  67. def test_multiple_hybrid(self) -> None:
  68. self.assertSerialize(
  69. b"\n".join(
  70. [
  71. makesha(0),
  72. b" ".join([makesha(1), makesha(2)]),
  73. b" ".join([makesha(3), makesha(4), makesha(5)]),
  74. ]
  75. ),
  76. {
  77. makesha(0): [],
  78. makesha(1): [makesha(2)],
  79. makesha(3): [makesha(4), makesha(5)],
  80. },
  81. )
  82. class GraftsInRepositoryBase:
  83. def tearDown(self) -> None:
  84. super().tearDown()
  85. def get_repo_with_grafts(self, grafts):
  86. r = self._repo
  87. r._add_graftpoints(grafts)
  88. return r
  89. def test_no_grafts(self) -> None:
  90. r = self.get_repo_with_grafts({})
  91. shas = [e.commit.id for e in r.get_walker()]
  92. self.assertEqual(shas, self._shas[::-1])
  93. def test_no_parents_graft(self) -> None:
  94. r = self.get_repo_with_grafts({self._repo.head(): []})
  95. self.assertEqual([e.commit.id for e in r.get_walker()], [r.head()])
  96. def test_existing_parent_graft(self) -> None:
  97. r = self.get_repo_with_grafts({self._shas[-1]: [self._shas[0]]})
  98. self.assertEqual(
  99. [e.commit.id for e in r.get_walker()],
  100. [self._shas[-1], self._shas[0]],
  101. )
  102. def test_remove_graft(self) -> None:
  103. r = self.get_repo_with_grafts({self._repo.head(): []})
  104. r._remove_graftpoints([self._repo.head()])
  105. self.assertEqual([e.commit.id for e in r.get_walker()], self._shas[::-1])
  106. def test_object_store_fail_invalid_parents(self) -> None:
  107. r = self._repo
  108. self.assertRaises(
  109. ObjectFormatException, r._add_graftpoints, {self._shas[-1]: ["1"]}
  110. )
  111. class GraftsInRepoTests(GraftsInRepositoryBase, TestCase):
  112. def setUp(self) -> None:
  113. super().setUp()
  114. self._repo_dir = os.path.join(tempfile.mkdtemp())
  115. r = self._repo = Repo.init(self._repo_dir)
  116. self.addCleanup(shutil.rmtree, self._repo_dir)
  117. self._shas = []
  118. commit_kwargs = {
  119. "committer": b"Test Committer <test@nodomain.com>",
  120. "author": b"Test Author <test@nodomain.com>",
  121. "commit_timestamp": 12395,
  122. "commit_timezone": 0,
  123. "author_timestamp": 12395,
  124. "author_timezone": 0,
  125. }
  126. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))
  127. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))
  128. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))
  129. def test_init_with_empty_info_grafts(self) -> None:
  130. r = self._repo
  131. r._put_named_file(os.path.join("info", "grafts"), b"")
  132. r = Repo(self._repo_dir)
  133. self.assertEqual({}, r._graftpoints)
  134. def test_init_with_info_grafts(self) -> None:
  135. r = self._repo
  136. r._put_named_file(
  137. os.path.join("info", "grafts"),
  138. self._shas[-1] + b" " + self._shas[0],
  139. )
  140. r = Repo(self._repo_dir)
  141. self.assertEqual({self._shas[-1]: [self._shas[0]]}, r._graftpoints)
  142. class GraftsInMemoryRepoTests(GraftsInRepositoryBase, TestCase):
  143. def setUp(self) -> None:
  144. super().setUp()
  145. r = self._repo = MemoryRepo()
  146. self._shas = []
  147. tree = Tree()
  148. commit_kwargs = {
  149. "committer": b"Test Committer <test@nodomain.com>",
  150. "author": b"Test Author <test@nodomain.com>",
  151. "commit_timestamp": 12395,
  152. "commit_timezone": 0,
  153. "author_timestamp": 12395,
  154. "author_timezone": 0,
  155. "tree": tree.id,
  156. }
  157. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))
  158. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))
  159. self._shas.append(r.do_commit(b"empty commit", **commit_kwargs))