/**
 * WordPress dependencies
 */
import { CheckboxControl } from '@safe-wordpress/components';
import { useState } from '@safe-wordpress/element';
import { _x } from '@safe-wordpress/i18n';
import {
	select as doSelect,
	useDispatch,
	useSelect,
} from '@safe-wordpress/data';

/**
 * External dependencies
 */
import clsx from 'clsx';
import { filter, map } from 'lodash';
import { PostSearcher } from '@nab/components';
import { createAlternative } from '@nab/utils';

import type { PostSearcherProps } from '@nab/components';
import type { Alternative, ExperimentEditProps } from '@nab/types';

// NOTE. Dependency loop with @nab package.
import type { store as editorStore } from '@nab/editor';
const NAB_EDITOR = 'nab/editor' as unknown as typeof editorStore;

/**
 * Internal dependencies
 */
import './style.scss';
import type { ControlAttributes as Attributes } from '../../types';

export type OriginalProps = ExperimentEditProps< Attributes > & {
	readonly disableExistingContentSelect?: boolean;
	readonly validPostFilter?: PostSearcherProps[ 'filter' ];
};

export const Original = ( {
	attributes,
	setAttributes,
	disableExistingContentSelect,
	validPostFilter,
}: OriginalProps ): JSX.Element => {
	const isPaused = useIsPaused();
	const toggleExistingContent = useExistingContentToggler( setAttributes );

	return (
		<div className="nab-original-pattern-alternative">
			<div className="nab-original-pattern-alternative__selector">
				<PostSearcher
					type="wp_block"
					value={ attributes.patternId }
					perPage={ 10 }
					onChange={ ( value ) =>
						// @ts-expect-error Pattern ID has the proper type already.
						setAttributes( { patternId: value } )
					}
					filter={ validPostFilter }
					placeholder={ _x(
						'Select a pattern…',
						'user',
						'nelio-ab-testing'
					) }
				/>
			</div>
			{ ! disableExistingContentSelect && (
				<div
					className={ clsx( {
						'nab-original-pattern-alternative__existing-content':
							true,
						'nab-original-pattern-alternative__existing-content--is-disabled':
							isPaused,
					} ) }
				>
					<CheckboxControl
						label={ _x(
							'Test against already existing patterns',
							'command',
							'nelio-ab-testing'
						) }
						disabled={ isPaused }
						checked={ !! attributes.testAgainstExistingPatterns }
						onChange={ toggleExistingContent }
					/>
				</div>
			) }
		</div>
	);
};

// =====
// HOOKS
// =====

const useIsPaused = () =>
	useSelect(
		( select ) =>
			`${ select( NAB_EDITOR ).getExperimentAttribute(
				'status'
			) }`.includes( 'paused' ),
		[]
	);

const useExistingContentToggler = (
	setAttributes: (
		props: Partial< Pick< Attributes, 'testAgainstExistingPatterns' > >
	) => void
) => {
	const [ prevAlts, setPrevAlts ] = useState( [ createAlternative() ] );
	const { replaceAlternatives } = useDispatch( NAB_EDITOR );
	return ( checked: boolean ) => {
		const alts = filter(
			doSelect( NAB_EDITOR ).getAlternatives(),
			( { id }: Alternative ) => 'control' !== id
		);
		void replaceAlternatives( map( alts, 'id' ), prevAlts );
		setPrevAlts( alts );
		setAttributes( {
			testAgainstExistingPatterns: checked ? true : undefined,
		} );
	};
};
