import React from 'react';
import { screen } from '@testing-library/react';
import { renderInAppContext } from '@theorchard/suite-testing';
import { TaxFormInfoViewType } from '../tax-form-info';
import TaxFormInfoTopSection, {
    TaxFormInfoTopSectionPropTypes,
    CLASS_NAME,
} from '../tax-form-info-top-section';
import { REQUEST_NEW_FORM_BTN_TEXT } from '../tax-form-info-subsection';
import { useCanPerformAction } from 'src/apollo/queries/can-perform';
import dayjs from 'dayjs';
import { DATE_FORMAT } from 'src/constants';

jest.mock('src/apollo/queries/can-perform', () => ({
    useCanPerformAction: jest.fn(),
}));

describe('<TaxFormInfoTopSection>', () => {
    const defaultProps: TaxFormInfoTopSectionPropTypes = {
        accountId: '32145',
        accountPayeeId: '123',
        expirationDate: '2024-11-20T13:09:29.000000',
        isTaxFormInfoEmpty: true,
        taxFormInfoViewType: TaxFormInfoViewType.DEFAULT,
        taxEligibilityItem: {
            abacusStateId: '71127',
            actionName: 'tax_eligibility',
            actionStatus: 'init',
            createdAt: '',
            lastModified: '2024-11-20T13:09:29.000000',
            message: 'Test Notes Message',
        },
        isNonSpanishTaxResident: false,
        isOrchardESAccount: false,
        canEditUSTaxInfo: true,
    };

    afterEach(jest.restoreAllMocks);

    const render = (props: TaxFormInfoTopSectionPropTypes) =>
        renderInAppContext(<TaxFormInfoTopSection {...props} />);

    it('renders', () => {
        const { container } = render(defaultProps);

        expect(container).toBeDefined();
        expect(screen.getByTestId(CLASS_NAME)).toBeDefined();
        expect(screen.getByText('Tax Information')).toBeDefined();
    });

    it('renders PENDING view', () => {
        const updatedProps = {
            ...defaultProps,
            taxFormInfoViewType: TaxFormInfoViewType.PENDING,
        };

        render(updatedProps);
        expect(screen.getByTestId('WarningGlyphIcon')).toBeDefined();
        const rejectFormButton = screen.getByRole('button', {
            name: 'Reject the Form',
        });
        expect(rejectFormButton).toBeDefined();

        const addDetailsButton = screen.getByRole('button', {
            name: 'Add Tax Form details',
        });
        expect(addDetailsButton).toBeDefined();
        expect(addDetailsButton.firstChild).toHaveClass('PlusGlyphIcon');
        expect(
            screen.getByText('Tax information has not been added yet')
        ).toBeDefined();
    });

    it('renders REJECTED view', () => {
        (useCanPerformAction as jest.Mock).mockReturnValue({
            data: true,
            loading: false,
        });

        const updatedProps = {
            ...defaultProps,
            taxFormInfoViewType: TaxFormInfoViewType.REJECTED,
        };

        render(updatedProps);
        expect(screen.getByTestId('CloseGlyphIcon')).toBeDefined();
        expect(screen.getByTestId('Alert')).toBeDefined();
        expect(screen.getByTestId('WarningGlyphIcon')).toBeDefined();
        expect(
            screen.getByText('Tax form rejected on 11/20/2024')
        ).toBeDefined();

        expect(screen.getByText('See notes')).toBeDefined();
        expect(screen.getByText('Test Notes Message')).toBeDefined();

        expect(
            screen.getByText(
                'Please request an updated tax form from the client.'
            )
        ).toBeDefined();

        const receivedNewFormButton = screen.getByRole('button', {
            name: REQUEST_NEW_FORM_BTN_TEXT,
        });
        expect(receivedNewFormButton).toBeDefined();
    });

    it('renders EXPIRED view', () => {
        (useCanPerformAction as jest.Mock).mockReturnValue({
            data: true,
            loading: false,
        });

        const updatedProps = {
            ...defaultProps,
            taxFormInfoViewType: TaxFormInfoViewType.EXPIRED,
        };

        render(updatedProps);
        expect(screen.getAllByTestId('WarningGlyphIcon')).toHaveLength(2);
        expect(screen.getByTestId('Alert')).toBeDefined();
        expect(
            screen.getByText('Tax form expired on 11/20/2024')
        ).toBeDefined();
        expect(
            screen.getByText(
                'Please request an updated tax form from the client.'
            )
        ).toBeDefined();

        const receivedNewFormButton = screen.getByRole('button', {
            name: REQUEST_NEW_FORM_BTN_TEXT,
        });
        expect(receivedNewFormButton).toBeDefined();
    });

    it('renders EXPIRED view non Spanish resident', () => {
        (useCanPerformAction as jest.Mock).mockReturnValue({
            data: true,
            loading: false,
        });

        const updatedProps = {
            ...defaultProps,
            taxFormInfoViewType: TaxFormInfoViewType.EXPIRED,
            isNonSpanishTaxResident: true,
            isOrchardESAccount: true,
            taxInfoESData: {
                abacusAccount: {
                    accountTaxInfo: {
                        countryOfTaxResidence: 'ALB',
                        certificateOfResidenceExpirationDate: '2025-01-01',
                    },
                },
            },
        } as TaxFormInfoTopSectionPropTypes;

        render(updatedProps);
        expect(screen.getAllByTestId('WarningGlyphIcon')).toHaveLength(2);
        expect(screen.getByTestId('Alert')).toBeDefined();
        expect(
            screen.getByText(/Account is not eligible for payment as the/i)
        ).toBeInTheDocument();
        expect(screen.getByText(/expired on 2025-01-01/i)).toBeInTheDocument();
    });

    describe('renders COMPLETED view', () => {
        test('renders COMPLETED view', () => {
            const updatedProps = {
                ...defaultProps,
                taxFormInfoViewType: TaxFormInfoViewType.COMPLETED,
            };

            render(updatedProps);
            expect(screen.getByTestId('CheckGlyphIcon')).toBeDefined();
            expect(screen.getByText('Tax Information')).toBeDefined();
        });

        test('renders COMPLETED view with expiring certificate for non-Spanish resident', () => {
            (useCanPerformAction as jest.Mock).mockReturnValue({
                data: true,
                loading: false,
            });
            const updatedProps = {
                ...defaultProps,
                taxFormInfoViewType: TaxFormInfoViewType.COMPLETED,
                isNonSpanishTaxResident: true,
                isOrchardESAccount: true,
                taxInfoESData: {
                    abacusAccount: {
                        accountTaxInfo: {
                            certificateOfResidenceExpirationDate: dayjs()
                                .add(3, 'month')
                                .format(DATE_FORMAT),
                        },
                    },
                },
            } as TaxFormInfoTopSectionPropTypes;

            const { baseElement } = render(updatedProps);

            expect(
                baseElement.querySelector('.Alert-text')?.textContent
            ).toContain('Certificate of Residence will expire on');
        });
    });
});
