calendi/backend/src/Domain/Chat/Message.php
2025-04-26 04:16:02 +02:00

139 lines
3.4 KiB
PHP

<?php
declare(strict_types=1);
namespace App\Domain\Chat;
use DateTimeImmutable;
use DateTimeInterface;
final class Message
{
/**
* @param array<ToolCall>|null $toolCalls
*/
public function __construct(
private readonly string $role,
private readonly ?string $content,
private readonly ?array $toolCalls = null,
private readonly ?ToolResult $toolResult = null,
private readonly DateTimeInterface $createdAt = new DateTimeImmutable(),
) {
}
public function getRole(): string
{
return $this->role;
}
public function getContent(): ?string
{
return $this->content;
}
public function getTwig(): ?string
{
$content = $this->getContent() ?? '```twig\n{}\n```';
$matches = [];
if (preg_match('/```twig\s*([\s\S]*?)\s*```/m', $content, $matches) > 0) {
return $matches[1];
}
return null;
}
/**
* @return array<string, mixed>|null
*/
public function getJson(): ?array
{
$content = $this->getContent() ?? '```json\n{}\n```';
$matches = [];
if (preg_match('/```json\s*([\s\S]*?)\s*```/m', $content, $matches) > 0) {
$decoded = json_decode($matches[1], true);
return is_array($decoded) ? $decoded : null;
}
return null;
}
public function getCreatedAt(): DateTimeInterface
{
return $this->createdAt;
}
/**
* @return array<ToolCall>
*/
public function getToolCalls(): array
{
return $this->toolCalls ?? [];
}
public function getToolResult(): ?ToolResult
{
if (isset($this->toolResult)) {
return $this->toolResult;
}
return null;
}
/**
* @return array<string, mixed>
*/
public function toArray(): array
{
$result = [
'role' => $this->role,
];
if ($this->content !== null) {
$result['content'] = $this->content;
}
if ($this->toolResult !== null) {
$result['tool_call_id'] = $this->toolResult->getToolCallId();
}
if ($this->toolCalls !== null && $this->toolCalls !== []) {
$result['tool_calls'] = array_map(
fn (ToolCall $toolCall) => [
'id' => $toolCall->getId(),
'type' => $toolCall->getType(),
'function' => [
'name' => $toolCall->getName(),
'arguments' => json_encode($toolCall->getArguments()),
],
],
$this->toolCalls
);
}
return $result;
}
public static function fromUser(string $content): self
{
return new self(role: 'user', content: $content);
}
public static function fromSystem(string $content): self
{
return new self(role: 'system', content: $content);
}
/**
* @param array<ToolCall>|null $toolCalls
*/
public static function fromAssistant(?string $content = null, ?array $toolCalls = null): self
{
return new self(role: 'assistant', content: $content, toolCalls: $toolCalls);
}
public static function fromToolResult(string $content, string $toolCallId, string $toolName): self
{
return new self(role: 'tool', content: $content, toolResult: new ToolResult($toolCallId, $toolName));
}
}