<?php

declare(strict_types=1);

namespace App\Framework\Search;

use App\Framework\Core\ValueObjects\Timestamp;

/**
 * Result of bulk indexing operation
 */
final readonly class BulkIndexResult
{
    /**
     * @param array<string> $successfulIds
     * @param array<string> $failedIds
     * @param array<string, string> $errors
     */
    public function __construct(
        public int $total,
        public int $successful,
        public int $failed,
        public Timestamp $startedAt,
        public Timestamp $finishedAt,
        public array $successfulIds = [],
        public array $failedIds = [],
        public array $errors = []
    ) {
    }

    public function isFullySuccessful(): bool
    {
        return $this->failed === 0;
    }

    public function hasErrors(): bool
    {
        return $this->failed > 0;
    }

    public function hasPartialSuccess(): bool
    {
        return $this->successful > 0 && $this->failed > 0;
    }

    public function getSuccessRate(): float
    {
        if ($this->total === 0) {
            return 0.0;
        }

        return ($this->successful / $this->total) * 100;
    }

    public function getDurationMs(): float
    {
        return $this->finishedAt->toFloat() - $this->startedAt->toFloat();
    }

    public function toArray(): array
    {
        return [
            'total' => $this->total,
            'successful' => $this->successful,
            'failed' => $this->failed,
            'successful_ids' => $this->successfulIds,
            'failed_ids' => $this->failedIds,
            'errors' => $this->errors,
            'started_at' => $this->startedAt->toISOString(),
            'finished_at' => $this->finishedAt->toISOString(),
            'duration_ms' => $this->getDurationMs(),
            'success_rate' => $this->getSuccessRate(),
        ];
    }

    public static function empty(): self
    {
        $now = Timestamp::now();

        return new self(
            total: 0,
            successful: 0,
            failed: 0,
            startedAt: $now,
            finishedAt: $now,
            successfulIds: [],
            failedIds: [],
            errors: []
        );
    }
}
