import React, { useEffect, useState } from 'react';
import { SkeletonLoader } from '@theorchard/suite-components';
import cx from 'classnames';
import { isEmpty } from 'lodash-es';
import { useParams } from 'react-router-dom';
import { useNRContributionsList } from 'src/apollo/queries/nr-contributions';
import {
    sortByColumn,
    sortDirection,
} from 'src/apollo/type-constants/schedule';
import InfiniteScroll from 'src/components/shared/infinite-scroll';
import type { NrContributionsQuery } from 'src/apollo/queries/nr-contributions/__generated__/get-nr-contributions';
import type { NrContributionFilter } from 'src/types/contribution';

type NrContribution = NrContributionsQuery['nrContributions']['items'][0];

export interface ContributionsListPropTypes {
    hasAbacusSchedule: boolean;
    includeOnlyValidContributions: boolean;
}

export const ContributionsList: React.FC<ContributionsListPropTypes> = ({
    hasAbacusSchedule,
    includeOnlyValidContributions,
}) => {
    const [contributionsList, setContributionsList] = useState<
        NrContribution[]
    >([]);
    const { contributorId, scheduleId } = useParams<{
        contributorId: string;
        scheduleId: string;
    }>();
    const filterValues: NrContributionFilter = {
        filters: {
            abacusScheduleId:
                hasAbacusSchedule && scheduleId
                    ? parseInt(scheduleId, 10)
                    : null,
            contributorId,
            hasAbacusSchedule,
            validContributions: includeOnlyValidContributions,
        },
        limit: 100,
        offset: 0,
        orderBy: sortByColumn['nrsrNameVersion'],
        orderDir: sortDirection['asc'],
    };
    const [noResultsMessage, setNoResultsMessage] = useState<string>('');
    const { data, loading, fetchMore } = useNRContributionsList(filterValues);

    const handleFetchMore = async (limit: number, offset: number) =>
        await fetchMore({ variables: { limit, offset } });

    useEffect(() => {
        if (data) {
            const contributions = data?.nrContributions?.items;
            setContributionsList([...contributions]);
        }
        setNoResultsMessage(
            `No ${hasAbacusSchedule ? 'Assigned' : 'Unassigned'} Contributions`
        );
    }, [data]);

    if (loading && isEmpty(contributionsList)) return <SkeletonLoader />;

    return (
        <>
            {isEmpty(contributionsList) ? (
                <span className="NoResultsFound">{noResultsMessage}</span>
            ) : (
                <InfiniteScroll
                    fetchMore={handleFetchMore}
                    loading={loading}
                    count={contributionsList?.length}
                    loadLimit={100}
                    totalLimit={data?.nrContributions?.totalCount}
                    totalResults={data?.nrContributions?.totalCount}
                    scrollContainerClassName={cx({
                        'ContributionsAssigned-list': hasAbacusSchedule,
                        'ContributionsUnassigned-list': !hasAbacusSchedule,
                    })}
                    loaderSize={true}
                >
                    {contributionsList &&
                        contributionsList?.map(
                            (contribution: NrContribution) => (
                                <div
                                    className={cx({
                                        'ContributionsAssigned-list-item':
                                            hasAbacusSchedule,
                                        'ContributionsUnassigned-list-item':
                                            !hasAbacusSchedule,
                                    })}
                                    data-testid="Contributions-list-item"
                                    key={contribution.id}
                                >
                                    {`${contribution?.nrSoundRecording?.recordingTitle} - ${contribution?.nrSoundRecording?.mainArtist}`}
                                    <br />
                                    <span className="ContributionLabel">
                                        {`${contribution?.id}`}
                                    </span>
                                </div>
                            )
                        )}
                </InfiniteScroll>
            )}
        </>
    );
};
