Files
roboco/tests/unit/services/test_task_soft_block.py
T

116 lines
3.2 KiB
Python
Raw Normal View History

"""soft_block_task_for_agent forwards the typed resolver_type unchanged.
The schema 422s a typo at the boundary; this test pins the handler side —
a HUMAN request stays HUMAN, not silently downgraded to AGENT.
"""
from __future__ import annotations
from typing import TYPE_CHECKING
from unittest.mock import AsyncMock
from uuid import uuid4
import pytest
import pytest_asyncio
from roboco.db.tables import AgentTable, ProjectTable
from roboco.models import AgentRole, AgentStatus, Team
from roboco.models.base import (
BlockerResolverType,
Complexity,
TaskNature,
TaskStatus,
TaskType,
)
from roboco.models.permissions import AgentContext
from roboco.models.task import TaskCreateRequest
from roboco.services.task import SoftBlockInput, TaskService
if TYPE_CHECKING:
from collections.abc import AsyncIterator
from sqlalchemy.ext.asyncio import AsyncSession
@pytest_asyncio.fixture
async def soft_block_setup(
db_session: AsyncSession, monkeypatch: pytest.MonkeyPatch
) -> AsyncIterator[dict]:
async def _no_commit() -> None:
await db_session.flush()
monkeypatch.setattr(db_session, "commit", _no_commit)
agent = AgentTable(
id=uuid4(),
name="Dev",
slug=f"be-dev-{uuid4().hex[:8]}",
role=AgentRole.DEVELOPER,
team=Team.BACKEND,
status=AgentStatus.ACTIVE,
model_config={},
system_prompt="dev",
capabilities=[],
permissions={},
metrics={},
)
db_session.add(agent)
project = ProjectTable(
id=uuid4(),
name="P",
slug=f"p-{uuid4().hex[:8]}",
git_url="https://example.com/r.git",
assigned_cell=Team.BACKEND,
created_by=agent.id,
)
db_session.add(project)
await db_session.flush()
yield {
"svc": TaskService(db_session),
"agent_id": agent.id,
"project_id": project.id,
}
@pytest.mark.asyncio
async def test_soft_block_handler_preserves_human_resolver(
soft_block_setup: dict, db_session: AsyncSession, monkeypatch: pytest.MonkeyPatch
) -> None:
svc = soft_block_setup["svc"]
agent_id = soft_block_setup["agent_id"]
task = await svc.create(
TaskCreateRequest(
title="t",
description="d",
acceptance_criteria=["ac"],
team=Team.BACKEND,
created_by=agent_id,
project_id=soft_block_setup["project_id"],
task_type=TaskType.CODE,
nature=TaskNature.TECHNICAL,
estimated_complexity=Complexity.MEDIUM,
)
)
task.assigned_to = agent_id
task.status = TaskStatus.IN_PROGRESS
await db_session.flush()
monkeypatch.setattr(
"roboco.services.notification_delivery.get_notification_delivery_service",
lambda _s: AsyncMock(),
)
req = SoftBlockInput(
blocker_type="external",
reason="r",
what_needed="w",
resolver_type=BlockerResolverType.HUMAN,
)
out = await svc.soft_block_task_for_agent(
task.id,
AgentContext(
agent_id=agent_id, role=AgentRole.DEVELOPER, team=Team.BACKEND, slug="s"
),
req,
)
assert out.blocker_resolver_type == BlockerResolverType.HUMAN