|
1 | 1 | from typing import Any, List
|
2 | 2 | from unittest.mock import ANY, MagicMock, call, patch
|
| 3 | +import base64 |
3 | 4 |
|
4 | 5 | import pytest
|
| 6 | +from github import GithubException |
| 7 | +from github.InputGitTreeElement import InputGitTreeElement |
5 | 8 | from operatorcert import github
|
6 | 9 | from requests import HTTPError, Response
|
7 | 10 |
|
@@ -229,3 +232,141 @@ def test_close_pull_request() -> None:
|
229 | 232 | mock_pull_request.edit.assert_called_once_with(state="closed")
|
230 | 233 |
|
231 | 234 | assert resp == mock_pull_request
|
| 235 | + |
| 236 | + |
| 237 | +def test_copy_branch_success() -> None: |
| 238 | + mock_client = MagicMock() |
| 239 | + src_repo = mock_client.get_repo.return_value |
| 240 | + dest_repo = mock_client.get_repo.return_value |
| 241 | + |
| 242 | + src_branch_ref = MagicMock() |
| 243 | + src_branch_ref.commit.sha = "abc123" |
| 244 | + src_repo.get_branch.return_value = src_branch_ref |
| 245 | + |
| 246 | + dest_branch_ref = MagicMock() |
| 247 | + dest_branch_ref.commit.sha = "def456" |
| 248 | + dest_branch_ref.commit.commit.tree = MagicMock() |
| 249 | + dest_repo.get_branch.return_value = dest_branch_ref |
| 250 | + |
| 251 | + dest_repo.create_git_ref.return_value = MagicMock() |
| 252 | + |
| 253 | + mock_file = MagicMock() |
| 254 | + mock_file.path = "test.txt" |
| 255 | + mock_file.type = "file" |
| 256 | + mock_file.decoded_content = b"new content" |
| 257 | + |
| 258 | + src_repo.get_contents.side_effect = lambda path, ref: ( |
| 259 | + [mock_file] if path == "" else mock_file |
| 260 | + ) |
| 261 | + |
| 262 | + dest_repo.create_git_tree.return_value = MagicMock() |
| 263 | + dest_repo.create_git_commit.return_value = MagicMock(sha="new_commit_sha") |
| 264 | + |
| 265 | + ref_mock = MagicMock() |
| 266 | + dest_repo.get_git_ref.return_value = ref_mock |
| 267 | + |
| 268 | + github.copy_branch( |
| 269 | + mock_client, |
| 270 | + "org/source-repo", |
| 271 | + "main", |
| 272 | + "org/dest-repo", |
| 273 | + "copied-branch", |
| 274 | + ) |
| 275 | + |
| 276 | + dest_repo.create_git_ref.assert_called_once_with( |
| 277 | + ref="refs/heads/copied-branch", sha="def456" |
| 278 | + ) |
| 279 | + dest_repo.create_git_tree.assert_called() |
| 280 | + dest_repo.create_git_commit.assert_called() |
| 281 | + ref_mock.edit.assert_called_once_with("new_commit_sha") |
| 282 | + |
| 283 | + |
| 284 | +def test_copy_branch_with_nested_files() -> None: |
| 285 | + mock_client = MagicMock() |
| 286 | + src_repo = mock_client.get_repo.return_value |
| 287 | + dest_repo = mock_client.get_repo.return_value |
| 288 | + |
| 289 | + src_branch_ref = MagicMock() |
| 290 | + src_branch_ref.commit.sha = "abc123" |
| 291 | + src_repo.get_branch.return_value = src_branch_ref |
| 292 | + |
| 293 | + dest_branch_ref = MagicMock() |
| 294 | + dest_branch_ref.commit.sha = "def456" |
| 295 | + dest_branch_ref.commit.commit.tree = MagicMock() |
| 296 | + dest_repo.get_branch.return_value = dest_branch_ref |
| 297 | + |
| 298 | + dest_repo.create_git_ref.return_value = MagicMock() |
| 299 | + |
| 300 | + mock_dir = MagicMock() |
| 301 | + mock_dir.path = "dir1" |
| 302 | + mock_dir.type = "dir" |
| 303 | + |
| 304 | + mock_file = MagicMock() |
| 305 | + mock_file.path = "dir1/test.txt" |
| 306 | + mock_file.type = "file" |
| 307 | + mock_file.decoded_content = b"nested content" |
| 308 | + |
| 309 | + src_repo.get_contents.side_effect = lambda path, ref: ( |
| 310 | + [mock_dir] if path == "" else [mock_file] if path == "dir1" else mock_file |
| 311 | + ) |
| 312 | + |
| 313 | + dest_repo.create_git_tree.return_value = MagicMock() |
| 314 | + dest_repo.create_git_commit.return_value = MagicMock(sha="new_commit_sha") |
| 315 | + |
| 316 | + ref_mock = MagicMock() |
| 317 | + dest_repo.get_git_ref.return_value = ref_mock |
| 318 | + |
| 319 | + github.copy_branch( |
| 320 | + mock_client, |
| 321 | + "org/source-repo", |
| 322 | + "main", |
| 323 | + "org/dest-repo", |
| 324 | + "copied-branch", |
| 325 | + ) |
| 326 | + |
| 327 | + dest_repo.create_git_ref.assert_called_once_with( |
| 328 | + ref="refs/heads/copied-branch", sha="def456" |
| 329 | + ) |
| 330 | + dest_repo.create_git_tree.assert_called() |
| 331 | + dest_repo.create_git_commit.assert_called() |
| 332 | + ref_mock.edit.assert_called_once_with("new_commit_sha") |
| 333 | + |
| 334 | + |
| 335 | +def test_copy_branch_handles_github_exception() -> None: |
| 336 | + mock_client = MagicMock() |
| 337 | + mock_client.get_repo.side_effect = GithubException(500, "Internal Server Error", {}) |
| 338 | + |
| 339 | + with pytest.raises(GithubException): |
| 340 | + github.copy_branch( |
| 341 | + mock_client, |
| 342 | + "org/source-repo", |
| 343 | + "main", |
| 344 | + "org/dest-repo", |
| 345 | + "copied-branch", |
| 346 | + ) |
| 347 | + |
| 348 | + |
| 349 | +def test_delete_branch_success() -> None: |
| 350 | + mock_client = MagicMock() |
| 351 | + mock_repo = MagicMock() |
| 352 | + mock_client.get_repo.return_value = mock_repo |
| 353 | + |
| 354 | + branch_ref = MagicMock() |
| 355 | + mock_repo.get_git_ref.return_value = branch_ref |
| 356 | + |
| 357 | + github.delete_branch(mock_client, "org/repo-name", "old-feature-branch") |
| 358 | + |
| 359 | + mock_repo.get_git_ref.assert_called_once_with("heads/old-feature-branch") |
| 360 | + branch_ref.delete.assert_called_once() |
| 361 | + |
| 362 | + |
| 363 | +def test_delete_branch_when_branch_does_not_exist() -> None: |
| 364 | + mock_client = MagicMock() |
| 365 | + mock_repo = MagicMock() |
| 366 | + mock_get_git_ref = MagicMock() |
| 367 | + mock_client.get_repo.return_value = mock_repo |
| 368 | + mock_repo.get_git_ref.return_value = mock_get_git_ref |
| 369 | + mock_get_git_ref.delete.side_effect = GithubException(0, "err", None) |
| 370 | + |
| 371 | + with pytest.raises(GithubException): |
| 372 | + github.delete_branch(mock_client, "org/repo-name", "non-existent-branch") |
0 commit comments