test: 7 agents — plugins ~158 tests, extractor 98-100%, dashboard routes 99-100%, git services 94-100%, services 94-100%, dataset_review 100%. Fix test_api_key_routes.py sys.modules pollution
This commit is contained in:
@@ -477,4 +477,210 @@ class TestCreateGiteaPullRequest:
|
||||
"feature", "main", "PR title",
|
||||
)
|
||||
# #endregion test_pr_unexpected_response
|
||||
|
||||
# #region test_pr_404_with_branch_detail [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_pr_404_with_branch_detail(self):
|
||||
"""404 with branch missing → HTTPException 400 with detail."""
|
||||
svc = TestableGitGitea()
|
||||
with patch.object(svc, "_gitea_request", side_effect=HTTPException(status_code=404, detail="not found")), \
|
||||
patch.object(svc, "_build_gitea_pr_404_detail", new_callable=AsyncMock, return_value="Gitea branch not found: source branch 'feature' in owner/repo"):
|
||||
with pytest.raises(HTTPException) as exc_info:
|
||||
await svc.create_gitea_pull_request(
|
||||
"https://gitea.com", "pat", "https://gitea.com/owner/repo.git",
|
||||
"feature", "main", "PR title",
|
||||
)
|
||||
assert exc_info.value.status_code == 400
|
||||
# #endregion test_pr_404_with_branch_detail
|
||||
|
||||
# #region test_pr_404_retry_with_fallback [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_pr_404_retry_with_fallback(self):
|
||||
"""404 with different fallback URL → retries with fallback."""
|
||||
svc = TestableGitGitea()
|
||||
call_count = 0
|
||||
async def mock_request(method, url, pat, endpoint, payload=None):
|
||||
nonlocal call_count
|
||||
call_count += 1
|
||||
if call_count == 1:
|
||||
raise HTTPException(status_code=404, detail="not found")
|
||||
if call_count == 2:
|
||||
raise HTTPException(status_code=404, detail="not found on fallback")
|
||||
return {"number": 1, "html_url": "http://fallback/pr/1", "state": "open"}
|
||||
# _derive_server_url_from_remote returns different URL than primary
|
||||
with patch.object(svc, "_gitea_request", side_effect=mock_request), \
|
||||
patch.object(svc, "_derive_server_url_from_remote", return_value="http://fallback.example.com"), \
|
||||
patch.object(svc, "_build_gitea_pr_404_detail", new_callable=AsyncMock, return_value=None):
|
||||
with pytest.raises(HTTPException):
|
||||
await svc.create_gitea_pull_request(
|
||||
"http://primary.example.com", "pat", "http://different.example.com/owner/repo.git",
|
||||
"feature", "main", "PR title",
|
||||
)
|
||||
assert call_count == 2
|
||||
# #endregion test_pr_404_retry_with_fallback
|
||||
|
||||
# #region test_pr_404_retry_with_branch_detail [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_pr_404_retry_with_branch_detail(self):
|
||||
"""Fallback retry 404 → builds branch detail."""
|
||||
svc = TestableGitGitea()
|
||||
call_count = 0
|
||||
async def mock_request(method, url, pat, endpoint, payload=None):
|
||||
nonlocal call_count
|
||||
call_count += 1
|
||||
if call_count == 1:
|
||||
raise HTTPException(status_code=404, detail="not found")
|
||||
raise HTTPException(status_code=404, detail="not found on fallback")
|
||||
with patch.object(svc, "_gitea_request", side_effect=mock_request), \
|
||||
patch.object(svc, "_derive_server_url_from_remote", return_value="http://fallback.example.com"), \
|
||||
patch.object(svc, "_build_gitea_pr_404_detail", new_callable=AsyncMock, return_value="Gitea branch not found: source branch 'feature' in owner/repo"):
|
||||
with pytest.raises(HTTPException) as exc_info:
|
||||
await svc.create_gitea_pull_request(
|
||||
"http://primary.example.com", "pat", "http://different.example.com/owner/repo.git",
|
||||
"feature", "main", "PR title",
|
||||
)
|
||||
assert exc_info.value.status_code == 400
|
||||
assert "branch not found" in exc_info.value.detail
|
||||
# #endregion test_pr_404_retry_with_branch_detail
|
||||
|
||||
|
||||
# ── _build_gitea_pr_404_detail ──
|
||||
|
||||
class TestBuildGiteaPR404Detail:
|
||||
"""_build_gitea_pr_404_detail — specific branch missing message."""
|
||||
|
||||
# #region test_source_branch_missing [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_source_branch_missing(self):
|
||||
"""Source branch not found → specific message."""
|
||||
svc = TestableGitGitea()
|
||||
with patch.object(svc, "_gitea_branch_exists", new_callable=AsyncMock, side_effect=[False, True]):
|
||||
result = await svc._build_gitea_pr_404_detail(
|
||||
"https://gitea.com", "pat", "owner", "repo", "feature", "main"
|
||||
)
|
||||
assert result is not None
|
||||
assert "source branch" in result
|
||||
assert "feature" in result
|
||||
# #endregion test_source_branch_missing
|
||||
|
||||
# #region test_target_branch_missing [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_target_branch_missing(self):
|
||||
"""Target branch not found → specific message."""
|
||||
svc = TestableGitGitea()
|
||||
with patch.object(svc, "_gitea_branch_exists", new_callable=AsyncMock, side_effect=[True, False]):
|
||||
result = await svc._build_gitea_pr_404_detail(
|
||||
"https://gitea.com", "pat", "owner", "repo", "feature", "main"
|
||||
)
|
||||
assert result is not None
|
||||
assert "target branch" in result
|
||||
assert "main" in result
|
||||
# #endregion test_target_branch_missing
|
||||
|
||||
# #region test_both_branches_exist [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_both_branches_exist(self):
|
||||
"""Both branches exist → returns None."""
|
||||
svc = TestableGitGitea()
|
||||
with patch.object(svc, "_gitea_branch_exists", new_callable=AsyncMock, return_value=True):
|
||||
result = await svc._build_gitea_pr_404_detail(
|
||||
"https://gitea.com", "pat", "owner", "repo", "feature", "main"
|
||||
)
|
||||
assert result is None
|
||||
# #endregion test_both_branches_exist
|
||||
|
||||
|
||||
# ── _gitea_request edge ──
|
||||
|
||||
class TestGiteaRequestEdge:
|
||||
"""_gitea_request — error response handling edges."""
|
||||
|
||||
# #region test_request_error_json_parse_fallback [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_request_error_json_parse_fallback(self):
|
||||
"""Error response with unparseable JSON → falls back to response.text."""
|
||||
svc = TestableGitGitea()
|
||||
resp = MagicMock()
|
||||
resp.status_code = 500
|
||||
resp.text = "Internal Server Error"
|
||||
resp.json.side_effect = Exception("invalid json")
|
||||
svc._http_client.request.return_value = resp
|
||||
with pytest.raises(HTTPException, match="Gitea API error: Internal Server Error"):
|
||||
await svc._gitea_request("GET", "https://gitea.com", "pat", "/user")
|
||||
# #endregion test_request_error_json_parse_fallback
|
||||
|
||||
|
||||
# ── create_gitea_repository edge ──
|
||||
|
||||
class TestCreateGiteaRepositoryEdge:
|
||||
"""create_gitea_repository — optional params and raise paths."""
|
||||
|
||||
# #region test_create_repo_with_description [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_create_repo_with_description(self):
|
||||
"""Description and default_branch passed in payload."""
|
||||
svc = TestableGitGitea()
|
||||
created = {"name": "my-repo"}
|
||||
with patch.object(svc, "_gitea_request", new_callable=AsyncMock, return_value=created) as mock_req:
|
||||
result = await svc.create_gitea_repository(
|
||||
"https://gitea.com", "pat", "my-repo",
|
||||
private=True, description="My repo", default_branch="main"
|
||||
)
|
||||
assert result["name"] == "my-repo"
|
||||
call_kwargs = mock_req.call_args[1]
|
||||
assert call_kwargs["payload"]["description"] == "My repo"
|
||||
assert call_kwargs["payload"]["default_branch"] == "main"
|
||||
# #endregion test_create_repo_with_description
|
||||
|
||||
# #region test_create_repo_conflict_non_dict_response [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_create_repo_conflict_non_dict_response(self):
|
||||
"""409 conflict but existing fetch returns non-dict → raises original."""
|
||||
svc = TestableGitGitea()
|
||||
call_count = 0
|
||||
async def mock_request(method, url, pat, endpoint, payload=None):
|
||||
nonlocal call_count
|
||||
call_count += 1
|
||||
if method == "POST":
|
||||
raise HTTPException(status_code=409, detail="conflict")
|
||||
if call_count <= 2:
|
||||
return {"login": "user"}
|
||||
return ["not", "a", "dict"] # non-dict from GET /repos/{owner}/{name}
|
||||
with patch.object(svc, "_gitea_request", side_effect=mock_request):
|
||||
with pytest.raises(HTTPException) as exc_info:
|
||||
await svc.create_gitea_repository("https://gitea.com", "pat", "existing-repo")
|
||||
assert exc_info.value.status_code == 409
|
||||
# #endregion test_create_repo_conflict_non_dict_response
|
||||
|
||||
# #region test_create_repo_without_description [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_create_repo_without_description(self):
|
||||
"""No description/default_branch → not in payload."""
|
||||
svc = TestableGitGitea()
|
||||
created = {"name": "simple-repo"}
|
||||
with patch.object(svc, "_gitea_request", new_callable=AsyncMock, return_value=created) as mock_req:
|
||||
result = await svc.create_gitea_repository(
|
||||
"https://gitea.com", "pat", "simple-repo"
|
||||
)
|
||||
assert result["name"] == "simple-repo"
|
||||
call_kwargs = mock_req.call_args[1]
|
||||
assert "description" not in call_kwargs.get("payload", {})
|
||||
# #endregion test_create_repo_without_description
|
||||
|
||||
|
||||
# ── _gitea_branch_exists edge ──
|
||||
|
||||
class TestGiteaBranchExistsEdge:
|
||||
"""_gitea_branch_exists — non-404 error re-raises."""
|
||||
|
||||
# #region test_branch_exists_raises_non_404 [C:2] [TYPE Function]
|
||||
@pytest.mark.asyncio
|
||||
async def test_branch_exists_raises_non_404(self):
|
||||
"""Non-404 HTTPException → re-raised."""
|
||||
svc = TestableGitGitea()
|
||||
with patch.object(svc, "_gitea_request", side_effect=HTTPException(status_code=500, detail="server error")):
|
||||
with pytest.raises(HTTPException, match="server error"):
|
||||
await svc._gitea_branch_exists("https://gitea.com", "pat", "owner", "repo", "dev")
|
||||
# #endregion test_branch_exists_raises_non_404
|
||||
|
||||
# #endregion Test.Git.Gitea
|
||||
|
||||
Reference in New Issue
Block a user