Release Notes - v1.17.0¶
Major Changes¶
Capability-Based Agent Architecture¶
Overhaul of the Agent system with a modular, capability-based design:
use Cognesy\Addons\AgentBuilder\AgentBuilder;
use Cognesy\Addons\AgentBuilder\Capabilities\Bash\UseBash;
use Cognesy\Addons\AgentBuilder\Capabilities\File\UseFileTools;
use Cognesy\Addons\AgentBuilder\Capabilities\Tasks\UseTaskPlanning;
$agent = AgentBuilder::base()
->withCapability(new UseBash())
->withCapability(new UseFileTools())
->withCapability(new UseTaskPlanning())
->build();
New Agent Capabilities:
- UseBash - Execute shell commands with configurable policies
- UseFileTools - Read, write, edit, search, and list files
- UseSkills - Manage reusable skill libraries
- UseTaskPlanning - Multi-step task management with TodoWriteTool
- UseMetadataTools - Agent scratchpad for inter-tool data sharing
- UseStructuredOutputs - LLM-powered structured data extraction
- UseSubagents - Recursive agent spawning with AgentRegistry
- UseSelfCritique - Self-evaluation of agent work
HTTP Client Resilience Framework¶
New middleware for robust HTTP communication:
use Cognesy\HttpClient\HttpClientBuilder;
use Cognesy\HttpClient\Middleware\Policies\RetryPolicy;
use Cognesy\HttpClient\Middleware\Policies\CircuitBreakerPolicy;
$client = HttpClientBuilder::make()
->withRetryPolicy(new RetryPolicy(
maxAttempts: 3,
baseDelayMs: 250,
maxDelayMs: 8000,
jitter: 'full',
))
->withCircuitBreakerPolicy(new CircuitBreakerPolicy(
failureThreshold: 5,
openWindowSeconds: 30,
))
->withIdempotencyMiddleware()
->build();
Features:
- Exponential backoff with configurable jitter strategies
- Respects Retry-After headers
- Circuit breaker pattern (closed → open → half-open → closed)
- Per-host circuit tracking
- Idempotency keys for safe retries
Inference Retry¶
Smart retry logic for LLM inference requests:
use Cognesy\Polyglot\Inference\Inference;
$response = Inference::with($messages)
->withRetryPolicy([
'maxAttempts' => 3,
'baseDelayMs' => 500,
'lengthRecovery' => 'continue', // or 'increase_max_tokens'
])
->get();
Features: - Automatic retry on rate limits and transient errors - Length limit recovery (retry with "Continue." prompt or increased max_tokens) - Provider-specific error classification with typed exceptions
Driver Capabilities System¶
Explicit capability declarations for all LLM providers:
$driver = $inference->getDriver();
$capabilities = $driver->capabilities('gpt-4');
if ($capabilities->supportsJsonSchema) {
// Use native JSON schema mode
}
if ($capabilities->supportsToolCalling) {
// Use function calling
}
All 14+ drivers now declare support for: - Output modes (JSON Schema, Tools, MdJson, Text) - Streaming - Tool/function calling - Native JSON schema mode
New Features¶
Agent Registry & Specifications¶
Declarative agent definitions with registry-based discovery:
use Cognesy\Addons\AgentTemplate\Registry\AgentRegistry;use Cognesy\Addons\AgentTemplate\Spec\AgentSpec;
$registry = new AgentRegistry();
$registry->register('researcher', AgentSpec::from([
'name' => 'researcher',
'description' => 'Research agent',
'capabilities' => [UseFileTools::class, UseSkills::class],
]));
$agent = $registry->make('researcher');
Agent State Serialization¶
Efficient state persistence for distributed/resumable agents:
use Cognesy\Addons\Agent\Serialization\SlimAgentStateSerializer;
$serializer = new SlimAgentStateSerializer();
$serialized = $serializer->serialize($agent->state());
// Later...
$state = $serializer->deserialize($serialized);
Deterministic Agent Testing¶
Test agents without LLM calls:
use Cognesy\Addons\Agent\Drivers\Testing\DeterministicAgentDriver;
use Cognesy\Addons\Agent\Drivers\Testing\ScenarioStep;
$driver = new DeterministicAgentDriver([
ScenarioStep::toolCall('search', ['query' => 'test']),
ScenarioStep::response('Search completed'),
]);
$agent = AgentBuilder::base()
->withDriver($driver)
->build();
Real-time Agent Event Broadcasting¶
Broadcast agent events via Laravel Reverb/Pusher:
use Cognesy\Addons\Agent\Broadcasting\AgentEventEnvelopeAdapter;
$adapter = new AgentEventEnvelopeAdapter($events);
$adapter->broadcast($agentId);
Message Collection Classes¶
New collection abstractions for messages:
use Cognesy\Messages\ContentParts;
use Cognesy\Messages\MessageList;
// ContentParts collection
$parts = new ContentParts([$textPart, $imagePart]);
$filtered = $parts->filter(fn($p) => $p->isText());
// MessageList collection
$messages = new MessageList([$msg1, $msg2]);
$reversed = $messages->reversed();
Centralized Input Handling¶
Unified factories for content and message creation:
use Cognesy\Messages\Support\ContentInput;
use Cognesy\Messages\Support\MessageInput;
// Normalize any input to Content
$content = ContentInput::fromAny($stringOrArrayOrContent);
// Create Message from various inputs
$message = MessageInput::fromAny($input, MessageRole::User);
Provider Error Classification¶
Typed exceptions for better error handling:
use Cognesy\Polyglot\Inference\Exceptions\ProviderRateLimitException;
use Cognesy\Polyglot\Inference\Exceptions\ProviderQuotaExceededException;
try {
$response = $inference->get();
} catch (ProviderRateLimitException $e) {
// Retriable - wait and retry
} catch (ProviderQuotaExceededException $e) {
// Non-retriable - notify user
}
MockSandbox for Testing¶
Mock command execution in tests:
use Cognesy\Utils\Sandbox\MockSandbox;
$sandbox = new MockSandbox();
$sandbox->queueResponse('ls', ['stdout' => 'file1.txt\nfile2.txt']);
$result = $sandbox->execute('ls');
Improvements¶
Agent System¶
- Sophisticated continuation logic with priority-based resolution
- Enhanced error handling with granular
ErrorPolicyconfiguration - State processors integrated into capability installation
- Tools can access agent state via
CanAccessAgentStatecontract - Improved
ToolCallingDriverwith better parallelization
Messages Package¶
Content,Messages,Sections,Sectionnow implementCountableandIteratorAggregateMessageStoreuses standardMetadataclass instead of custom parameters- Cleaner API with
partsList()andmessageList()methods
Polyglot Package¶
- Response adapters simplified (tool calls handled separately from content)
- Better handling of empty content parts
AnthropicBodyFormatupdated for new message structure
Evals Package¶
- Driver capability filtering for test cases
- Dependency injection support for test mocking
Instructor Package¶
- Simplified
MessageStoreoperations using new merge/cleanup methods - Enhanced array return handling respects
defaultToStdClass()config
Breaking Changes¶
Agent Namespace Reorganization¶
Core classes moved from Agent/ to Agent/Core/:
- Agent/Data/AgentState → Agent/Core/Data/AgentState
- Agent/Collections/ → Agent/Core/Collections/
- Agent/Contracts/ → Agent/Core/Contracts/
Agent Construction¶
Old AgentFactory removed. Use AgentBuilder:
// Before
$agent = AgentFactory::create($config);
// After
$agent = AgentBuilder::base()
->withCapability(...)
->build();
Messages API Deprecations¶
Content::parts()→ useContent::partsList()Messages::head()→ useMessages::headList()Messages::tail()→ useMessages::tailList()Messages::all()→ useMessages::messageList()
MessageStore Parameters¶
MessageStoreParameters class removed. Use Metadata instead:
// Before
$store = new MessageStore($sections, new MessageStoreParameters($data));
// After
$store = new MessageStore($sections, new Metadata($data));
Driver Capabilities Interface¶
Drivers must implement new capabilities() method:
Provider Exceptions¶
HTTP errors now throw typed ProviderException subclasses instead of generic exceptions.
Bug Fixes¶
- Fixed variadic parameter type handling in
StructureFactoryfor mixed/null types - Fixed PHP 8.5 compatibility issues with reflection API
- Fixed Gemini response adapter content concatenation
- Fixed contentParts() returning collection instead of array in templates
- Updated Symfony Console API calls (
add()→addCommand())