<?php

declare(strict_types=1);

use App\Application\Campaign\ValueObjects\Campaign;
use App\Application\Campaign\ValueObjects\CampaignTrack;

describe('SpotifyCampaignService - Spotify ID Extraction', function () {

    it('extracts Spotify ID from URI format (spotify:track:xxx)', function () {
        $track = CampaignTrack::fromArray([
            'id' => 'track_1',
            'position' => 1,
            'title' => 'Test Track',
            'duration' => 180,
            'preview_url' => null,
            'spotify_uri' => 'spotify:track:track_id_123',
            'isrc' => null,
        ]);

        // Use reflection to test private method
        $service = new \ReflectionClass(App\Application\Campaign\Services\SpotifyCampaignService::class);
        $method = $service->getMethod('extractSpotifyId');
        $method->setAccessible(true);

        $extracted = $method->invoke(
            $service->newInstanceWithoutConstructor(),
            'spotify:track:track_id_123'
        );

        expect($extracted)->toBe('track_id_123');
    });

    it('extracts Spotify ID from URL format', function () {
        $service = new \ReflectionClass(App\Application\Campaign\Services\SpotifyCampaignService::class);
        $method = $service->getMethod('extractSpotifyId');
        $method->setAccessible(true);

        $extracted = $method->invoke(
            $service->newInstanceWithoutConstructor(),
            'https://open.spotify.com/track/url_track_id'
        );

        expect($extracted)->toBe('url_track_id');
    });

    it('returns ID if already just an ID', function () {
        $service = new \ReflectionClass(App\Application\Campaign\Services\SpotifyCampaignService::class);
        $method = $service->getMethod('extractSpotifyId');
        $method->setAccessible(true);

        $extracted = $method->invoke(
            $service->newInstanceWithoutConstructor(),
            'just_an_id_123'
        );

        expect($extracted)->toBe('just_an_id_123');
    });

    it('returns null for null input', function () {
        $service = new \ReflectionClass(App\Application\Campaign\Services\SpotifyCampaignService::class);
        $method = $service->getMethod('extractSpotifyId');
        $method->setAccessible(true);

        $extracted = $method->invoke(
            $service->newInstanceWithoutConstructor(),
            null
        );

        expect($extracted)->toBeNull();
    });
});

describe('Campaign Value Objects', function () {

    it('creates campaign with tracks', function () {
        $campaign = Campaign::fromArray([
            'id' => '123',
            'slug' => 'test-album',
            'artist_name' => 'Test Artist',
            'album_title' => 'Test Album',
            'description' => 'Test description',
            'artwork_url' => 'https://example.com/art.jpg',
            'release_date' => '2024-12-01',
            'total_saves' => 100,
            'track_count' => 2,
            'spotify_enabled' => true,
            'apple_music_enabled' => true,
            'spotify_uri' => 'spotify:album:abc123',
            'apple_music_id' => 'apple123',
            'tracks' => [
                [
                    'id' => 'track_1',
                    'position' => 1,
                    'title' => 'Track 1',
                    'duration' => 180,
                    'preview_url' => null,
                    'spotify_uri' => 'spotify:track:track1',
                    'isrc' => 'US1234567890',
                ],
                [
                    'id' => 'track_2',
                    'position' => 2,
                    'title' => 'Track 2',
                    'duration' => 200,
                    'preview_url' => null,
                    'spotify_uri' => 'spotify:track:track2',
                    'isrc' => 'US0987654321',
                ],
            ],
            'status' => 'active',
        ]);

        expect($campaign->id)->toBe('123');
        expect($campaign->slug)->toBe('test-album');
        expect($campaign->spotify_enabled)->toBeTrue();
        expect($campaign->tracks)->toHaveCount(2);
        expect($campaign->tracks[0]->title)->toBe('Track 1');
    });

    it('validates campaign status methods', function () {
        $activeCampaign = Campaign::fromArray([
            'id' => '1',
            'slug' => 'active',
            'artist_name' => 'Artist',
            'album_title' => 'Album',
            'description' => null,
            'artwork_url' => null,
            'release_date' => '2025-12-01',
            'total_saves' => 0,
            'track_count' => 0,
            'spotify_enabled' => false,
            'apple_music_enabled' => false,
            'spotify_uri' => null,
            'apple_music_id' => null,
            'status' => 'active',
        ]);

        expect($activeCampaign->isActive())->toBeTrue();
        expect($activeCampaign->hasReleased())->toBeFalse();
    });

    it('creates campaign track value object', function () {
        $track = CampaignTrack::fromArray([
            'id' => 'track_123',
            'position' => 1,
            'title' => 'Amazing Song',
            'duration' => 240,
            'preview_url' => 'https://example.com/preview.mp3',
            'spotify_id' => 'abc123',
            'apple_music_id' => 'apple456',
        ]);

        expect($track->id)->toBe('track_123');
        expect($track->position)->toBe(1);
        expect($track->title)->toBe('Amazing Song');
        expect($track->duration)->toBe(240);
        expect($track->spotify_id)->toBe('abc123');
        expect($track->apple_music_id)->toBe('apple456');
    });
});
