mirror of
https://github.com/crewAIInc/crewAI.git
synced 2026-01-23 07:08:14 +00:00
Apply automatic linting fixes to tests directory
Co-Authored-By: Joe Moura <joao@crewai.com>
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
import asyncio
|
||||
from datetime import datetime
|
||||
from typing import NoReturn
|
||||
|
||||
import pytest
|
||||
from pydantic import BaseModel
|
||||
@@ -17,17 +18,17 @@ from crewai.utilities.events import (
|
||||
from crewai.utilities.events.flow_events import FlowPlotEvent
|
||||
|
||||
|
||||
def test_simple_sequential_flow():
|
||||
def test_simple_sequential_flow() -> None:
|
||||
"""Test a simple flow with two steps called sequentially."""
|
||||
execution_order = []
|
||||
|
||||
class SimpleFlow(Flow):
|
||||
@start()
|
||||
def step_1(self):
|
||||
def step_1(self) -> None:
|
||||
execution_order.append("step_1")
|
||||
|
||||
@listen(step_1)
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
execution_order.append("step_2")
|
||||
|
||||
flow = SimpleFlow()
|
||||
@@ -36,25 +37,25 @@ def test_simple_sequential_flow():
|
||||
assert execution_order == ["step_1", "step_2"]
|
||||
|
||||
|
||||
def test_flow_with_multiple_starts():
|
||||
def test_flow_with_multiple_starts() -> None:
|
||||
"""Test a flow with multiple start methods."""
|
||||
execution_order = []
|
||||
|
||||
class MultiStartFlow(Flow):
|
||||
@start()
|
||||
def step_a(self):
|
||||
def step_a(self) -> None:
|
||||
execution_order.append("step_a")
|
||||
|
||||
@start()
|
||||
def step_b(self):
|
||||
def step_b(self) -> None:
|
||||
execution_order.append("step_b")
|
||||
|
||||
@listen(step_a)
|
||||
def step_c(self):
|
||||
def step_c(self) -> None:
|
||||
execution_order.append("step_c")
|
||||
|
||||
@listen(step_b)
|
||||
def step_d(self):
|
||||
def step_d(self) -> None:
|
||||
execution_order.append("step_d")
|
||||
|
||||
flow = MultiStartFlow()
|
||||
@@ -68,7 +69,7 @@ def test_flow_with_multiple_starts():
|
||||
assert execution_order.index("step_d") > execution_order.index("step_b")
|
||||
|
||||
|
||||
def test_cyclic_flow():
|
||||
def test_cyclic_flow() -> None:
|
||||
"""Test a cyclic flow that runs a finite number of iterations."""
|
||||
execution_order = []
|
||||
|
||||
@@ -77,17 +78,17 @@ def test_cyclic_flow():
|
||||
max_iterations = 3
|
||||
|
||||
@start("loop")
|
||||
def step_1(self):
|
||||
def step_1(self) -> None:
|
||||
if self.iteration >= self.max_iterations:
|
||||
return # Do not proceed further
|
||||
execution_order.append(f"step_1_{self.iteration}")
|
||||
|
||||
@listen(step_1)
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
execution_order.append(f"step_2_{self.iteration}")
|
||||
|
||||
@router(step_2)
|
||||
def step_3(self):
|
||||
def step_3(self) -> str:
|
||||
execution_order.append(f"step_3_{self.iteration}")
|
||||
self.iteration += 1
|
||||
if self.iteration < self.max_iterations:
|
||||
@@ -105,21 +106,21 @@ def test_cyclic_flow():
|
||||
assert execution_order == expected_order
|
||||
|
||||
|
||||
def test_flow_with_and_condition():
|
||||
def test_flow_with_and_condition() -> None:
|
||||
"""Test a flow where a step waits for multiple other steps to complete."""
|
||||
execution_order = []
|
||||
|
||||
class AndConditionFlow(Flow):
|
||||
@start()
|
||||
def step_1(self):
|
||||
def step_1(self) -> None:
|
||||
execution_order.append("step_1")
|
||||
|
||||
@start()
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
execution_order.append("step_2")
|
||||
|
||||
@listen(and_(step_1, step_2))
|
||||
def step_3(self):
|
||||
def step_3(self) -> None:
|
||||
execution_order.append("step_3")
|
||||
|
||||
flow = AndConditionFlow()
|
||||
@@ -132,21 +133,21 @@ def test_flow_with_and_condition():
|
||||
assert execution_order.index("step_3") > execution_order.index("step_2")
|
||||
|
||||
|
||||
def test_flow_with_or_condition():
|
||||
def test_flow_with_or_condition() -> None:
|
||||
"""Test a flow where a step is triggered when any of multiple steps complete."""
|
||||
execution_order = []
|
||||
|
||||
class OrConditionFlow(Flow):
|
||||
@start()
|
||||
def step_a(self):
|
||||
def step_a(self) -> None:
|
||||
execution_order.append("step_a")
|
||||
|
||||
@start()
|
||||
def step_b(self):
|
||||
def step_b(self) -> None:
|
||||
execution_order.append("step_b")
|
||||
|
||||
@listen(or_(step_a, step_b))
|
||||
def step_c(self):
|
||||
def step_c(self) -> None:
|
||||
execution_order.append("step_c")
|
||||
|
||||
flow = OrConditionFlow()
|
||||
@@ -155,32 +156,32 @@ def test_flow_with_or_condition():
|
||||
assert "step_a" in execution_order or "step_b" in execution_order
|
||||
assert "step_c" in execution_order
|
||||
assert execution_order.index("step_c") > min(
|
||||
execution_order.index("step_a"), execution_order.index("step_b")
|
||||
execution_order.index("step_a"), execution_order.index("step_b"),
|
||||
)
|
||||
|
||||
|
||||
def test_flow_with_router():
|
||||
def test_flow_with_router() -> None:
|
||||
"""Test a flow that uses a router method to determine the next step."""
|
||||
execution_order = []
|
||||
|
||||
class RouterFlow(Flow):
|
||||
@start()
|
||||
def start_method(self):
|
||||
def start_method(self) -> None:
|
||||
execution_order.append("start_method")
|
||||
|
||||
@router(start_method)
|
||||
def router(self):
|
||||
def router(self) -> str:
|
||||
execution_order.append("router")
|
||||
# Ensure the condition is set to True to follow the "step_if_true" path
|
||||
condition = True
|
||||
return "step_if_true" if condition else "step_if_false"
|
||||
|
||||
@listen("step_if_true")
|
||||
def truthy(self):
|
||||
def truthy(self) -> None:
|
||||
execution_order.append("step_if_true")
|
||||
|
||||
@listen("step_if_false")
|
||||
def falsy(self):
|
||||
def falsy(self) -> None:
|
||||
execution_order.append("step_if_false")
|
||||
|
||||
flow = RouterFlow()
|
||||
@@ -189,18 +190,18 @@ def test_flow_with_router():
|
||||
assert execution_order == ["start_method", "router", "step_if_true"]
|
||||
|
||||
|
||||
def test_async_flow():
|
||||
def test_async_flow() -> None:
|
||||
"""Test an asynchronous flow."""
|
||||
execution_order = []
|
||||
|
||||
class AsyncFlow(Flow):
|
||||
@start()
|
||||
async def step_1(self):
|
||||
async def step_1(self) -> None:
|
||||
execution_order.append("step_1")
|
||||
await asyncio.sleep(0.1)
|
||||
|
||||
@listen(step_1)
|
||||
async def step_2(self):
|
||||
async def step_2(self) -> None:
|
||||
execution_order.append("step_2")
|
||||
await asyncio.sleep(0.1)
|
||||
|
||||
@@ -210,18 +211,19 @@ def test_async_flow():
|
||||
assert execution_order == ["step_1", "step_2"]
|
||||
|
||||
|
||||
def test_flow_with_exceptions():
|
||||
def test_flow_with_exceptions() -> None:
|
||||
"""Test flow behavior when exceptions occur in steps."""
|
||||
execution_order = []
|
||||
|
||||
class ExceptionFlow(Flow):
|
||||
@start()
|
||||
def step_1(self):
|
||||
def step_1(self) -> NoReturn:
|
||||
execution_order.append("step_1")
|
||||
raise ValueError("An error occurred in step_1")
|
||||
msg = "An error occurred in step_1"
|
||||
raise ValueError(msg)
|
||||
|
||||
@listen(step_1)
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
execution_order.append("step_2")
|
||||
|
||||
flow = ExceptionFlow()
|
||||
@@ -233,17 +235,17 @@ def test_flow_with_exceptions():
|
||||
assert execution_order == ["step_1"]
|
||||
|
||||
|
||||
def test_flow_restart():
|
||||
def test_flow_restart() -> None:
|
||||
"""Test restarting a flow after it has completed."""
|
||||
execution_order = []
|
||||
|
||||
class RestartableFlow(Flow):
|
||||
@start()
|
||||
def step_1(self):
|
||||
def step_1(self) -> None:
|
||||
execution_order.append("step_1")
|
||||
|
||||
@listen(step_1)
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
execution_order.append("step_2")
|
||||
|
||||
flow = RestartableFlow()
|
||||
@@ -253,20 +255,20 @@ def test_flow_restart():
|
||||
assert execution_order == ["step_1", "step_2", "step_1", "step_2"]
|
||||
|
||||
|
||||
def test_flow_with_custom_state():
|
||||
def test_flow_with_custom_state() -> None:
|
||||
"""Test a flow that maintains and modifies internal state."""
|
||||
|
||||
class StateFlow(Flow):
|
||||
def __init__(self):
|
||||
def __init__(self) -> None:
|
||||
super().__init__()
|
||||
self.counter = 0
|
||||
|
||||
@start()
|
||||
def step_1(self):
|
||||
def step_1(self) -> None:
|
||||
self.counter += 1
|
||||
|
||||
@listen(step_1)
|
||||
def step_2(self):
|
||||
def step_2(self) -> None:
|
||||
self.counter *= 2
|
||||
assert self.counter == 2
|
||||
|
||||
@@ -275,13 +277,13 @@ def test_flow_with_custom_state():
|
||||
assert flow.counter == 2
|
||||
|
||||
|
||||
def test_flow_uuid_unstructured():
|
||||
def test_flow_uuid_unstructured() -> None:
|
||||
"""Test that unstructured (dictionary) flow states automatically get a UUID that persists."""
|
||||
initial_id = None
|
||||
|
||||
class UUIDUnstructuredFlow(Flow):
|
||||
@start()
|
||||
def first_method(self):
|
||||
def first_method(self) -> None:
|
||||
nonlocal initial_id
|
||||
# Verify ID is automatically generated
|
||||
assert "id" in self.state
|
||||
@@ -292,7 +294,7 @@ def test_flow_uuid_unstructured():
|
||||
self.state["data"] = "example"
|
||||
|
||||
@listen(first_method)
|
||||
def second_method(self):
|
||||
def second_method(self) -> None:
|
||||
# Ensure the ID persists after state updates
|
||||
assert "id" in self.state
|
||||
assert self.state["id"] == initial_id
|
||||
@@ -308,7 +310,7 @@ def test_flow_uuid_unstructured():
|
||||
assert len(flow.state["id"]) == 36
|
||||
|
||||
|
||||
def test_flow_uuid_structured():
|
||||
def test_flow_uuid_structured() -> None:
|
||||
"""Test that structured (Pydantic) flow states automatically get a UUID that persists."""
|
||||
initial_id = None
|
||||
|
||||
@@ -318,7 +320,7 @@ def test_flow_uuid_structured():
|
||||
|
||||
class UUIDStructuredFlow(Flow[MyStructuredState]):
|
||||
@start()
|
||||
def first_method(self):
|
||||
def first_method(self) -> None:
|
||||
nonlocal initial_id
|
||||
# Verify ID is automatically generated and accessible as attribute
|
||||
assert hasattr(self.state, "id")
|
||||
@@ -330,7 +332,7 @@ def test_flow_uuid_structured():
|
||||
self.state.message = "updated"
|
||||
|
||||
@listen(first_method)
|
||||
def second_method(self):
|
||||
def second_method(self) -> None:
|
||||
# Ensure the ID persists after state updates
|
||||
assert hasattr(self.state, "id")
|
||||
assert self.state.id == initial_id
|
||||
@@ -350,42 +352,41 @@ def test_flow_uuid_structured():
|
||||
assert flow.state.message == "final"
|
||||
|
||||
|
||||
def test_router_with_multiple_conditions():
|
||||
def test_router_with_multiple_conditions() -> None:
|
||||
"""Test a router that triggers when any of multiple steps complete (OR condition),
|
||||
and another router that triggers only after all specified steps complete (AND condition).
|
||||
"""
|
||||
|
||||
execution_order = []
|
||||
|
||||
class ComplexRouterFlow(Flow):
|
||||
@start()
|
||||
def step_a(self):
|
||||
def step_a(self) -> None:
|
||||
execution_order.append("step_a")
|
||||
|
||||
@start()
|
||||
def step_b(self):
|
||||
def step_b(self) -> None:
|
||||
execution_order.append("step_b")
|
||||
|
||||
@router(or_("step_a", "step_b"))
|
||||
def router_or(self):
|
||||
def router_or(self) -> str:
|
||||
execution_order.append("router_or")
|
||||
return "next_step_or"
|
||||
|
||||
@listen("next_step_or")
|
||||
def handle_next_step_or_event(self):
|
||||
def handle_next_step_or_event(self) -> None:
|
||||
execution_order.append("handle_next_step_or_event")
|
||||
|
||||
@listen(handle_next_step_or_event)
|
||||
def branch_2_step(self):
|
||||
def branch_2_step(self) -> None:
|
||||
execution_order.append("branch_2_step")
|
||||
|
||||
@router(and_(handle_next_step_or_event, branch_2_step))
|
||||
def router_and(self):
|
||||
def router_and(self) -> str:
|
||||
execution_order.append("router_and")
|
||||
return "final_step"
|
||||
|
||||
@listen("final_step")
|
||||
def log_final_step(self):
|
||||
def log_final_step(self) -> None:
|
||||
execution_order.append("log_final_step")
|
||||
|
||||
flow = ComplexRouterFlow()
|
||||
@@ -401,7 +402,7 @@ def test_router_with_multiple_conditions():
|
||||
|
||||
# Check that the AND router triggered after both relevant steps:
|
||||
assert execution_order.index("router_and") > execution_order.index(
|
||||
"handle_next_step_or_event"
|
||||
"handle_next_step_or_event",
|
||||
)
|
||||
assert execution_order.index("router_and") > execution_order.index("branch_2_step")
|
||||
|
||||
@@ -409,23 +410,24 @@ def test_router_with_multiple_conditions():
|
||||
assert execution_order.index("log_final_step") > execution_order.index("router_and")
|
||||
|
||||
|
||||
def test_unstructured_flow_event_emission():
|
||||
def test_unstructured_flow_event_emission() -> None:
|
||||
"""Test that the correct events are emitted during unstructured flow
|
||||
execution with all fields validated."""
|
||||
execution with all fields validated.
|
||||
"""
|
||||
|
||||
class PoemFlow(Flow):
|
||||
@start()
|
||||
def prepare_flower(self):
|
||||
def prepare_flower(self) -> str:
|
||||
self.state["flower"] = "roses"
|
||||
return "foo"
|
||||
|
||||
@start()
|
||||
def prepare_color(self):
|
||||
def prepare_color(self) -> str:
|
||||
self.state["color"] = "red"
|
||||
return "bar"
|
||||
|
||||
@listen(prepare_color)
|
||||
def write_first_sentence(self):
|
||||
def write_first_sentence(self) -> str:
|
||||
return f"{self.state['flower']} are {self.state['color']}"
|
||||
|
||||
@listen(write_first_sentence)
|
||||
@@ -434,7 +436,7 @@ def test_unstructured_flow_event_emission():
|
||||
return separator.join([first_sentence, "violets are blue"])
|
||||
|
||||
@listen(finish_poem)
|
||||
def save_poem_to_database(self):
|
||||
def save_poem_to_database(self) -> str:
|
||||
# A method without args/kwargs to ensure events are sent correctly
|
||||
return "roses are red\nviolets are blue"
|
||||
|
||||
@@ -442,15 +444,15 @@ def test_unstructured_flow_event_emission():
|
||||
received_events = []
|
||||
|
||||
@crewai_event_bus.on(FlowStartedEvent)
|
||||
def handle_flow_start(source, event):
|
||||
def handle_flow_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(MethodExecutionStartedEvent)
|
||||
def handle_method_start(source, event):
|
||||
def handle_method_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(FlowFinishedEvent)
|
||||
def handle_flow_end(source, event):
|
||||
def handle_flow_end(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
flow.kickoff(inputs={"separator": ", "})
|
||||
@@ -473,7 +475,6 @@ def test_unstructured_flow_event_emission():
|
||||
|
||||
assert received_events[2].method_name == "prepare_color"
|
||||
assert received_events[2].params == {}
|
||||
print("received_events[2]", received_events[2])
|
||||
assert "flower" in received_events[2].state
|
||||
|
||||
assert received_events[3].method_name == "write_first_sentence"
|
||||
@@ -497,9 +498,10 @@ def test_unstructured_flow_event_emission():
|
||||
assert isinstance(received_events[6].timestamp, datetime)
|
||||
|
||||
|
||||
def test_structured_flow_event_emission():
|
||||
def test_structured_flow_event_emission() -> None:
|
||||
"""Test that the correct events are emitted during structured flow
|
||||
execution with all fields validated."""
|
||||
execution with all fields validated.
|
||||
"""
|
||||
|
||||
class OnboardingState(BaseModel):
|
||||
name: str = ""
|
||||
@@ -507,11 +509,11 @@ def test_structured_flow_event_emission():
|
||||
|
||||
class OnboardingFlow(Flow[OnboardingState]):
|
||||
@start()
|
||||
def user_signs_up(self):
|
||||
def user_signs_up(self) -> None:
|
||||
self.state.sent = False
|
||||
|
||||
@listen(user_signs_up)
|
||||
def send_welcome_message(self):
|
||||
def send_welcome_message(self) -> str:
|
||||
self.state.sent = True
|
||||
return f"Welcome, {self.state.name}!"
|
||||
|
||||
@@ -521,19 +523,19 @@ def test_structured_flow_event_emission():
|
||||
received_events = []
|
||||
|
||||
@crewai_event_bus.on(FlowStartedEvent)
|
||||
def handle_flow_start(source, event):
|
||||
def handle_flow_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(MethodExecutionStartedEvent)
|
||||
def handle_method_start(source, event):
|
||||
def handle_method_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(MethodExecutionFinishedEvent)
|
||||
def handle_method_end(source, event):
|
||||
def handle_method_end(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(FlowFinishedEvent)
|
||||
def handle_flow_end(source, event):
|
||||
def handle_flow_end(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
flow.kickoff(inputs={"name": "Anakin"})
|
||||
@@ -552,11 +554,11 @@ def test_structured_flow_event_emission():
|
||||
assert isinstance(received_events[3], MethodExecutionStartedEvent)
|
||||
assert received_events[3].method_name == "send_welcome_message"
|
||||
assert received_events[3].params == {}
|
||||
assert getattr(received_events[3].state, "sent") is False
|
||||
assert received_events[3].state.sent is False
|
||||
|
||||
assert isinstance(received_events[4], MethodExecutionFinishedEvent)
|
||||
assert received_events[4].method_name == "send_welcome_message"
|
||||
assert getattr(received_events[4].state, "sent") is True
|
||||
assert received_events[4].state.sent is True
|
||||
assert received_events[4].result == "Welcome, Anakin!"
|
||||
|
||||
assert isinstance(received_events[5], FlowFinishedEvent)
|
||||
@@ -565,41 +567,42 @@ def test_structured_flow_event_emission():
|
||||
assert isinstance(received_events[5].timestamp, datetime)
|
||||
|
||||
|
||||
def test_stateless_flow_event_emission():
|
||||
def test_stateless_flow_event_emission() -> None:
|
||||
"""Test that the correct events are emitted stateless during flow execution
|
||||
with all fields validated."""
|
||||
with all fields validated.
|
||||
"""
|
||||
|
||||
class StatelessFlow(Flow):
|
||||
@start()
|
||||
def init(self):
|
||||
def init(self) -> None:
|
||||
pass
|
||||
|
||||
@listen(init)
|
||||
def process(self):
|
||||
def process(self) -> str:
|
||||
return "Deeds will not be less valiant because they are unpraised."
|
||||
|
||||
event_log = []
|
||||
|
||||
def handle_event(_, event):
|
||||
def handle_event(_, event) -> None:
|
||||
event_log.append(event)
|
||||
|
||||
flow = StatelessFlow()
|
||||
received_events = []
|
||||
|
||||
@crewai_event_bus.on(FlowStartedEvent)
|
||||
def handle_flow_start(source, event):
|
||||
def handle_flow_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(MethodExecutionStartedEvent)
|
||||
def handle_method_start(source, event):
|
||||
def handle_method_start(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(MethodExecutionFinishedEvent)
|
||||
def handle_method_end(source, event):
|
||||
def handle_method_end(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
@crewai_event_bus.on(FlowFinishedEvent)
|
||||
def handle_flow_end(source, event):
|
||||
def handle_flow_end(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
flow.kickoff()
|
||||
@@ -630,14 +633,14 @@ def test_stateless_flow_event_emission():
|
||||
assert isinstance(received_events[5].timestamp, datetime)
|
||||
|
||||
|
||||
def test_flow_plotting():
|
||||
def test_flow_plotting() -> None:
|
||||
class StatelessFlow(Flow):
|
||||
@start()
|
||||
def init(self):
|
||||
def init(self) -> str:
|
||||
return "Initializing flow..."
|
||||
|
||||
@listen(init)
|
||||
def process(self):
|
||||
def process(self) -> str:
|
||||
return "Deeds will not be less valiant because they are unpraised."
|
||||
|
||||
flow = StatelessFlow()
|
||||
@@ -645,7 +648,7 @@ def test_flow_plotting():
|
||||
received_events = []
|
||||
|
||||
@crewai_event_bus.on(FlowPlotEvent)
|
||||
def handle_flow_plot(source, event):
|
||||
def handle_flow_plot(source, event) -> None:
|
||||
received_events.append(event)
|
||||
|
||||
flow.plot("test_flow")
|
||||
@@ -656,59 +659,59 @@ def test_flow_plotting():
|
||||
assert isinstance(received_events[0].timestamp, datetime)
|
||||
|
||||
|
||||
def test_multiple_routers_from_same_trigger():
|
||||
def test_multiple_routers_from_same_trigger() -> None:
|
||||
"""Test that multiple routers triggered by the same method all activate their listeners."""
|
||||
execution_order = []
|
||||
|
||||
class MultiRouterFlow(Flow):
|
||||
def __init__(self):
|
||||
def __init__(self) -> None:
|
||||
super().__init__()
|
||||
# Set diagnosed conditions to trigger all routers
|
||||
self.state["diagnosed_conditions"] = "DHA" # Contains D, H, and A
|
||||
|
||||
@start()
|
||||
def scan_medical(self):
|
||||
def scan_medical(self) -> str:
|
||||
execution_order.append("scan_medical")
|
||||
return "scan_complete"
|
||||
|
||||
@router(scan_medical)
|
||||
def diagnose_conditions(self):
|
||||
def diagnose_conditions(self) -> str:
|
||||
execution_order.append("diagnose_conditions")
|
||||
return "diagnosis_complete"
|
||||
|
||||
@router(diagnose_conditions)
|
||||
def diabetes_router(self):
|
||||
def diabetes_router(self) -> str | None:
|
||||
execution_order.append("diabetes_router")
|
||||
if "D" in self.state["diagnosed_conditions"]:
|
||||
return "diabetes"
|
||||
return None
|
||||
|
||||
@listen("diabetes")
|
||||
def diabetes_analysis(self):
|
||||
def diabetes_analysis(self) -> str:
|
||||
execution_order.append("diabetes_analysis")
|
||||
return "diabetes_analysis_complete"
|
||||
|
||||
@router(diagnose_conditions)
|
||||
def hypertension_router(self):
|
||||
def hypertension_router(self) -> str | None:
|
||||
execution_order.append("hypertension_router")
|
||||
if "H" in self.state["diagnosed_conditions"]:
|
||||
return "hypertension"
|
||||
return None
|
||||
|
||||
@listen("hypertension")
|
||||
def hypertension_analysis(self):
|
||||
def hypertension_analysis(self) -> str:
|
||||
execution_order.append("hypertension_analysis")
|
||||
return "hypertension_analysis_complete"
|
||||
|
||||
@router(diagnose_conditions)
|
||||
def anemia_router(self):
|
||||
def anemia_router(self) -> str | None:
|
||||
execution_order.append("anemia_router")
|
||||
if "A" in self.state["diagnosed_conditions"]:
|
||||
return "anemia"
|
||||
return None
|
||||
|
||||
@listen("anemia")
|
||||
def anemia_analysis(self):
|
||||
def anemia_analysis(self) -> str:
|
||||
execution_order.append("anemia_analysis")
|
||||
return "anemia_analysis_complete"
|
||||
|
||||
@@ -731,27 +734,27 @@ def test_multiple_routers_from_same_trigger():
|
||||
|
||||
# Verify execution order constraints
|
||||
assert execution_order.index("diagnose_conditions") > execution_order.index(
|
||||
"scan_medical"
|
||||
"scan_medical",
|
||||
)
|
||||
|
||||
# All routers should execute after diagnose_conditions
|
||||
assert execution_order.index("diabetes_router") > execution_order.index(
|
||||
"diagnose_conditions"
|
||||
"diagnose_conditions",
|
||||
)
|
||||
assert execution_order.index("hypertension_router") > execution_order.index(
|
||||
"diagnose_conditions"
|
||||
"diagnose_conditions",
|
||||
)
|
||||
assert execution_order.index("anemia_router") > execution_order.index(
|
||||
"diagnose_conditions"
|
||||
"diagnose_conditions",
|
||||
)
|
||||
|
||||
# All analyses should execute after their respective routers
|
||||
assert execution_order.index("diabetes_analysis") > execution_order.index(
|
||||
"diabetes_router"
|
||||
"diabetes_router",
|
||||
)
|
||||
assert execution_order.index("hypertension_analysis") > execution_order.index(
|
||||
"hypertension_router"
|
||||
"hypertension_router",
|
||||
)
|
||||
assert execution_order.index("anemia_analysis") > execution_order.index(
|
||||
"anemia_router"
|
||||
"anemia_router",
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user