Skip to content

Commit 3eeeb4d

Browse files
authored
Merge pull request #3 from llm-agents-php/feature/error-handling
Handle LLM errors
2 parents 3ff8f6d + 1c6f619 commit 3eeeb4d

9 files changed

+82
-2
lines changed

composer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
"require": {
66
"php": "^8.3",
77
"openai-php/client": "^0.10.1",
8-
"llm-agents/agents": "^1.0",
8+
"llm-agents/agents": "^1.4",
99
"guzzlehttp/guzzle": "^7.0"
1010
},
1111
"require-dev": {
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace LLM\Agents\OpenAI\Client\Exception;
6+
7+
final class LimitExceededException extends OpenAiClientException
8+
{
9+
10+
}
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace LLM\Agents\OpenAI\Client\Exception;
6+
7+
class OpenAiClientException extends \Exception
8+
{
9+
10+
}

src/Exception/RateLimitException.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace LLM\Agents\OpenAI\Client\Exception;
6+
7+
final class RateLimitException extends OpenAiClientException
8+
{
9+
10+
}

src/Exception/TimeoutException.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace LLM\Agents\OpenAI\Client\Exception;
6+
7+
final class TimeoutException extends OpenAiClientException
8+
{
9+
10+
}

src/LLM.php

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,9 @@
1212
use LLM\Agents\LLM\Prompt\PromptInterface;
1313
use LLM\Agents\LLM\Prompt\Tool;
1414
use LLM\Agents\LLM\Response\Response;
15+
use LLM\Agents\OpenAI\Client\Exception\LimitExceededException;
16+
use LLM\Agents\OpenAI\Client\Exception\RateLimitException;
17+
use LLM\Agents\OpenAI\Client\Exception\TimeoutException;
1518
use OpenAI\Contracts\ClientContract;
1619

1720
final class LLM implements LLMInterface
@@ -77,7 +80,17 @@ public function generate(
7780
->chat()
7881
->createStreamed($request);
7982

80-
return $this->streamParser->parse($stream, $callback);
83+
try {
84+
return $this->streamParser->parse($stream, $callback);
85+
} catch (LimitExceededException) {
86+
throw new \LLM\Agents\LLM\Exception\LimitExceededException(
87+
currentLimit: $request['max_tokens'],
88+
);
89+
} catch (RateLimitException) {
90+
throw new \LLM\Agents\LLM\Exception\RateLimitException();
91+
} catch (TimeoutException) {
92+
throw new \LLM\Agents\LLM\Exception\TimeoutException();
93+
}
8194
}
8295

8396
protected function buildOptions(OptionsInterface $options): array

src/Parsers/ChatResponseParser.php

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,9 @@
55
namespace LLM\Agents\OpenAI\Client\Parsers;
66

77
use LLM\Agents\OpenAI\Client\Event\MessageChunk;
8+
use LLM\Agents\OpenAI\Client\Exception\LimitExceededException;
9+
use LLM\Agents\OpenAI\Client\Exception\RateLimitException;
10+
use LLM\Agents\OpenAI\Client\Exception\TimeoutException;
811
use LLM\Agents\OpenAI\Client\StreamChunkCallbackInterface;
912
use LLM\Agents\LLM\Response\FinishReason;
1013
use LLM\Agents\LLM\Response\Response;
@@ -21,6 +24,11 @@ public function __construct(
2124
private ?EventDispatcherInterface $eventDispatcher = null,
2225
) {}
2326

27+
/**
28+
* @throws LimitExceededException
29+
* @throws RateLimitException
30+
* @throws TimeoutException
31+
*/
2432
public function parse(ResponseStreamContract $stream, ?StreamChunkCallbackInterface $callback = null): Response
2533
{
2634
$callback ??= static fn(?string $chunk, bool $stop, ?string $finishReason = null) => null;
@@ -112,6 +120,9 @@ public function parse(ResponseStreamContract $stream, ?StreamChunkCallbackInterf
112120
tools: \array_values($toolCalls),
113121
finishReason: $finishReason->value,
114122
),
123+
$finishReason === FinishReason::Length => throw new LimitExceededException(),
124+
$finishReason === FinishReason::Timeout => throw new TimeoutException(),
125+
$finishReason === FinishReason::Limit => throw new RateLimitException(),
115126
};
116127
}
117128
}

src/Parsers/ParserInterface.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,19 @@
44

55
namespace LLM\Agents\OpenAI\Client\Parsers;
66

7+
use LLM\Agents\OpenAI\Client\Exception\LimitExceededException;
8+
use LLM\Agents\OpenAI\Client\Exception\RateLimitException;
9+
use LLM\Agents\OpenAI\Client\Exception\TimeoutException;
710
use LLM\Agents\OpenAI\Client\StreamChunkCallbackInterface;
811
use LLM\Agents\LLM\Response\Response;
912
use OpenAI\Contracts\ResponseStreamContract;
1013

1114
interface ParserInterface
1215
{
16+
/**
17+
* @throws LimitExceededException
18+
* @throws RateLimitException
19+
* @throws TimeoutException
20+
*/
1321
public function parse(ResponseStreamContract $stream, ?StreamChunkCallbackInterface $callback = null): Response;
1422
}

src/StreamResponseParser.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@
44

55
namespace LLM\Agents\OpenAI\Client;
66

7+
use LLM\Agents\OpenAI\Client\Exception\LimitExceededException;
8+
use LLM\Agents\OpenAI\Client\Exception\RateLimitException;
9+
use LLM\Agents\OpenAI\Client\Exception\TimeoutException;
710
use LLM\Agents\OpenAI\Client\Parsers\ParserInterface;
811
use LLM\Agents\LLM\Exception\LLMException;
912
use LLM\Agents\LLM\Response\Response;
@@ -19,6 +22,11 @@ public function registerParser(string $type, ParserInterface $parser): void
1922
$this->parsers[$type] = $parser;
2023
}
2124

25+
/**
26+
* @throws LimitExceededException
27+
* @throws RateLimitException
28+
* @throws TimeoutException
29+
*/
2230
public function parse(StreamResponse $stream, ?StreamChunkCallbackInterface $callback = null): Response
2331
{
2432
$this->validateStreamResponse($stream);

0 commit comments

Comments
 (0)