<?php
namespace boru\ai\Schema;

class Response
{
    /** @var string */
    protected $id;

    /** @var string */
    protected $provider;

    /** @var string */
    protected $model;

    /** @var string */
    protected $status = 'completed';

    /** @var string */
    protected $text = '';

    /** @var ToolCall[] */
    protected $toolCalls = array();

    /** @var array */
    protected $usage = array();

    /** @var mixed */
    protected $error;

    /** @var mixed */
    protected $raw;

    /** @var array */
    protected $metadata = array();

    public function id($value = null)
    {
        if ($value !== null) {
            $this->id = (string)$value;
            return $this;
        }
        return $this->id;
    }

    public function provider($value = null)
    {
        if ($value !== null) {
            $this->provider = (string)$value;
            return $this;
        }
        return $this->provider;
    }

    public function model($value = null)
    {
        if ($value !== null) {
            $this->model = (string)$value;
            return $this;
        }
        return $this->model;
    }

    public function status($value = null)
    {
        if ($value !== null) {
            $this->status = (string)$value;
            return $this;
        }
        return $this->status;
    }

    public function text($value = null)
    {
        if ($value !== null) {
            $this->text = (string)$value;
            return $this;
        }
        return $this->text;
    }

    public function addToolCall($toolCall)
    {
        if (!$toolCall instanceof ToolCall) {
            throw new \InvalidArgumentException('Tool call must be a ToolCall instance');
        }
        $this->toolCalls[] = $toolCall;
        return $this;
    }

    public function toolCalls($toolCalls = null)
    {
        if ($toolCalls !== null) {
            $this->toolCalls = array();
            foreach ((array)$toolCalls as $toolCall) {
                $this->addToolCall($toolCall);
            }
            return $this;
        }
        return $this->toolCalls;
    }

    public function hasToolCalls()
    {
        return count($this->toolCalls()) > 0;
    }

    public function usage($value = null)
    {
        if ($value !== null) {
            $this->usage = is_array($value) ? $value : array();
            return $this;
        }
        return $this->usage;
    }

    public function inputTokens()
    {
        return $this->usageValue('input_tokens');
    }

    public function outputTokens()
    {
        return $this->usageValue('output_tokens');
    }

    public function totalTokens()
    {
        return $this->usageValue('total_tokens');
    }

    public function cachedInputTokens()
    {
        return $this->usageValue('cached_input_tokens');
    }

    public function reasoningTokens()
    {
        return $this->usageValue('reasoning_tokens');
    }

    public function rawUsage()
    {
        return isset($this->usage['raw']) && is_array($this->usage['raw']) ? $this->usage['raw'] : array();
    }

    protected function usageValue($key)
    {
        if (!isset($this->usage[$key])) {
            return null;
        }

        return (int)$this->usage[$key];
    }


    public function error($value = null)
    {
        if (func_num_args() > 0) {
            $this->error = $value;
            return $this;
        }
        return $this->error;
    }

    public function raw($value = null)
    {
        if (func_num_args() > 0) {
            $this->raw = $value;
            return $this;
        }
        return $this->raw;
    }

    public function metadata($key = null, $value = null)
    {
        if ($key === null) {
            return $this->metadata;
        }
        if (is_array($key)) {
            $this->metadata = $key;
            return $this;
        }
        if (func_num_args() > 1) {
            $this->metadata[$key] = $value;
            return $this;
        }
        return isset($this->metadata[$key]) ? $this->metadata[$key] : null;
    }

    public function toArray()
    {
        $toolCalls = array();
        foreach ($this->toolCalls() as $toolCall) {
            $toolCalls[] = $toolCall instanceof ToolCall ? $toolCall->toArray() : $toolCall;
        }

        return array(
            'id' => $this->id(),
            'provider' => $this->provider(),
            'model' => $this->model(),
            'status' => $this->status(),
            'text' => $this->text(),
            'tool_calls' => $toolCalls,
            'usage' => $this->usage(),
            'error' => $this->error(),
            'raw' => $this->raw(),
            'metadata' => $this->metadata(),
        );
    }
}
