import { describe, it, expect } from 'vitest';
import { mount } from '@vue/test-utils';
import { createVuetify } from 'vuetify';
import { createPinia, setActivePinia } from 'pinia';
import KanbanView from '../../resources/js/views/KanbanView.vue';
import { LEAD_STATUSES } from '../../resources/js/composables/leadStatuses';

describe('KanbanView.vue', () => {
    // KanbanView содержит DealDetailDrawer (v-navigation-drawer), который требует
    // injected layout от v-app — оборачиваем в v-app для теста.
    // KanbanView содержит DealDetailDrawer (v-navigation-drawer) — stub'им,
    // т.к. layout-injection недоступна в Vitest. Drawer тестируется отдельно.
    const factory = () => {
        setActivePinia(createPinia());
        return mount(KanbanView, {
            global: {
                plugins: [createVuetify()],
                stubs: { DealDetailDrawer: true, NewDealDialog: true },
            },
        });
    };

    it('монтируется и содержит заголовок «Канбан»', () => {
        const wrapper = factory();
        expect(wrapper.find('h1').text()).toBe('Канбан');
    });

    it('рендерит ровно 14 KanbanColumn (по числу lead_statuses)', () => {
        const wrapper = factory();
        const cols = wrapper.findAllComponents({ name: 'KanbanColumn' });
        expect(cols).toHaveLength(LEAD_STATUSES.length);
        expect(cols).toHaveLength(14);
    });

    it('каждая колонка получает соответствующий статус', () => {
        const wrapper = factory();
        const cols = wrapper.findAllComponents({ name: 'KanbanColumn' });
        cols.forEach((col, i) => {
            expect(col.props('status').slug).toBe(LEAD_STATUSES[i].slug);
        });
    });

    it('содержит page-stats с числом статусов и сделок', () => {
        const wrapper = factory();
        const text = wrapper.text();
        expect(text).toContain('14');
        expect(text).toContain('статусов');
        expect(text).toContain('сделок');
    });

    it('содержит кнопку «Новая сделка»', () => {
        const wrapper = factory();
        expect(wrapper.text()).toContain('Новая сделка');
    });

    it('содержит подсказку про перетаскивание (DnD активен)', () => {
        const wrapper = factory();
        expect(wrapper.text()).toMatch(/[Пп]еретаскивание/);
    });

    it('кнопка «Новая сделка» открывает NewDealDialog', async () => {
        const wrapper = factory();
        const vm = wrapper.vm as unknown as { newDealOpen: boolean };
        expect(vm.newDealOpen).toBe(false);
        await wrapper.find('[data-testid="new-deal-btn"]').trigger('click');
        await wrapper.vm.$nextTick();
        expect(vm.newDealOpen).toBe(true);
    });

    it('onDealCreated кладёт сделку в правильную колонку по statusSlug', async () => {
        const wrapper = factory();
        const vm = wrapper.vm as unknown as {
            dealsByStatus: Record<string, Array<{ id: number; statusSlug: string }>>;
            onDealCreated: (deal: Record<string, unknown>) => void;
            totalDeals: number;
        };
        const beforeNew = vm.dealsByStatus.new.length;
        const beforeTotal = vm.totalDeals;
        // Передаём полную форму deal — Kanban-карточка ожидает manager/cost/etc.
        vm.onDealCreated({
            id: 999,
            name: 'Тест',
            phone: '+7 (999) 000-00-00',
            statusSlug: 'new',
            project: 'Окна Москва',
            manager: { initials: 'Т', name: 'Тест' },
            cost: 100,
            receivedMinutesAgo: 0,
        });
        await wrapper.vm.$nextTick();
        expect(vm.dealsByStatus.new.length).toBe(beforeNew + 1);
        expect(vm.dealsByStatus.new[0].id).toBe(999);
        expect(vm.totalDeals).toBe(beforeTotal + 1);
    });

    it('обновляет statusSlug сделки при drop в новую колонку (event.added)', async () => {
        const wrapper = factory();
        const cols = wrapper.findAllComponents({ name: 'KanbanColumn' });
        // Берём сделку из первой колонки (new) и эмулируем «added» в paid-колонке.
        const newCol = cols[0]; // new — sortOrder=1
        const paidCol = cols.find((c) => c.props('status').slug === 'paid')!;
        const dealToMove = (newCol.props('deals') as { id: number; statusSlug: string }[])[0];

        // Эмуляция события vuedraggable@change → KanbanView.onColumnChange.
        await paidCol.vm.$emit('change', {
            added: { element: dealToMove, newIndex: 0 },
        });
        await wrapper.vm.$nextTick();

        // statusSlug сделки должен переключиться на 'paid'.
        expect(dealToMove.statusSlug).toBe('paid');
    });
});
