Files
cleveragents-core/features/provider_registry_coverage_boost.feature
hurui200320 7164b04019
CI / lint (push) Successful in 1m1s
CI / build (push) Successful in 53s
CI / quality (push) Successful in 1m23s
CI / typecheck (push) Successful in 1m24s
CI / benchmark-regression (push) Has been skipped
CI / security (push) Successful in 1m42s
CI / push-validation (push) Successful in 21s
CI / helm (push) Successful in 25s
CI / e2e_tests (push) Successful in 4m6s
CI / integration_tests (push) Successful in 4m12s
CI / unit_tests (push) Successful in 6m39s
CI / docker (push) Successful in 1m44s
CI / coverage (push) Successful in 10m51s
CI / status-check (push) Successful in 2s
CI / benchmark-publish (push) Successful in 1h17m10s
CI / benchmark-publish (pull_request) Has been skipped
CI / helm (pull_request) Successful in 33s
CI / build (pull_request) Successful in 50s
CI / lint (pull_request) Successful in 1m7s
CI / quality (pull_request) Successful in 1m9s
CI / typecheck (pull_request) Successful in 1m20s
CI / security (pull_request) Successful in 1m25s
CI / push-validation (pull_request) Successful in 19s
CI / integration_tests (pull_request) Successful in 3m20s
CI / e2e_tests (pull_request) Failing after 5m3s
CI / unit_tests (pull_request) Successful in 6m40s
CI / docker (pull_request) Successful in 1m30s
CI / coverage (pull_request) Successful in 11m9s
CI / status-check (pull_request) Failing after 3s
CI / benchmark-regression (pull_request) Failing after 1m11s
refactor(providers): unify provider factory behind single source of truth
Extract _get_api_key() and _create_provider_instance() as a single internal
factory that handles all provider types, including MOCK. Both create_llm() and
create_ai_provider() now delegate to _create_provider_instance(), eliminating
the duplicated if/elif provider-switching chains and the divergence between the
two code paths. Adding a new provider now requires touching exactly one place.

Key changes:
- New _get_api_key(provider_type) consolidates API key lookup and validation
  that was previously duplicated across create_llm(), _create_provider_llm(),
  and every branch of create_ai_provider().
- New _create_provider_instance() is the unified raw-LLM factory, replacing
  _create_provider_llm() and the specialised adapter constructors in
  create_ai_provider(). MOCK is now handled here via FakeListLLM.
- create_ai_provider() wraps all providers uniformly in LangChainChatProvider
  instead of using specialised adapters (OpenAIChatProvider, AnthropicChatProvider,
  GoogleChatProvider, OpenRouterChatProvider) for the four primary providers.
- create_llm() drops its own API key validation block; validation now happens
  inside _create_provider_instance() via _get_api_key().
- All BDD scenarios updated: _create_provider_llm references become
  _create_provider_instance, and provider-type assertions on create_ai_provider
  results are updated to LangChainChatProvider.

Review fixes (Cycle 2):
- Add _coerce_env_bool() for consistent boolean env-var coercion in
  CLEVERAGENTS_ALLOW_MOCK_PROVIDER checks.
- Introduce _ApiKeyMissing sentinel to distinguish 'not provided' from None
  in provider configuration.
- Set MOCK supports_streaming=False in DEFAULT_CAPABILITIES to align with
  FakeListLLM semantics.
- Make MOCK is_configured conditional on CLEVERAGENTS_ALLOW_MOCK_PROVIDER.
- Use FakeListLLM(responses=['mock response'] * 10) to prevent IndexError
  in multi-step workflows.
- Strip max_retries from kwargs before passing to LangChain constructors.
- Extract _resolve_provider_type() helper shared by create_llm() and
  create_ai_provider() to reduce duplication and improve readability.
- Ensure __api_key_sentinel flows through factory_kwargs even when api_key
  is None, avoiding double _get_api_key() calls.
- Add CHANGELOG env-var documentation and providers.md env-var table.
- Resolve template DB lock issues by persisting in-memory SQLite via
  VACUUM INTO instead of direct file creation on tmpfs.

ISSUES CLOSED: #10949
2026-05-05 06:16:46 +00:00

74 lines
3.8 KiB
Gherkin

Feature: Provider Registry Coverage Boost
As a developer
I want to cover remaining untested paths in the ProviderRegistry
So that edge cases in provider selection and creation are verified
@unit @providers @registry
Scenario: Settings default provider is valid but not configured falls through to fallback
Given a registry where settings default_provider is "openai" but only anthropic key is set
And CLEVERAGENTS_DEFAULT_PROVIDER env var is cleared
When I request the default provider type from the boost registry
Then the boost result should be ProviderType ANTHROPIC
@unit @providers @registry
Scenario: Azure deployment resolves from settings when model_id is None
Given a registry with azure API key and deployment setting "my-azure-deploy"
And the Azure LangChain client is stubbed for boost
When I call _create_provider_instance for AZURE with model_id None via boost
Then the stubbed Azure client deployment_name should be "my-azure-deploy"
@unit @providers @registry
Scenario: Azure deployment falls back to gpt-4o when settings deployment is also empty
Given a registry with azure API key and no deployment setting
And the Azure LangChain client is stubbed for boost
When I call _create_provider_instance for AZURE with model_id None via boost
Then the stubbed Azure client deployment_name should be "gpt-4o"
@unit @providers @registry
Scenario: Google create_ai_provider uses DEFAULT_MODELS when model_id is empty string
Given a registry with google API key configured for boost
When I create an AI provider for google with empty string model_id via boost
Then the boost AI provider model_id should be "gemini-2.0-flash"
@unit @providers @registry
Scenario: OpenRouter create_ai_provider raises error when API key is missing
Given a registry with no API keys for boost
When I try to create an AI provider for openrouter via boost
Then a boost ValueError should be raised
And the boost error message should contain "openrouter"
And the boost error message should contain "not configured"
@unit @providers @registry
Scenario: OpenRouter create_ai_provider uses DEFAULT_MODELS when model_id is empty string
Given a registry with openrouter API key configured for boost
When I create an AI provider for openrouter with empty string model_id via boost
Then the boost AI provider model_id should be "anthropic/claude-sonnet-4-20250514"
@unit @providers @registry
Scenario: OpenRouter _create_provider_instance with sanitized numeric headers and organization
Given a registry with openrouter API key configured for boost
And the openrouter organization is set to "my-org"
When I call _create_provider_instance for openrouter with model "claude-or" and numeric headers
Then the returned LLM should be recorded with sanitized headers including "X-Debug"
And the openrouter kwargs should include HTTP-Referer "my-org"
@unit @providers @registry
Scenario: _create_provider_instance accepts pre-validated api_key sentinel None
Given CLEVERAGENTS_ALLOW_MOCK_PROVIDER is set
And a registry with no API keys for boost
When I call _create_provider_instance for mock with api_key sentinel None
Then the boost result should be a FakeListLLM instance
And calling it twice yields the same response
@unit @providers @registry
Scenario: Azure endpoint missing raises ValueError
Given a registry with azure API key but no endpoint setting
When I try to call _create_provider_instance for AZURE with model_id None via boost
Then a boost ValueError should be raised
And the boost error message should contain "endpoint"
@unit @providers @registry
Scenario: coerce_optional_str coerces non-string values
When I coerce optional string with integer 42
Then the coerced optional string result should be "42"