"""ASV benchmarks for Config Service resolution chain performance. Measures the performance of: - Single key resolution (default, env var, verbose chain) - Full registry resolution (resolve_all) - Key validation and type coercion - Registry lookup and enumeration - Memory consumption for bulk operations """ from __future__ import annotations import importlib import os import shutil import sys import tempfile from pathlib import Path # Ensure the local *source* tree is importable even when ASV has an # older build of the package installed. _SRC = str(Path(__file__).resolve().parents[1] / "src") if _SRC not in sys.path: sys.path.insert(0, _SRC) import cleveragents # noqa: E402 importlib.reload(cleveragents) from cleveragents.application.services.config_service import ( # noqa: E402 ConfigService, ) class ConfigResolutionTimeSuite: """Benchmark timing for config resolution, validation, and registry ops.""" def setup(self) -> None: self._tmpdir = Path(tempfile.mkdtemp()) self._service = ConfigService( config_dir=self._tmpdir, config_path=self._tmpdir / "config.toml", ) def teardown(self) -> None: os.environ.pop("CLEVERAGENTS_LOG_LEVEL", None) shutil.rmtree(str(self._tmpdir), ignore_errors=True) def time_resolve_single_key(self) -> None: """Resolve a single key (core.log.level) with no overrides.""" self._service.resolve("core.log.level") def time_resolve_all_keys(self) -> None: """Resolve all 103 registered keys via resolve_all().""" self._service.resolve_all() def time_resolve_with_env_var(self) -> None: """Resolve with an env var set.""" os.environ["CLEVERAGENTS_LOG_LEVEL"] = "DEBUG" self._service.resolve("core.log.level") def time_resolve_verbose(self) -> None: """Resolve with verbose=True (builds resolution chain).""" self._service.resolve("core.log.level", verbose=True) def time_validate_key(self) -> None: """Call validate_key() for a known key.""" ConfigService.validate_key("core.log.level") def time_validate_type_coercion(self) -> None: """Call validate_type() for str->int coercion.""" ConfigService.validate_type("core.log.retention-days", "90") def time_registry_lookup(self) -> None: """Look up an entry via get_entry().""" ConfigService.get_entry("core.log.level") def time_registered_keys_sorted(self) -> None: """Get sorted list of all registered keys.""" ConfigService.registered_keys() class ConfigResolutionMemSuite: """Benchmark memory consumption for bulk config operations.""" def setup(self) -> None: self._tmpdir = Path(tempfile.mkdtemp()) self._service = ConfigService( config_dir=self._tmpdir, config_path=self._tmpdir / "config.toml", ) def teardown(self) -> None: shutil.rmtree(str(self._tmpdir), ignore_errors=True) def mem_resolve_all(self) -> dict: """Memory for resolving all keys.""" return self._service.resolve_all() def mem_registry_copy(self) -> dict: """Memory for .registry() (dict copy).""" return ConfigService.registry()