import React from 'react';
import {render, screen} from '@testing-library/react';

const mockedGet = jest.fn();
jest.mock('@/http', () => ({
  __esModule: true,
  default: {get: (...args: unknown[]) => mockedGet(...args)},
}));
jest.mock('next-intl', () => ({
  NextIntlClientProvider: ({children}: {children: React.ReactNode}) => <>{children}</>,
  useTranslations: () => (key: string) => key,
}));
jest.mock('@/i18n', () => jest.fn().mockResolvedValue({messages: {EnsembleEvenementsDetailsPage: {}}}));
jest.mock('@/components/EnsembleEvenement/EventCardEnsembleEvenement', () => ({__esModule: true, default: () => <div data-testid="event-card" />}));
jest.mock('@/components/EnsembleEvenement/CarouselAfficheEnsembleEvenementClient', () => ({__esModule: true, default: () => <div data-testid="carousel" />}));
jest.mock('@/components/EnsembleEvenement/EditionsEnsemble', () => ({
  __esModule: true,
  default: ({editions, titleKey}: {editions?: {eesLibelle: string}[]; titleKey: string}) => (
    <div data-testid={`editions-${titleKey}`} data-count={editions?.length ?? 0} data-noms={(editions ?? []).map(e => e.eesLibelle).join('|')} />
  ),
}));
jest.mock('@/components/EnsembleEvenement/EnsembleEvenementCarte', () => ({
  __esModule: true,
  default: ({evenements}: {evenements?: unknown[]}) => <div data-testid="carte" data-count={evenements?.length ?? 0} />,
}));
jest.mock('@/services/entityFilesService', () => ({getFichiers: jest.fn().mockResolvedValue([])}));
jest.mock('@/components/shared/FichiersSection/FichiersSection', () => ({
  __esModule: true,
  default: ({fichiers}: {fichiers: {nom: string}[]}) => <div data-testid="fichiers" data-count={fichiers.length} />,
}));
jest.mock('@/components/community/FavoriteButton', () => ({__esModule: true, default: () => <div data-testid="favorite" />}));
jest.mock('@/services/articleLienService', () => ({
  getArticlesLies: jest.fn().mockResolvedValue([]),
}));
jest.mock('@/components/shared/ArticlesLiesSection/ArticlesLiesSection', () => ({
  __esModule: true,
  default: ({articles, locale}: {articles?: unknown[]; locale: string}) => (
    <div data-testid="articles-lies" data-count={articles?.length ?? 0} data-locale={locale} />
  ),
}));
jest.mock('@/components/shared/VisitCounter/VisitCounter', () => ({
  __esModule: true,
  default: ({tableCible, cibleId}: {tableCible: string; cibleId: number}) => (
    <div data-testid="visit-counter" data-table={tableCible} data-cible={cibleId} />
  ),
}));

import Page, {generateMetadata} from '../page';
import {getArticlesLies} from '@/services/articleLienService';

const mockedGetArticlesLies = getArticlesLies as jest.Mock;

const props = {params: Promise.resolve({locale: 'fr', ensId: '5'})};

const interceltique = {
  eesId: 5,
  eesLibelle: 'Festival Interceltique',
  eesFils: [],
  eesPere: {allEditions: []},
  endDate: null,
  startDate: null,
  nbEvent: 1,
  tev: [],
  evenements: [{eveId: 1, eveVil: {vilNom: 'Lorient'}}],
  logoUrl: null,
  parents: [],
  enfants: [],
};

describe("Page ensemble d'événements — titre et compteur de vues", () => {
  beforeEach(() => {
    jest.clearAllMocks();
    mockedGet.mockResolvedValue({data: interceltique});
  });

  it('shouldBuildTheDocumentTitleFromTheEnsembleName', async () => {
    expect(await generateMetadata(props)).toEqual({title: 'Festival Interceltique - Tamm-Kreiz'});
  });

  it('shouldFallBackToTheSiteNameWhenTheEnsembleCannotBeLoaded', async () => {
    mockedGet.mockRejectedValue(new Error('HTTP 404'));

    expect(await generateMetadata(props)).toEqual({title: 'Tamm-Kreiz'});
  });

  it('shouldCountTheViewsOfTheEnsemble', async () => {
    render(await (Page as any)(props));

    expect(screen.getByRole('heading', {level: 1})).toHaveTextContent('Festival Interceltique');
    const counter = screen.getByTestId('visit-counter');
    expect(counter).toHaveAttribute('data-table', 'evenement_ensemble');
    expect(counter).toHaveAttribute('data-cible', '5');
  });
});

describe("Page ensemble d'événements — articles du Mag", () => {
  beforeEach(() => {
    jest.clearAllMocks();
    mockedGet.mockResolvedValue({data: interceltique});
    mockedGetArticlesLies.mockResolvedValue([{id: 1, title: 'Les sonneurs de couple', slug: 'sonneurs-de-couple'}]);
  });

  it('shouldListTheArticlesLinkedToTheEnsemble', async () => {
    render(await (Page as any)(props));

    expect(mockedGetArticlesLies).toHaveBeenCalledWith('evenement_ensemble', '5');
    const section = screen.getByTestId('articles-lies');
    expect(section).toHaveAttribute('data-count', '1');
    expect(section).toHaveAttribute('data-locale', 'fr');
  });
});

describe("Page ensemble d'événements — logo, carte, éditions, fichiers", () => {
  beforeEach(() => {
    jest.clearAllMocks();
    mockedGetArticlesLies.mockResolvedValue([]);
  });

  it('shouldShowTheLogoTheMapTheEditionsAndTheFiles', async () => {
    const {getFichiers} = jest.requireMock('@/services/entityFilesService');
    getFichiers.mockResolvedValue([{nom: 'programme.pdf', url: 'https://files.test/programme.pdf'}]);
    mockedGet.mockResolvedValue({data: {
      ...interceltique,
      logoUrl: 'https://media.test/fil.png',
      parents: [{eesId: 1, eesLibelle: 'Festival Interceltique', logoUrl: null}],
      enfants: [{eesId: 6, eesLibelle: 'Édition 2025', logoUrl: null, nbEvent: 3}, {eesId: 7, eesLibelle: 'Édition 2026', logoUrl: null, nbEvent: 0}],
    }});

    render(await (Page as any)(props));

    expect(screen.getByRole('img', {name: 'Festival Interceltique'})).toHaveAttribute('src', 'https://media.test/fil.png');
    expect(screen.getByTestId('carte')).toHaveAttribute('data-count', '1');
    expect(screen.getByTestId('editions-title_parents')).toHaveAttribute('data-noms', 'Festival Interceltique');
    expect(screen.getByTestId('editions-title_children')).toHaveAttribute('data-noms', 'Édition 2025|Édition 2026');
    expect(getFichiers).toHaveBeenCalledWith('evenement_ensemble', '5');
    expect(screen.getByTestId('fichiers')).toHaveAttribute('data-count', '1');
  });

  it('shouldShowAPlaceholderInsteadOfAFakeLogo', async () => {
    mockedGet.mockResolvedValue({data: interceltique});

    render(await (Page as any)(props));

    expect(screen.getByTestId('ensemble-sans-logo')).toBeInTheDocument();
    expect(document.querySelector('img[src*="picsum"]')).toBeNull();
  });
});
