import { describe, it, expect, vi, beforeEach } from 'vitest';
import { render, screen } from '@testing-library/react';
import { TrackSearchResults } from './TrackSearchResults';
import type { Track } from '../types/track';

// Mock react-router-dom
vi.mock('react-router-dom', () => ({
  Link: ({ children, to }: { children: React.ReactNode; to: string }) => (
    <a href={to}>{children}</a>
  ),
}));

describe('TrackSearchResults', () => {
  const mockTracks: Track[] = [
    {
      id: 1,
      creator_id: 123,
      title: 'Test Track 1',
      artist: 'Test Artist 1',
      duration: 180,
      file_path: '/test/track1.mp3',
      file_size: 5000000,
      format: 'MP3',
      genre: 'Rock',
      is_public: true,
      play_count: 10,
      like_count: 5,
      created_at: '2024-01-01T00:00:00Z',
      updated_at: '2024-01-01T00:00:00Z',
    },
    {
      id: 2,
      creator_id: 123,
      title: 'Test Track 2',
      artist: 'Test Artist 2',
      duration: 200,
      file_path: '/test/track2.mp3',
      file_size: 6000000,
      format: 'FLAC',
      genre: 'Pop',
      is_public: true,
      play_count: 20,
      like_count: 10,
      created_at: '2024-01-02T00:00:00Z',
      updated_at: '2024-01-02T00:00:00Z',
    },
  ];

  const mockOnPageChange = vi.fn();

  beforeEach(() => {
    vi.clearAllMocks();
  });

  it('should display loading state', () => {
    render(
      <TrackSearchResults
        tracks={[]}
        total={0}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
        loading={true}
      />,
    );

    // Loading spinner should be visible (checking by role or text)
    expect(screen.queryByText('Aucun track trouvé')).not.toBeInTheDocument();
  });

  it('should display error message', () => {
    render(
      <TrackSearchResults
        tracks={[]}
        total={0}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
        error="Search failed"
      />,
    );

    expect(screen.getByText('Erreur')).toBeInTheDocument();
    expect(screen.getByText('Search failed')).toBeInTheDocument();
  });

  it('should display empty state when no tracks', () => {
    render(
      <TrackSearchResults
        tracks={[]}
        total={0}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
      />,
    );

    expect(screen.getByText('Aucun track trouvé')).toBeInTheDocument();
    expect(
      screen.getByText(/Essayez de modifier vos critères de recherche/i),
    ).toBeInTheDocument();
  });

  it('should display tracks', () => {
    render(
      <TrackSearchResults
        tracks={mockTracks}
        total={2}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
      />,
    );

    expect(screen.getByText('Test Track 1')).toBeInTheDocument();
    expect(screen.getByText('Test Track 2')).toBeInTheDocument();
    expect(screen.getByText('Test Artist 1')).toBeInTheDocument();
    expect(screen.getByText('Test Artist 2')).toBeInTheDocument();
    expect(screen.getByText('2 résultats trouvés')).toBeInTheDocument();
  });

  it('should display pagination when multiple pages', () => {
    render(
      <TrackSearchResults
        tracks={mockTracks}
        total={50}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
      />,
    );

    expect(screen.getByText('Page 1 sur 3')).toBeInTheDocument();
    expect(screen.getByText('Précédent')).toBeInTheDocument();
    expect(screen.getByText('Suivant')).toBeInTheDocument();
  });

  it('should disable previous button on first page', () => {
    render(
      <TrackSearchResults
        tracks={mockTracks}
        total={50}
        page={1}
        limit={20}
        onPageChange={mockOnPageChange}
      />,
    );

    const prevButton = screen.getByText('Précédent').closest('button');
    expect(prevButton).toBeDisabled();
  });

  it('should disable next button on last page', () => {
    render(
      <TrackSearchResults
        tracks={mockTracks}
        total={50}
        page={3}
        limit={20}
        onPageChange={mockOnPageChange}
      />,
    );

    const nextButton = screen.getByText('Suivant').closest('button');
    expect(nextButton).toBeDisabled();
  });
});
