Files
agentci/tests/test_workflow_render.py
2026-07-22 23:10:23 +02:00

118 lines
3.7 KiB
Python

import json
import pytest
from agentci.workflows.model import (
AgentResult,
ReviewFinding,
ReviewReport,
ReviewSeverity,
)
from agentci.workflows.render import (
agent_comment,
commit_title,
final_comment,
pull_request_body,
report_for_prompt,
required_session,
result_comment,
review_markdown,
)
def report() -> ReviewReport:
return ReviewReport(
summary="One issue remains.",
findings=[
ReviewFinding(
severity=ReviewSeverity.MAJOR,
title="Missing validation",
detail="The empty input is not checked.",
location="src/widget.py:12",
recommendation="Reject empty input.",
)
],
)
def test_review_markdown_renders_user_visible_finding() -> None:
assert review_markdown(report()) == (
"## Remaining review findings\n\n"
"One issue remains.\n\n"
"### MAJOR: Missing validation \u2014 `src/widget.py:12`\n"
"The empty input is not checked.\n\n"
"Recommendation: Reject empty input."
)
assert review_markdown(ReviewReport(summary="Ready", findings=[])) == ""
def test_agent_and_final_comments_preserve_protocol_marker() -> None:
assert agent_comment("plan", "flow-1", "Plan body") == (
"<!-- agentci:plan workflow=flow-1 -->\nPlan body"
)
assert final_comment("plan", "flow-1", "Plan body", report()) == (
f"<!-- agentci:plan workflow=flow-1 -->\nPlan body\n\n{review_markdown(report())}"
)
assert (
final_comment("plan", "flow-1", "Plan body", ReviewReport(summary="Ready", findings=[]))
== "<!-- agentci:plan workflow=flow-1 -->\nPlan body"
)
def test_pull_request_body_and_result_comment_render_validation() -> None:
result = AgentResult(
summary_markdown="Implemented the widget fix.",
tests=["pytest: passed", "ruff: passed"],
)
assert pull_request_body(17, result) == (
"Closes #17\n\n"
"## Implementation\n\nImplemented the widget fix.\n\n"
"## Validation\n\n- pytest: passed\n- ruff: passed\n\n"
"_Created by Agent CI._"
)
assert result_comment(result, sha="abc123") == (
"## Agent result\n\nImplemented the widget fix.\n\n"
"## Validation\n\n- pytest: passed\n- ruff: passed\n\n"
"Commit: `abc123`"
)
def test_renderers_report_missing_validation() -> None:
result = AgentResult(summary_markdown="Applied the change.", tests=[])
assert "## Validation\n\n- Not reported" in pull_request_body(2, result)
assert result_comment(result) == (
"## Agent result\n\nApplied the change.\n\n## Validation\n\n- Not reported"
)
@pytest.mark.parametrize(
("markdown", "expected"),
[
("# Fix widget\n\nDetails", "Fix widget"),
("\n## Trim heading \n", "Trim heading"),
("\n\t\n", "apply requested changes"),
("x" * 80, "x" * 72),
],
)
def test_commit_title_uses_first_content_line(markdown: str, expected: str) -> None:
assert commit_title(markdown) == expected
def test_report_for_prompt_formats_json_and_preserves_unstructured_text() -> None:
stored = '{"summary":"Ready","findings":[]}'
formatted = report_for_prompt(stored)
assert json.loads(formatted) == {"summary": "Ready", "findings": []}
assert formatted == '{\n "summary": "Ready",\n "findings": []\n}'
assert report_for_prompt("plain text review") == "plain text review"
assert report_for_prompt(None) == "(none)"
def test_required_session_returns_value_or_fails_fast() -> None:
assert required_session("session-1") == "session-1"
with pytest.raises(RuntimeError, match="Expected a persisted OpenCode session ID"):
required_session(None)