<?php

namespace Tests\Unit;

use App\Campaigns\PerformanceTrend;
use App\Models\CampaignPerformanceStat;
use Illuminate\Support\Collection;
use Tests\TestCase;

class CampaignPerformanceTrendTest extends TestCase
{
    public function test_a_lower_recent_cpc_is_improving(): void
    {
        $this->travelTo('2026-09-22 12:00:00');

        $metrics = PerformanceTrend::fromDays($this->days([
            ['stat_date' => '2026-09-10', 'spend' => 20.00, 'impressions' => 2000, 'clicks' => 10],
            ['stat_date' => '2026-09-20', 'spend' => 20.00, 'impressions' => 2000, 'clicks' => 20],
        ]));

        $this->assertSame('improving', $metrics['trend']);
        $this->assertSame(-50.0, $metrics['trend_cpc_change_pct']);
        $this->assertStringContainsString('CPC improved 50%', $metrics['trend_summary']);
        $this->assertSame(20, $metrics['last_7_days']['clicks']);
        $this->assertSame(10, $metrics['previous_7_days']['clicks']);
        $this->assertSame(40.0, $metrics['lifetime']['spend']);
    }

    public function test_a_higher_recent_cpc_is_declining(): void
    {
        $this->travelTo('2026-09-22 12:00:00');

        $metrics = PerformanceTrend::fromDays($this->days([
            ['stat_date' => '2026-09-10', 'spend' => 10.00, 'impressions' => 1000, 'clicks' => 20],
            ['stat_date' => '2026-09-20', 'spend' => 20.00, 'impressions' => 1000, 'clicks' => 10],
        ]));

        $this->assertSame('declining', $metrics['trend']);
        $this->assertStringContainsString('CPC worsened', $metrics['trend_summary']);
    }

    public function test_without_a_prior_week_the_trend_is_unknown(): void
    {
        $this->travelTo('2026-09-22 12:00:00');

        $metrics = PerformanceTrend::fromDays($this->days([
            ['stat_date' => '2026-09-22', 'spend' => 12.10, 'impressions' => 800, 'clicks' => 0],
        ]));

        $this->assertSame('unknown', $metrics['trend']);
        $this->assertSame(12.1, $metrics['lifetime']['spend']);
        $this->assertSame(0, $metrics['previous_7_days']['clicks']);
    }

    /**
     * @param  list<array{stat_date: string, spend: float, impressions: int, clicks: int}>  $rows
     * @return Collection<int, CampaignPerformanceStat>
     */
    private function days(array $rows): Collection
    {
        return collect($rows)->map(
            fn (array $row): CampaignPerformanceStat => CampaignPerformanceStat::make($row),
        );
    }
}
