import React, { FC, useCallback, useMemo } from 'react';
import { formatMessage } from '@theorchard/suite-frontend';
import { DropdownOption } from 'src/components/dropdown';
import SearchableDropdown from 'src/components/searchableDropdown';
import { FILTER_DEBOUNCE } from 'src/constants';
import {
    useLazySoundRecordingSearchQuery, Song
} from 'src/data/queries';

export interface Props {
    disabled?: boolean;
    onChange: (data?: Song) => void
    song?: Song;
}

export const getOptionName = (song: Song) =>
    `${song.name} - ${song.isrc}`;

const getOptionSubtitle = (song: Song) => {
    const artistName = song.participants.map(({ name }) => name).join(', ');
    if (artistName)
        return (<span key={artistName}>{artistName} </span>);
    return '-';
};

const createOption = (song: Song): DropdownOption<Song> => ({
    label: getOptionName(song),
    value: song.id,
    data: song
});

const SoundRecordingSearch: FC<Props> = (props) => {
    const { onChange, disabled, song } = props;
    const [executeSearch, { data: searchData, loading }] = useLazySoundRecordingSearchQuery();

    const handleInputChange = useCallback((searchTerm: string) => {
        if (searchTerm)
            executeSearch({ term: searchTerm, limit: 20 });
    }, [executeSearch]);

    const handleClearable = (option?: DropdownOption) => Boolean(option?.value);

    const songOptions = useMemo<DropdownOption<Song>[]>(() => {
        const options = [
            ...searchData?.items ?? [],
        ].map(createOption);
        return options;
    }, [searchData?.items]);

    const handleChange = useCallback((songName?: string, value?: string, data?: Song) => {
        if (!value)
            executeSearch({ term: '' });
        onChange(data);
    }, [onChange, executeSearch]);

    let selectedOption;
    if (song?.name)
        selectedOption = createOption(song);

    const formatOptionLabel = (
        option: DropdownOption<Song>
    ) => (
        <div>
            <div className="SongSearchSource">
                {formatMessage('repertoire.source')}: {option.data?.source || 'The Orchard'}
            </div>
            <div className="SongSearchName">
                {option.label}
            </div>
            {option.data && (
                <div className="SongSearchSubtitle">
                    {getOptionSubtitle(option.data)}
                </div>
            )}
        </div>
    );

    const isLoading = loading && !searchData;

    return (
        <SearchableDropdown
            name="songSearch"
            className="SoundRecordingSearch"
            onChange={handleChange}
            onInputChange={handleInputChange}
            options={songOptions}
            disabled={disabled}
            debounceTimeout={FILTER_DEBOUNCE}
            selectedOption={selectedOption}
            clearable={handleClearable}
            hideIfEmpty={false}
            formatOptionLabel={formatOptionLabel}
            loading={isLoading}
            placeholder={formatMessage('repertoire.songSearch')}
        />
    );
};

export default SoundRecordingSearch;
