Skip to content

Commit 861ab5f

Browse files
authored
Merge pull request #92 from dkotter/fix/89
Modify the `toText` and `toTexts` methods of the `GenerativeAiResult` class to only return the content channel
2 parents 666f9aa + cfdbec7 commit 861ab5f

File tree

2 files changed

+88
-5
lines changed

2 files changed

+88
-5
lines changed

src/Results/DTO/GenerativeAiResult.php

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -201,6 +201,8 @@ public function hasMultipleCandidates(): bool
201201
/**
202202
* Converts the first candidate to text.
203203
*
204+
* Only text from the content channel is considered. Text within model thought or reasoning is ignored.
205+
*
204206
* @since 0.1.0
205207
*
206208
* @return string The text content.
@@ -210,8 +212,9 @@ public function toText(): string
210212
{
211213
$message = $this->candidates[0]->getMessage();
212214
foreach ($message->getParts() as $part) {
215+
$channel = $part->getChannel();
213216
$text = $part->getText();
214-
if ($text !== null) {
217+
if ($channel->isContent() && $text !== null) {
215218
return $text;
216219
}
217220
}
@@ -222,6 +225,8 @@ public function toText(): string
222225
/**
223226
* Converts the first candidate to a file.
224227
*
228+
* Only files from the content channel are considered. Files within model thought or reasoning are ignored.
229+
*
225230
* @since 0.1.0
226231
*
227232
* @return File The file.
@@ -231,8 +236,9 @@ public function toFile(): File
231236
{
232237
$message = $this->candidates[0]->getMessage();
233238
foreach ($message->getParts() as $part) {
239+
$channel = $part->getChannel();
234240
$file = $part->getFile();
235-
if ($file !== null) {
241+
if ($channel->isContent() && $file !== null) {
236242
return $file;
237243
}
238244
}
@@ -316,7 +322,7 @@ public function toMessage(): Message
316322
}
317323

318324
/**
319-
* Converts all candidates to text array.
325+
* Converts all candidates to text.
320326
*
321327
* @since 0.1.0
322328
*
@@ -328,8 +334,9 @@ public function toTexts(): array
328334
foreach ($this->candidates as $candidate) {
329335
$message = $candidate->getMessage();
330336
foreach ($message->getParts() as $part) {
337+
$channel = $part->getChannel();
331338
$text = $part->getText();
332-
if ($text !== null) {
339+
if ($channel->isContent() && $text !== null) {
333340
$texts[] = $text;
334341
break;
335342
}
@@ -351,8 +358,9 @@ public function toFiles(): array
351358
foreach ($this->candidates as $candidate) {
352359
$message = $candidate->getMessage();
353360
foreach ($message->getParts() as $part) {
361+
$channel = $part->getChannel();
354362
$file = $part->getFile();
355-
if ($file !== null) {
363+
if ($channel->isContent() && $file !== null) {
356364
$files[] = $file;
357365
break;
358366
}

tests/unit/Results/DTO/GenerativeAiResultTest.php

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
use WordPress\AiClient\Messages\DTO\Message;
1212
use WordPress\AiClient\Messages\DTO\MessagePart;
1313
use WordPress\AiClient\Messages\DTO\ModelMessage;
14+
use WordPress\AiClient\Messages\Enums\MessagePartChannelEnum;
1415
use WordPress\AiClient\Messages\Enums\MessagePartTypeEnum;
1516
use WordPress\AiClient\Messages\Enums\MessageRoleEnum;
1617
use WordPress\AiClient\Providers\DTO\ProviderMetadata;
@@ -189,6 +190,36 @@ public function testToText(): void
189190
$this->assertEquals($text, $result->toText());
190191
}
191192

193+
/**
194+
* Tests toText method with both reasoning_content and content channels.
195+
*
196+
* @return void
197+
*/
198+
public function testToTextWithReasoningContent(): void
199+
{
200+
$reasoningContent = 'Let me think about this step by step...';
201+
$actualContent = 'This is the final answer.';
202+
203+
$message = new ModelMessage([
204+
new MessagePart($reasoningContent, MessagePartChannelEnum::thought()),
205+
new MessagePart($actualContent, MessagePartChannelEnum::content())
206+
]);
207+
$candidate = new Candidate($message, FinishReasonEnum::stop());
208+
$tokenUsage = new TokenUsage(10, 8, 18);
209+
210+
$result = new GenerativeAiResult(
211+
'result_with_reasoning',
212+
[$candidate],
213+
$tokenUsage,
214+
$this->createTestProviderMetadata(),
215+
$this->createTestModelMetadata()
216+
);
217+
218+
// toText() should only return content from the 'content' channel, not 'thought' channel
219+
$this->assertEquals($actualContent, $result->toText());
220+
$this->assertNotEquals($reasoningContent, $result->toText());
221+
}
222+
192223
/**
193224
* Tests toText throws exception when no text content.
194225
*
@@ -430,6 +461,50 @@ public function testToTextsWithMultipleCandidates(): void
430461
$this->assertEquals($texts, $result->toTexts());
431462
}
432463

464+
/**
465+
* Tests toTexts method with both reasoning_content and content channels.
466+
*
467+
* @return void
468+
*/
469+
public function testToTextsWithReasoningContent(): void
470+
{
471+
$reasoningContent1 = 'Let me think about the first question...';
472+
$actualContent1 = 'This is the first answer.';
473+
$reasoningContent2 = 'Now for the second question...';
474+
$actualContent2 = 'This is the second answer.';
475+
476+
$message1 = new ModelMessage([
477+
new MessagePart($reasoningContent1, MessagePartChannelEnum::thought()),
478+
new MessagePart($actualContent1, MessagePartChannelEnum::content())
479+
]);
480+
$message2 = new ModelMessage([
481+
new MessagePart($reasoningContent2, MessagePartChannelEnum::thought()),
482+
new MessagePart($actualContent2, MessagePartChannelEnum::content())
483+
]);
484+
485+
$candidates = [
486+
new Candidate($message1, FinishReasonEnum::stop()),
487+
new Candidate($message2, FinishReasonEnum::stop())
488+
];
489+
$tokenUsage = new TokenUsage(20, 15, 35);
490+
491+
$result = new GenerativeAiResult(
492+
'result_texts_with_reasoning',
493+
$candidates,
494+
$tokenUsage,
495+
$this->createTestProviderMetadata(),
496+
$this->createTestModelMetadata()
497+
);
498+
499+
// toTexts() should only return content from the 'content' channel, not 'thought' channel
500+
$expectedTexts = [$actualContent1, $actualContent2];
501+
$this->assertEquals($expectedTexts, $result->toTexts());
502+
503+
// Verify reasoning content is not included
504+
$this->assertNotContains($reasoningContent1, $result->toTexts());
505+
$this->assertNotContains($reasoningContent2, $result->toTexts());
506+
}
507+
433508
/**
434509
* Tests toFiles method with multiple candidates.
435510
*

0 commit comments

Comments
 (0)