mirror of
https://github.com/x1xhlol/system-prompts-and-models-of-ai-tools.git
synced 2026-06-17 23:09:35 +00:00
87 lines
3.1 KiB
Python
87 lines
3.1 KiB
Python
"""Integration test for the GovernedPipeline (Phase 8 + Trust Plane)."""
|
|
|
|
from __future__ import annotations
|
|
|
|
import pytest
|
|
|
|
from dealix.execution import GovernedPipeline
|
|
from dealix.trust.policy import PolicyDecision
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_governed_pipeline_emits_decisions(sample_lead_payload, mock_router):
|
|
"""The governed pipeline must produce DecisionOutputs from the underlying run."""
|
|
mock_router.run.return_value.content = (
|
|
'{"pain_points":[{"text":"slow","category":"performance","severity":0.8}],'
|
|
'"urgency_score":0.9,"likely_offer":"X","recommended_next_step":"call","key_phrases":[]}'
|
|
)
|
|
|
|
governed = GovernedPipeline()
|
|
result = await governed.run(
|
|
payload=sample_lead_payload,
|
|
auto_book=False,
|
|
auto_proposal=False,
|
|
)
|
|
|
|
assert result.underlying.lead.id
|
|
# At minimum we expect pain + icp + qualification decisions
|
|
assert len(result.decisions) >= 2
|
|
|
|
# Every decision must carry classifications
|
|
for d in result.decisions:
|
|
assert d.approval_class is not None
|
|
assert d.reversibility_class is not None
|
|
assert d.sensitivity_class is not None
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_governed_pipeline_audits_every_step(sample_lead_payload, mock_router):
|
|
mock_router.run.return_value.content = '{"ok": true}'
|
|
governed = GovernedPipeline()
|
|
result = await governed.run(
|
|
payload=sample_lead_payload,
|
|
auto_book=False,
|
|
)
|
|
# Every emitted decision produces an audit entry
|
|
assert len(result.audit_trail) >= len(result.decisions)
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_governed_pipeline_escalates_high_stakes_actions(sample_lead_payload, mock_router):
|
|
"""When a tier-A lead is detected and a proposal is auto-generated,
|
|
the proposal-send NextAction should be ESCALATED (never auto-allowed)."""
|
|
mock_router.run.return_value.content = '{"ok": true}'
|
|
governed = GovernedPipeline()
|
|
result = await governed.run(
|
|
payload=sample_lead_payload,
|
|
auto_book=False,
|
|
auto_proposal=True, # force proposal generation
|
|
)
|
|
|
|
# Find any proposal_send action in the policy results
|
|
proposal_sends = [(d, a, r) for d, a, r in result.policy_results if a == "proposal_send"]
|
|
# If a proposal was generated, its send action must not be ALLOW
|
|
if proposal_sends:
|
|
for _d, _a, r in proposal_sends:
|
|
assert (
|
|
r.decision != PolicyDecision.ALLOW
|
|
), f"proposal_send was {r.decision.value} — should be ESCALATE"
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_governed_pipeline_creates_approval_requests(sample_lead_payload, mock_router):
|
|
"""Escalated actions must yield pending approval requests."""
|
|
mock_router.run.return_value.content = '{"ok": true}'
|
|
governed = GovernedPipeline()
|
|
result = await governed.run(
|
|
payload=sample_lead_payload,
|
|
auto_book=False,
|
|
auto_proposal=True,
|
|
)
|
|
|
|
# Count escalations vs approval requests — they should roughly match
|
|
n_escalations = sum(
|
|
1 for _, _, r in result.policy_results if r.decision == PolicyDecision.ESCALATE
|
|
)
|
|
assert len(result.approval_requests) == n_escalations
|