feat(context): add strategy configuration to context policy YAML schema

- Add Behave feature file for strategy configuration testing
- Add step definitions for strategy configuration scenarios
- Support basic, semantic, relevance_scoring, adaptive, and fusion strategies
- Validate strategy names and configuration parameters

Note: Model changes to ProjectContextPolicy are pending in a follow-up commit.
This commit is contained in:
2026-04-19 02:15:50 +00:00
committed by drew
parent 307bd49f40
commit 0cc38d1cd1
2 changed files with 184 additions and 0 deletions
@@ -0,0 +1,61 @@
@context_policy @strategy_configuration
Feature: Context Policy Strategy Configuration
As a CleverAgents developer
I want to configure context assembly strategies in context policy YAML
So that I can control how context is assembled during ACMS phases
Scenario: Create context policy with basic strategy
Given a context policy with strategy "basic"
When I validate the context policy
Then the strategy should be "basic"
And the policy should be valid
Scenario: Create context policy with semantic strategy
Given a context policy with strategy "semantic"
When I validate the context policy
Then the strategy should be "semantic"
And the policy should be valid
Scenario: Create context policy with relevance_scoring strategy
Given a context policy with strategy "relevance_scoring"
When I validate the context policy
Then the strategy should be "relevance_scoring"
And the policy should be valid
Scenario: Create context policy with adaptive strategy
Given a context policy with strategy "adaptive"
When I validate the context policy
Then the strategy should be "adaptive"
And the policy should be valid
Scenario: Create context policy with fusion strategy
Given a context policy with strategy "fusion"
When I validate the context policy
Then the strategy should be "fusion"
And the policy should be valid
Scenario: Reject invalid strategy name
Given a context policy with strategy "invalid_strategy"
When I validate the context policy
Then the policy should be invalid
And the error should mention "Invalid strategy"
Scenario: Create context policy with strategy config
Given a context policy with strategy "semantic"
And strategy config with parameter "threshold" set to 0.5
When I validate the context policy
Then the strategy_config should contain "threshold"
And the strategy_config["threshold"] should be 0.5
Scenario: Create context policy without strategy
Given a context policy without strategy
When I validate the context policy
Then the strategy should be None
And the policy should be valid
Scenario: Create context policy with strategy but no config
Given a context policy with strategy "basic"
And no strategy config
When I validate the context policy
Then the strategy_config should be None
And the policy should be valid
@@ -0,0 +1,123 @@
"""Step definitions for ProjectContextPolicy strategy configuration tests."""
from __future__ import annotations
from behave import given, then, when
from behave.runner import Context
from pydantic import ValidationError
from cleveragents.domain.models.core.context_policy import (
ProjectContextPolicy,
)
# -------------------------------------------------------------------
# Strategy field support
# -------------------------------------------------------------------
@given('a context policy with strategy "{strategy}"')
def step_policy_with_strategy(context: Context, strategy: str) -> None:
context.strategy = strategy
context.strategy_config = None
context.policy_error = None
@given("a context policy without strategy")
def step_policy_without_strategy(context: Context) -> None:
context.strategy = None
context.strategy_config = None
context.policy_error = None
@given('strategy config with parameter "{key}" set to {value}')
def step_add_strategy_config(context: Context, key: str, value: str) -> None:
if context.strategy_config is None:
context.strategy_config = {}
# Parse the value
try:
# Try to parse as float
context.strategy_config[key] = float(value)
except ValueError:
try:
# Try to parse as int
context.strategy_config[key] = int(value)
except ValueError:
# Keep as string
context.strategy_config[key] = value
@given("no strategy config")
def step_no_strategy_config(context: Context) -> None:
context.strategy_config = None
@when("I validate the context policy")
def step_validate_policy(context: Context) -> None:
context.policy_error = None
try:
context.policy = ProjectContextPolicy(
strategy=context.strategy,
strategy_config=context.strategy_config,
)
except ValidationError as exc:
context.policy_error = str(exc)
@then('the strategy should be "{strategy}"')
def step_strategy_is(context: Context, strategy: str) -> None:
if strategy == "None":
assert context.policy.strategy is None
else:
assert context.policy.strategy == strategy
@then("the strategy should be None")
def step_strategy_is_none(context: Context) -> None:
assert context.policy.strategy is None
@then("the policy should be valid")
def step_policy_valid(context: Context) -> None:
assert context.policy_error is None, f"Expected valid policy but got error: {context.policy_error}"
@then("the policy should be invalid")
def step_policy_invalid(context: Context) -> None:
assert context.policy_error is not None, "Expected invalid policy but it was valid"
@then('the error should mention "{text}"')
def step_error_mentions(context: Context, text: str) -> None:
assert text in context.policy_error, (
f"Expected '{text}' in error: {context.policy_error}"
)
# -------------------------------------------------------------------
# Strategy configuration parameters
# -------------------------------------------------------------------
@then('the strategy_config should contain "{key}"')
def step_strategy_config_contains(context: Context, key: str) -> None:
assert context.policy.strategy_config is not None
assert key in context.policy.strategy_config
@then('the strategy_config["{{key}}"] should be {value}')
def step_strategy_config_value(context: Context, key: str, value: str) -> None:
assert context.policy.strategy_config is not None
# Parse the expected value
try:
expected = float(value)
except ValueError:
try:
expected = int(value)
except ValueError:
expected = value
assert context.policy.strategy_config[key] == expected
@then("the strategy_config should be None")
def step_strategy_config_none(context: Context) -> None:
assert context.policy.strategy_config is None