From 9aa966cdaac443357600ef9b473c58242a8de5b2 Mon Sep 17 00:00:00 2001 From: CleverThis Date: Mon, 4 May 2026 20:42:05 +0000 Subject: [PATCH] fix(bench): correct API usage and formatting in core ASV benchmark files - Fix get_retry_decorator() calls to use category string instead of keyword arguments (max_attempts, base_delay, etc.) - Fix retry_on_result() calls to pass required predicate argument - Fix retry_service_operation() to use circuit_breaker= (CircuitBreaker instance) instead of use_circuit_breaker= (bool), and backoff_strategy= instead of wait_strategy= - Fix is_read_only_plan_operation() calls to pass dict instead of string - Fix RetryContext() to use operation_name= instead of service_name=, remove non-existent use_circuit_breaker and attempt_count constructor params - Fix retry_auto_debug() to use max_debug_attempts= instead of service_name=/operation_name= (which are not valid parameters) - Remove unused Any import from core_circuit_breaker_bench.py - Apply ruff format to all three benchmark files to fix CI format check --- benchmarks/core_circuit_breaker_bench.py | 5 +- benchmarks/core_retry_patterns_bench.py | 84 +++++------ .../core_retry_service_patterns_bench.py | 140 +++++++++++------- 3 files changed, 132 insertions(+), 97 deletions(-) diff --git a/benchmarks/core_circuit_breaker_bench.py b/benchmarks/core_circuit_breaker_bench.py index a02ed06eb..060082c58 100644 --- a/benchmarks/core_circuit_breaker_bench.py +++ b/benchmarks/core_circuit_breaker_bench.py @@ -8,7 +8,6 @@ from __future__ import annotations import asyncio import time -from typing import Any from cleveragents.core.circuit_breaker import ( CircuitBreaker, @@ -35,6 +34,7 @@ class CircuitBreakerClosedStateBench: def time_call_success(self) -> None: """Benchmark successful call overhead in closed state.""" + def dummy_func() -> str: return "success" @@ -42,6 +42,7 @@ class CircuitBreakerClosedStateBench: def time_call_with_args(self) -> None: """Benchmark call with arguments in closed state.""" + def dummy_func(x: int, y: str) -> str: return f"{x}:{y}" @@ -187,6 +188,7 @@ class CircuitBreakerAsyncBench: def time_async_call_success(self) -> None: """Benchmark successful async call overhead.""" + async def dummy_async() -> str: return "success" @@ -194,6 +196,7 @@ class CircuitBreakerAsyncBench: def time_async_call_with_args(self) -> None: """Benchmark async call with arguments.""" + async def dummy_async(x: int, y: str) -> str: return f"{x}:{y}" diff --git a/benchmarks/core_retry_patterns_bench.py b/benchmarks/core_retry_patterns_bench.py index f2130e7e5..172947819 100644 --- a/benchmarks/core_retry_patterns_bench.py +++ b/benchmarks/core_retry_patterns_bench.py @@ -15,6 +15,7 @@ from cleveragents.core.retry_patterns import ( retry_with_exponential_backoff, retry_with_jitter, retry_with_timeout, + should_retry_result, ) @@ -25,36 +26,47 @@ class RetryDecoratorConstructionBench: def time_retry_with_exponential_backoff_construction(self) -> None: """Benchmark constructing exponential backoff decorator.""" + @retry_with_exponential_backoff(max_attempts=3) def dummy_func() -> str: return "success" def time_retry_with_jitter_construction(self) -> None: """Benchmark constructing jitter decorator.""" + @retry_with_jitter(max_attempts=3) def dummy_func() -> str: return "success" def time_retry_with_timeout_construction(self) -> None: """Benchmark constructing timeout decorator.""" + @retry_with_timeout(timeout_seconds=5.0) def dummy_func() -> str: return "success" def time_retry_on_result_construction(self) -> None: """Benchmark constructing result-based retry decorator.""" - @retry_on_result(max_attempts=3) + + @retry_on_result(should_retry_result, max_attempts=3) def dummy_func() -> str: return "success" - def time_get_retry_decorator_construction(self) -> None: - """Benchmark constructing decorator via factory.""" - get_retry_decorator( - max_attempts=3, - base_delay=1.0, - max_delay=60.0, - strategy="exponential", - ) + def time_get_retry_decorator_network(self) -> None: + """Benchmark constructing decorator via factory for network category.""" + get_retry_decorator("network") + + def time_get_retry_decorator_provider(self) -> None: + """Benchmark constructing decorator via factory for provider category.""" + get_retry_decorator("provider") + + def time_get_retry_decorator_database(self) -> None: + """Benchmark constructing decorator via factory for database category.""" + get_retry_decorator("database") + + def time_get_retry_decorator_unknown(self) -> None: + """Benchmark constructing decorator via factory for unknown category.""" + get_retry_decorator("unknown_category") class RetryDecoratorInvocationBench: @@ -64,6 +76,7 @@ class RetryDecoratorInvocationBench: def setup(self) -> None: """Set up decorated functions.""" + @retry_with_exponential_backoff(max_attempts=3) def exponential_func() -> str: return "success" @@ -76,7 +89,7 @@ class RetryDecoratorInvocationBench: def timeout_func() -> str: return "success" - @retry_on_result(max_attempts=3) + @retry_on_result(should_retry_result, max_attempts=3) def result_func() -> str: return "success" @@ -109,6 +122,7 @@ class RetryDecoratorAsyncBench: def setup(self) -> None: """Set up async decorated functions.""" + @retry_with_exponential_backoff(max_attempts=3) async def async_exponential() -> str: return "success" @@ -145,6 +159,7 @@ class RetryDecoratorWithArgumentsBench: def setup(self) -> None: """Set up decorated functions with arguments.""" + @retry_with_exponential_backoff(max_attempts=3) def func_with_args(x: int, y: str, z: float = 1.0) -> str: return f"{x}:{y}:{z}" @@ -174,14 +189,9 @@ class RetryDecoratorFactoryBench: timeout = 60 - def time_factory_exponential_strategy(self) -> None: - """Benchmark factory with exponential strategy.""" - decorator = get_retry_decorator( - max_attempts=3, - base_delay=1.0, - max_delay=60.0, - strategy="exponential", - ) + def time_factory_network_category(self) -> None: + """Benchmark factory with network category.""" + decorator = get_retry_decorator("network") @decorator def dummy() -> str: @@ -189,14 +199,9 @@ class RetryDecoratorFactoryBench: dummy() - def time_factory_linear_strategy(self) -> None: - """Benchmark factory with linear strategy.""" - decorator = get_retry_decorator( - max_attempts=3, - base_delay=2.0, - max_delay=60.0, - strategy="linear", - ) + def time_factory_provider_category(self) -> None: + """Benchmark factory with provider category.""" + decorator = get_retry_decorator("provider") @decorator def dummy() -> str: @@ -204,14 +209,9 @@ class RetryDecoratorFactoryBench: dummy() - def time_factory_fixed_strategy(self) -> None: - """Benchmark factory with fixed strategy.""" - decorator = get_retry_decorator( - max_attempts=3, - base_delay=0.5, - max_delay=60.0, - strategy="fixed", - ) + def time_factory_database_category(self) -> None: + """Benchmark factory with database category.""" + decorator = get_retry_decorator("database") @decorator def dummy() -> str: @@ -219,14 +219,9 @@ class RetryDecoratorFactoryBench: dummy() - def time_factory_jitter_strategy(self) -> None: - """Benchmark factory with jitter strategy.""" - decorator = get_retry_decorator( - max_attempts=3, - base_delay=1.0, - max_delay=60.0, - strategy="jitter", - ) + def time_factory_file_operation_category(self) -> None: + """Benchmark factory with file_operation category.""" + decorator = get_retry_decorator("file_operation") @decorator def dummy() -> str: @@ -242,6 +237,7 @@ class RetryDecoratorConfigurationBench: def time_minimal_config(self) -> None: """Benchmark decorator with minimal configuration.""" + @retry_with_exponential_backoff() def dummy() -> str: return "success" @@ -250,6 +246,7 @@ class RetryDecoratorConfigurationBench: def time_aggressive_config(self) -> None: """Benchmark decorator with aggressive retry settings.""" + @retry_with_exponential_backoff(max_attempts=10) def dummy() -> str: return "success" @@ -258,6 +255,7 @@ class RetryDecoratorConfigurationBench: def time_conservative_config(self) -> None: """Benchmark decorator with conservative retry settings.""" + @retry_with_exponential_backoff(max_attempts=1) def dummy() -> str: return "success" @@ -266,6 +264,7 @@ class RetryDecoratorConfigurationBench: def time_long_timeout_config(self) -> None: """Benchmark decorator with long timeout.""" + @retry_with_timeout(timeout_seconds=300.0) def dummy() -> str: return "success" @@ -274,6 +273,7 @@ class RetryDecoratorConfigurationBench: def time_short_timeout_config(self) -> None: """Benchmark decorator with short timeout.""" + @retry_with_timeout(timeout_seconds=0.1) def dummy() -> str: return "success" diff --git a/benchmarks/core_retry_service_patterns_bench.py b/benchmarks/core_retry_service_patterns_bench.py index cfd0b2ae7..afbdbea98 100644 --- a/benchmarks/core_retry_service_patterns_bench.py +++ b/benchmarks/core_retry_service_patterns_bench.py @@ -9,6 +9,7 @@ from __future__ import annotations import asyncio from typing import Any +from cleveragents.core.circuit_breaker import CircuitBreaker from cleveragents.core.retry_service_patterns import ( RetryContext, is_read_only_plan_operation, @@ -24,6 +25,7 @@ class RetryServiceOperationDecoratorBench: def time_decorator_construction_sync(self) -> None: """Benchmark constructing sync service retry decorator.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", @@ -34,6 +36,7 @@ class RetryServiceOperationDecoratorBench: def time_decorator_construction_async(self) -> None: """Benchmark constructing async service retry decorator.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", @@ -43,23 +46,30 @@ class RetryServiceOperationDecoratorBench: return "success" def time_decorator_with_circuit_breaker(self) -> None: - """Benchmark decorator with circuit breaker enabled.""" + """Benchmark decorator with circuit breaker instance.""" + cb = CircuitBreaker( + failure_threshold=5, + recovery_timeout=60.0, + name="test_service", + ) + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - use_circuit_breaker=True, + circuit_breaker=cb, ) def dummy_func() -> str: return "success" - def time_decorator_with_custom_strategy(self) -> None: - """Benchmark decorator with custom wait strategy.""" + def time_decorator_with_exponential_strategy(self) -> None: + """Benchmark decorator with exponential backoff strategy.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - wait_strategy="exponential", + backoff_strategy="exponential", base_delay=1.0, max_delay=60.0, ) @@ -74,6 +84,7 @@ class RetryServiceOperationInvocationBench: def setup(self) -> None: """Set up decorated service operations.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", @@ -90,11 +101,17 @@ class RetryServiceOperationInvocationBench: async def async_op() -> str: return "success" + cb = CircuitBreaker( + failure_threshold=5, + recovery_timeout=60.0, + name="test_service", + ) + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - use_circuit_breaker=True, + circuit_breaker=cb, ) def breaker_op() -> str: return "success" @@ -123,12 +140,15 @@ class RetryServiceOperationWithArgumentsBench: def setup(self) -> None: """Set up decorated operations with arguments.""" + @retry_service_operation( service_name="test_service", operation_name="fetch_data", max_attempts=3, ) - def fetch_data(resource_id: int, include_metadata: bool = False) -> dict[str, Any]: + def fetch_data( + resource_id: int, include_metadata: bool = False + ) -> dict[str, Any]: return {"id": resource_id, "data": "test"} @retry_service_operation( @@ -136,7 +156,9 @@ class RetryServiceOperationWithArgumentsBench: operation_name="update_data", max_attempts=3, ) - async def update_data(resource_id: int, payload: dict[str, Any]) -> dict[str, Any]: + async def update_data( + resource_id: int, payload: dict[str, Any] + ) -> dict[str, Any]: return {"id": resource_id, "updated": True} self.fetch_data = fetch_data @@ -163,45 +185,37 @@ class RetryAutoDebugBench: def time_auto_debug_construction(self) -> None: """Benchmark constructing auto-debug decorator.""" - @retry_auto_debug( - service_name="test_service", - operation_name="test_op", - ) - def dummy_func() -> str: + + @retry_auto_debug(max_debug_attempts=3) + async def dummy_func() -> str: return "success" def time_auto_debug_invocation(self) -> None: """Benchmark auto-debug invocation (happy path).""" - @retry_auto_debug( - service_name="test_service", - operation_name="test_op", - ) - def dummy_func() -> str: - return "success" - dummy_func() - - def time_auto_debug_async_invocation(self) -> None: - """Benchmark async auto-debug invocation (happy path).""" - @retry_auto_debug( - service_name="test_service", - operation_name="test_op", - ) + @retry_auto_debug(max_debug_attempts=3) async def dummy_func() -> str: return "success" asyncio.run(dummy_func()) - def time_auto_debug_with_context(self) -> None: - """Benchmark auto-debug with retry context.""" - @retry_auto_debug( - service_name="test_service", - operation_name="test_op", - ) - def dummy_func(ctx: RetryContext | None = None) -> str: + def time_auto_debug_single_attempt(self) -> None: + """Benchmark auto-debug with single attempt.""" + + @retry_auto_debug(max_debug_attempts=1) + async def dummy_func() -> str: return "success" - dummy_func() + asyncio.run(dummy_func()) + + def time_auto_debug_multiple_attempts(self) -> None: + """Benchmark auto-debug with multiple attempts configured.""" + + @retry_auto_debug(max_debug_attempts=5) + async def dummy_func() -> str: + return "success" + + asyncio.run(dummy_func()) class RetryContextBench: @@ -212,32 +226,38 @@ class RetryContextBench: def time_context_creation(self) -> None: """Benchmark creating a retry context.""" RetryContext( - service_name="test_service", operation_name="test_op", max_attempts=3, ) - def time_context_with_circuit_breaker(self) -> None: - """Benchmark context with circuit breaker.""" + def time_context_with_custom_wait(self) -> None: + """Benchmark context with custom wait strategy.""" + from tenacity import wait_exponential + RetryContext( - service_name="test_service", operation_name="test_op", max_attempts=3, - use_circuit_breaker=True, + wait_strategy=wait_exponential(multiplier=1, min=1, max=30), ) def time_context_property_access(self) -> None: """Benchmark accessing context properties.""" ctx = RetryContext( - service_name="test_service", operation_name="test_op", max_attempts=3, ) - _ = ctx.service_name _ = ctx.operation_name _ = ctx.max_attempts _ = ctx.attempt_count + def time_context_execute(self) -> None: + """Benchmark executing a function via RetryContext.""" + ctx = RetryContext( + operation_name="test_op", + max_attempts=3, + ) + ctx.execute(lambda: "success") + class IsReadOnlyPlanOperationBench: """Benchmark is_read_only_plan_operation utility.""" @@ -246,35 +266,43 @@ class IsReadOnlyPlanOperationBench: def time_check_strategize(self) -> None: """Benchmark checking strategize operation.""" - is_read_only_plan_operation("strategize") + is_read_only_plan_operation({"plan_phase": "strategize"}) def time_check_plan(self) -> None: """Benchmark checking plan operation.""" - is_read_only_plan_operation("plan") + is_read_only_plan_operation({"plan_phase": "plan"}) def time_check_validate(self) -> None: """Benchmark checking validate operation.""" - is_read_only_plan_operation("validate") + is_read_only_plan_operation({"plan_phase": "validate"}) def time_check_review(self) -> None: """Benchmark checking review operation.""" - is_read_only_plan_operation("review") + is_read_only_plan_operation({"plan_phase": "review"}) def time_check_preview(self) -> None: """Benchmark checking preview operation.""" - is_read_only_plan_operation("preview") + is_read_only_plan_operation({"plan_phase": "preview"}) def time_check_check(self) -> None: """Benchmark checking check operation.""" - is_read_only_plan_operation("check") + is_read_only_plan_operation({"plan_phase": "check"}) def time_check_execute(self) -> None: """Benchmark checking execute operation (not read-only).""" - is_read_only_plan_operation("execute") + is_read_only_plan_operation({"plan_phase": "execute"}) + + def time_check_read_only_flag(self) -> None: + """Benchmark checking read_only flag.""" + is_read_only_plan_operation({"read_only": True}) def time_check_unknown_operation(self) -> None: """Benchmark checking unknown operation.""" - is_read_only_plan_operation("unknown_op") + is_read_only_plan_operation({"plan_phase": "unknown_op"}) + + def time_check_empty_kwargs(self) -> None: + """Benchmark checking empty kwargs.""" + is_read_only_plan_operation({}) class RetryServiceOperationStrategyBench: @@ -284,11 +312,12 @@ class RetryServiceOperationStrategyBench: def time_exponential_strategy(self) -> None: """Benchmark exponential strategy.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - wait_strategy="exponential", + backoff_strategy="exponential", ) def dummy() -> str: return "success" @@ -297,11 +326,12 @@ class RetryServiceOperationStrategyBench: def time_linear_strategy(self) -> None: """Benchmark linear strategy.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - wait_strategy="linear", + backoff_strategy="linear", ) def dummy() -> str: return "success" @@ -310,11 +340,12 @@ class RetryServiceOperationStrategyBench: def time_fixed_strategy(self) -> None: """Benchmark fixed strategy.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - wait_strategy="fixed", + backoff_strategy="fixed", ) def dummy() -> str: return "success" @@ -323,11 +354,12 @@ class RetryServiceOperationStrategyBench: def time_jitter_strategy(self) -> None: """Benchmark jitter strategy.""" + @retry_service_operation( service_name="test_service", operation_name="test_op", max_attempts=3, - wait_strategy="jitter", + backoff_strategy="jitter", ) def dummy() -> str: return "success"