/** * WordPress dependencies */ import { BaseControl, ExternalLink, SelectControl, TextControl, ToggleControl, } from '@safe-wordpress/components'; import { useInstanceId } from '@safe-wordpress/compose'; import { useSelect } from '@safe-wordpress/data'; import { createInterpolateElement, useCallback, useEffect, } from '@safe-wordpress/element'; import { _x } from '@safe-wordpress/i18n'; /** * External dependencies */ import clsx from 'clsx'; import { sortBy, trim } from 'lodash'; import { ErrorText, PostSearcher } from '@nab/components'; import { store as NAB_DATA } from '@nab/data'; import { EMPTY_ARRAY } from '@nab/utils'; import type { CAEditProps, EntityId, EntityKindName } from '@nab/types'; /** * Internal dependencies */ import type { Attributes } from './types'; export const Edit = ( props: CAEditProps< Attributes > ): JSX.Element => ( <> { props.attributes.mode === 'id' ? ( ) : ( ) } { props.setAttributes( { mode: enabled ? 'url' : 'id' } ); props.setScope( enabled ? { type: 'urls', regexes: [ props.attributes.url ] } : { type: 'post-ids', ids: [ props.attributes.postId ] } ); } } /> ); // ============ // HELPER VIEWS // ============ const EditPostId = ( { attributes: { postId, postType }, setAttributes, setScope, errors, }: CAEditProps< Attributes > ): JSX.Element | null => { const instanceId = useInstanceId( Edit ); const { value: postTypes, isLoading } = usePostTypes(); const currentPostType = postType || postTypes[ 0 ]?.value; const setAttributesAndScope = useCallback( ( attrs: Partial< Attributes > ) => { setAttributes( attrs ); setScope( { type: 'post-ids', ids: attrs.postType && attrs.postId ? [ attrs.postId ] : [], } ); }, [ setAttributes, setScope ] ); const hasPostType = postTypes.map( ( t ) => t.value ).includes( postType ); useEffect( () => { if ( isLoading || hasPostType ) { return; } setAttributesAndScope( { postType: 'page', postId: 0 } ); }, [ postType, hasPostType, isLoading, setAttributesAndScope ] ); if ( isLoading ) { return null; } return ( <> { postTypes.length > 1 && ( setAttributesAndScope( { postType: newPostType, postId: undefined, } ) } /> ) } } help={ } > setAttributesAndScope( { postId: newPostId, postType: currentPostType, } ) } /> ); }; const EditUrl = ( { attributes: { url }, setAttributes, setScope, errors, }: CAEditProps< Attributes > ): JSX.Element => ( <> { setAttributes( { url: trim( value ) } ); setScope( { type: 'urls', regexes: trim( value ) ? [ trim( value ) ] : [], } ); } } help={ } /> ); const Label = ( { postType, postId, }: { postType: EntityKindName; postId: EntityId; } ) => { const permalink = usePostPermalink( postType, postId ); if ( ! permalink ) { return ( { _x( 'Actual Content', 'text', 'nelio-ab-testing' ) } ); } return ( { createInterpolateElement( _x( 'Actual Content (View)', 'text', 'nelio-ab-testing' ), { a: permalink ? ( // @ts-expect-error children prop is set by createInterpolateComponent. ) : ( ), } ) } ); }; // ===== // HOOKS // ===== const EXCLUDED_POST_TYPES = [ 'attachment', 'product_variation' ]; const usePostTypes = () => { const { entities, isLoading } = useSelect( ( select ) => ( { entities: select( NAB_DATA ).getKindEntities() || EMPTY_ARRAY, isLoading: ! select( NAB_DATA ).hasFinishedResolution( 'getKindEntities' ) && ! select( NAB_DATA ).hasResolutionFailed( 'getKindEntities' ), } ), [] ); const postTypes = entities .filter( ( pt ) => 'entity' === pt.kind && ! EXCLUDED_POST_TYPES.includes( pt.name ) ) .map( ( pt ) => ( { value: pt.name, label: pt.labels.singular_name, } ) ); return { value: sortBy( postTypes, 'label' ), isLoading, }; }; const usePostPermalink = ( postType: EntityKindName, postId: EntityId ) => useSelect( ( select ) => select( NAB_DATA ).getEntityRecord( postType, postId )?.link, [ postType, postId ] );