/**
 * Facets Component
 *
 * Displays facet filters for search results with multiple display variants,
 * client-side search, count badges, and color swatch support.
 */
import React, { useState, useMemo, useRef, useEffect } from 'react';
import { useSearchContext } from './SearchProvider';
import { useSearchState } from '../hooks/useSearchState';
import { useFilters } from '../hooks/useFilters';
import { log } from '@seekora-ai/ui-sdk-core';
import { clsx } from 'clsx';
import { RangeSlider } from './RangeSlider';
// ---------------------------------------------------------------------------
// Helpers
// ---------------------------------------------------------------------------
/** Generate a deterministic colour from a string (used as fallback for color-swatch). */
function stringToColor(str) {
    let hash = 0;
    for (let i = 0; i < str.length; i++) {
        hash = str.charCodeAt(i) + ((hash << 5) - hash);
        hash |= 0; // Convert to 32-bit int
    }
    const h = Math.abs(hash) % 360;
    return `hsl(${h}, 65%, 55%)`;
}
/** Return swatch pixel size from the size prop. */
function swatchSize(size) {
    switch (size) {
        case 'small':
            return 24;
        case 'large':
            return 40;
        case 'medium':
        default:
            return 32;
    }
}
// ---------------------------------------------------------------------------
// Chevron SVG icon for collapsible variant
// ---------------------------------------------------------------------------
const ChevronIcon = ({ expanded, color = 'currentColor', size = 16, }) => (React.createElement("svg", { width: size, height: size, viewBox: "0 0 16 16", fill: "none", xmlns: "http://www.w3.org/2000/svg", style: {
        transform: expanded ? 'rotate(180deg)' : 'rotate(0deg)',
        transition: 'transform 200ms ease',
        flexShrink: 0,
    }, "aria-hidden": "true" },
    React.createElement("path", { d: "M4 6L8 10L12 6", stroke: color, strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" })));
// ---------------------------------------------------------------------------
// Checkmark SVG for selected color swatches
// ---------------------------------------------------------------------------
const CheckmarkIcon = ({ size = 16 }) => (React.createElement("svg", { width: size, height: size, viewBox: "0 0 16 16", fill: "none", xmlns: "http://www.w3.org/2000/svg", "aria-hidden": "true" },
    React.createElement("path", { d: "M3.5 8.5L6.5 11.5L12.5 4.5", stroke: "#fff", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" })));
// ---------------------------------------------------------------------------
// CSS variable defaults
// ---------------------------------------------------------------------------
const CSS_VAR_DEFAULTS = {
    '--seekora-facet-bg': 'transparent',
    '--seekora-facet-border': '#dee2e6',
    '--seekora-facet-active-bg': 'rgba(0, 0, 0, 0.05)',
    '--seekora-facet-swatch-size': '32px',
    '--seekora-facet-count-bg': '#e9ecef',
    '--seekora-facet-count-color': '#495057',
    '--seekora-primary': '#3b82f6',
    '--seekora-primary-text': '#ffffff',
};
// ---------------------------------------------------------------------------
// Component
// ---------------------------------------------------------------------------
export const Facets = ({ results: resultsProp, facets: facetsProp, onFacetChange, renderFacet, renderFacetItem, maxItems = 10, showMore = true, className, style, theme: customTheme, variant = 'checkbox', searchable = false, showCounts = true, colorMap, defaultCollapsed = false, size = 'medium', facetRanges, useFiltersApi = false, disjunctiveFacets, hideEmptyFacets = true, defaultCollapsedFields, onFacetsAvailable, }) => {
    const { theme } = useSearchContext();
    const { results: stateResults, refinements, addRefinement, removeRefinement } = useSearchState();
    const facetsTheme = customTheme || {};
    // Use dedicated Filters API when useFiltersApi is enabled
    const { filters: filtersApiData, searchFacetValues } = useFilters(useFiltersApi ? { disjunctiveFacets } : { autoFetch: false });
    // expandedFacets is used for "Show more/less" in checkbox/color-swatch variants
    // AND for collapse/expand in collapsible variant.
    const [expandedFacets, setExpandedFacets] = useState({});
    const [searchTerms, setSearchTerms] = useState({});
    // Use results from prop if provided, otherwise from state manager
    const results = resultsProp || stateResults;
    // -------------------------------------------------------------------
    // Extract facets from results (or Filters API)
    // -------------------------------------------------------------------
    const extractFacets = () => {
        if (facetsProp)
            return facetsProp;
        // When using Filters API, convert FilterField[] to Facet[]
        if (useFiltersApi && filtersApiData.length > 0) {
            log.verbose('Facets: Using Filters API data', { filterCount: filtersApiData.length });
            return filtersApiData.map((filter) => ({
                field: filter.field || '',
                label: filter.field || '',
                items: (filter.values || []).map((v) => ({
                    value: v.value || '',
                    count: v.count || 0,
                    selected: refinements.some(r => r.field === filter.field && r.value === v.value),
                })),
                stats: filter.stats?.min != null && filter.stats?.max != null
                    ? { min: filter.stats.min, max: filter.stats.max, avg: filter.stats.avg, sum: filter.stats.sum }
                    : undefined,
            }));
        }
        // Try to get facets from various locations in the response
        // Primary location: data.facets (widget_mode response structure)
        const rawFacets = results?.data?.facets
            || results?.facets
            || results?.data?.data?.facets
            || null;
        log.verbose('Facets: Extracting facets', {
            hasResults: !!results,
            hasData: !!results?.data,
            rawFacets: rawFacets ? (Array.isArray(rawFacets) ? rawFacets.length : 'not array') : null,
            resultsKeys: results ? Object.keys(results) : [],
            dataKeys: results?.data ? Object.keys(results.data) : [],
            sampleFacet: rawFacets && Array.isArray(rawFacets) && rawFacets.length > 0 ? rawFacets[0] : null,
        });
        // Ensure rawFacets is an array before mapping
        if (!rawFacets || !Array.isArray(rawFacets)) {
            log.verbose('Facets: No facets found in response', {
                rawFacetsType: rawFacets ? typeof rawFacets : 'null',
                isArray: Array.isArray(rawFacets),
                resultsStructure: results ? JSON.stringify(Object.keys(results)) : 'null',
                dataStructure: results?.data ? JSON.stringify(Object.keys(results.data)) : 'null',
            });
            return [];
        }
        const extracted = rawFacets.map((facet) => {
            const fieldName = facet.field_name || facet.field;
            return {
                field: fieldName,
                label: facet.label || fieldName,
                items: Array.isArray(facet.counts) ? facet.counts.map((count) => ({
                    value: count.value,
                    count: count.count,
                    selected: refinements.some(r => r.field === fieldName && r.value === count.value),
                })) : [],
                stats: facet.stats || undefined,
            };
        });
        log.verbose('Facets: Extracted facets', {
            count: extracted.length,
            facets: extracted.map(f => ({ field: f.field, itemsCount: f.items.length })),
        });
        return extracted;
    };
    const rawFacetList = extractFacets();
    const hasStats = (stats) => stats != null && (stats.min != null || stats.max != null);
    const facets = hideEmptyFacets
        ? rawFacetList.filter(f => f.items.length > 0 || hasStats(f.stats))
        : rawFacetList;
    // Notify parent about facet availability
    const facetCount = facets.length;
    const prevFacetAvailableRef = useRef(null);
    useEffect(() => {
        if (!onFacetsAvailable)
            return;
        const available = facetCount > 0;
        if (prevFacetAvailableRef.current !== available) {
            prevFacetAvailableRef.current = available;
            onFacetsAvailable(available);
        }
    }, [facetCount, onFacetsAvailable]);
    // -------------------------------------------------------------------
    // Handlers
    // -------------------------------------------------------------------
    const handleFacetToggle = (field, value, selected) => {
        const newSelected = !selected;
        log.verbose('Facets: Facet toggled', { field, value, selected: newSelected });
        // Update state manager (automatically triggers search)
        if (newSelected) {
            addRefinement(field, value);
        }
        else {
            removeRefinement(field, value);
        }
        // Call callback for backwards compatibility
        if (onFacetChange) {
            try {
                onFacetChange(field, value, newSelected);
            }
            catch (err) {
                const error = err instanceof Error ? err : new Error(String(err));
                log.error('Facets: Error in onFacetChange callback', {
                    field,
                    value,
                    selected: newSelected,
                    error: error.message,
                });
            }
        }
    };
    const toggleFacetExpansion = (field) => {
        setExpandedFacets((prev) => ({
            ...prev,
            [field]: !prev[field],
        }));
    };
    /** For collapsible variant — determine if a facet group is open. */
    const isFieldDefaultCollapsed = (field) => {
        if (defaultCollapsedFields?.includes(field))
            return true;
        return defaultCollapsed;
    };
    const isFacetGroupOpen = (field) => {
        if (field in expandedFacets) {
            return expandedFacets[field];
        }
        return !isFieldDefaultCollapsed(field);
    };
    const toggleCollapsible = (field) => {
        setExpandedFacets((prev) => ({
            ...prev,
            [field]: !(prev[field] ?? !isFieldDefaultCollapsed(field)),
        }));
    };
    const getSearchTerm = (field) => searchTerms[field] || '';
    const setSearchTerm = (field, term) => {
        setSearchTerms((prev) => ({ ...prev, [field]: term }));
    };
    /** Filter facet items by search term. */
    const filterItems = (items, field) => {
        if (!searchable)
            return items;
        const term = getSearchTerm(field).toLowerCase();
        if (!term)
            return items;
        return items.filter((item) => item.value.toLowerCase().includes(term));
    };
    // -------------------------------------------------------------------
    // Size helpers
    // -------------------------------------------------------------------
    const sizeScale = useMemo(() => {
        switch (size) {
            case 'small':
                return { font: theme.typography.fontSize.small, padding: '0.5rem', gap: '0.5rem' };
            case 'large':
                return { font: theme.typography.fontSize.large, padding: '0.75rem', gap: '0.75rem' };
            case 'medium':
            default:
                return { font: theme.typography.fontSize.medium, padding: theme.spacing.small, gap: theme.spacing.small };
        }
    }, [size, theme]);
    // -------------------------------------------------------------------
    // Count badge renderer
    // -------------------------------------------------------------------
    const renderCountBadge = (count) => {
        if (!showCounts)
            return null;
        return (React.createElement("span", { className: clsx(facetsTheme.countBadge), style: {
                display: 'inline-flex',
                alignItems: 'center',
                justifyContent: 'center',
                minWidth: '1.5em',
                padding: '0.1em 0.5em',
                marginLeft: sizeScale.gap,
                fontSize: theme.typography.fontSize.small,
                fontWeight: theme.typography.fontWeight?.medium ?? 500,
                lineHeight: 1,
                color: 'var(--seekora-facet-count-color, #495057)',
                backgroundColor: 'var(--seekora-facet-count-bg, #e9ecef)',
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.full,
                flexShrink: 0,
            } }, count));
    };
    // -------------------------------------------------------------------
    // Search input renderer
    // -------------------------------------------------------------------
    const renderSearchInput = (facet) => {
        if (!searchable)
            return null;
        return (React.createElement("input", { type: "text", value: getSearchTerm(facet.field), onChange: (e) => setSearchTerm(facet.field, e.target.value), placeholder: `Search ${facet.label || facet.field}...`, className: clsx(facetsTheme.searchInput), "aria-label": `Search within ${facet.label || facet.field}`, style: {
                width: '100%',
                boxSizing: 'border-box',
                padding: sizeScale.padding,
                marginBottom: sizeScale.gap,
                fontSize: theme.typography.fontSize.small,
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.small,
                outline: 'none',
                color: theme.colors.text,
                backgroundColor: 'var(--seekora-facet-bg, transparent)',
            } }));
    };
    // -------------------------------------------------------------------
    // Checkbox variant item renderer (original behaviour, preserved)
    // -------------------------------------------------------------------
    const defaultRenderFacetItem = (item, facet, index) => {
        const isExpanded = expandedFacets[facet.field] || index < maxItems;
        if (!isExpanded && index >= maxItems) {
            return null;
        }
        const isChecked = refinements.some(r => r.field === facet.field && r.value === item.value) || item.selected || false;
        return (React.createElement("div", { key: `${facet.field}-${item.value}`, className: clsx(facetsTheme.facetItem, isChecked && facetsTheme.facetItemActive), role: "option", "aria-selected": isChecked, "aria-checked": isChecked, tabIndex: -1, onClick: () => handleFacetToggle(facet.field, item.value, item.selected || false), style: {
                display: 'flex',
                alignItems: 'center',
                padding: sizeScale.padding,
                cursor: 'pointer',
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
                marginBottom: sizeScale.gap,
                backgroundColor: isChecked
                    ? 'var(--seekora-facet-active-bg, ' + theme.colors.hover + ')'
                    : 'transparent',
                transition: 'background-color 0.2s ease',
                boxSizing: 'border-box',
            } },
            React.createElement("input", { type: "checkbox", checked: refinements.some(r => r.field === facet.field && r.value === item.value) || item.selected || false, onChange: () => handleFacetToggle(facet.field, item.value, item.selected || false), className: facetsTheme.checkbox, style: {
                    marginRight: sizeScale.gap,
                    cursor: 'pointer',
                }, "aria-label": `Filter by ${item.value}` }),
            React.createElement("span", { className: facetsTheme.facetItemLabel, style: {
                    flex: 1,
                    fontSize: sizeScale.font,
                    lineHeight: 1.5,
                    color: theme.colors.text,
                } }, item.value),
            renderCountBadge(item.count)));
    };
    // -------------------------------------------------------------------
    // Color swatch variant item renderer
    // -------------------------------------------------------------------
    const renderColorSwatchItem = (item, facet, index) => {
        const isExpanded = expandedFacets[facet.field] || index < maxItems;
        if (!isExpanded && index >= maxItems) {
            return null;
        }
        const isChecked = refinements.some(r => r.field === facet.field && r.value === item.value) || item.selected || false;
        const color = colorMap?.[item.value] ?? stringToColor(item.value);
        const pxSize = swatchSize(size);
        return (React.createElement("div", { key: `${facet.field}-${item.value}`, className: clsx(facetsTheme.facetItem, isChecked && facetsTheme.facetItemActive), role: "option", "aria-selected": isChecked, "aria-checked": isChecked, tabIndex: -1, onClick: () => handleFacetToggle(facet.field, item.value, item.selected || false), title: `${item.value}${showCounts ? ` (${item.count})` : ''}`, style: {
                display: 'inline-flex',
                flexDirection: 'column',
                alignItems: 'center',
                cursor: 'pointer',
                margin: sizeScale.gap,
            } },
            React.createElement("div", { className: clsx(facetsTheme.colorSwatch, isChecked && facetsTheme.colorSwatchSelected), style: {
                    width: `var(--seekora-facet-swatch-size, ${pxSize}px)`,
                    height: `var(--seekora-facet-swatch-size, ${pxSize}px)`,
                    borderRadius: '50%',
                    backgroundColor: color,
                    border: isChecked
                        ? `3px solid var(--seekora-primary, ${theme.colors.primary})`
                        : `2px solid var(--seekora-facet-border, ${theme.colors.border})`,
                    display: 'flex',
                    alignItems: 'center',
                    justifyContent: 'center',
                    transition: 'border 0.2s ease, box-shadow 0.2s ease',
                    boxShadow: isChecked ? `0 0 0 2px var(--seekora-primary-alpha, ${theme.colors.primary}33)` : 'none',
                    position: 'relative',
                } }, isChecked && (React.createElement("span", { className: clsx(facetsTheme.colorSwatchInner), style: {
                    display: 'flex',
                    alignItems: 'center',
                    justifyContent: 'center',
                } },
                React.createElement(CheckmarkIcon, { size: Math.round(pxSize * 0.5) })))),
            React.createElement("span", { className: facetsTheme.facetItemLabel, style: {
                    fontSize: theme.typography.fontSize.small,
                    color: theme.colors.text,
                    marginTop: '0.25rem',
                    textAlign: 'center',
                    maxWidth: `${pxSize + 16}px`,
                    overflow: 'hidden',
                    textOverflow: 'ellipsis',
                    whiteSpace: 'nowrap',
                } }, item.value),
            showCounts && (React.createElement("span", { className: clsx(facetsTheme.countBadge), style: {
                    fontSize: theme.typography.fontSize.small,
                    color: 'var(--seekora-facet-count-color, ' + (theme.colors.textSecondary || theme.colors.text) + ')',
                    lineHeight: 1,
                    marginTop: '0.125rem',
                } }, item.count))));
    };
    // -------------------------------------------------------------------
    // Item renderer dispatcher
    // -------------------------------------------------------------------
    const renderItem = (item, facet, index) => {
        if (renderFacetItem) {
            return renderFacetItem(item, facet, index);
        }
        switch (variant) {
            case 'color-swatch':
                return renderColorSwatchItem(item, facet, index);
            case 'collapsible':
            case 'checkbox':
            default:
                return defaultRenderFacetItem(item, facet, index);
        }
    };
    // -------------------------------------------------------------------
    // Keyboard handler (shared across variants)
    // -------------------------------------------------------------------
    const handleListKeyDown = (e, visibleItems, facet) => {
        const currentEl = e.currentTarget.querySelector('[aria-selected="true"]');
        const allItems = Array.from(e.currentTarget.querySelectorAll('[role="option"]'));
        const currentIdx = currentEl ? allItems.indexOf(currentEl) : -1;
        if (e.key === 'ArrowDown') {
            e.preventDefault();
            const next = Math.min(currentIdx + 1, allItems.length - 1);
            allItems[next]?.focus();
        }
        else if (e.key === 'ArrowUp') {
            e.preventDefault();
            const prev = Math.max(currentIdx - 1, 0);
            allItems[prev]?.focus();
        }
        else if (e.key === 'Enter' || e.key === ' ') {
            e.preventDefault();
            if (currentIdx >= 0 && currentIdx < visibleItems.length) {
                handleFacetToggle(facet.field, visibleItems[currentIdx].value, visibleItems[currentIdx].selected || false);
            }
        }
    };
    // -------------------------------------------------------------------
    // Show more / less buttons (shared)
    // -------------------------------------------------------------------
    const renderShowMoreLess = (facet, filteredItems) => {
        const isExpanded = expandedFacets[facet.field] || false;
        const hasMore = filteredItems.length > maxItems;
        return (React.createElement(React.Fragment, null,
            showMore && hasMore && !isExpanded && (React.createElement("button", { type: "button", onClick: () => toggleFacetExpansion(facet.field), style: {
                    marginTop: sizeScale.gap,
                    padding: sizeScale.padding,
                    border: 'none',
                    backgroundColor: 'transparent',
                    color: theme.colors.primary,
                    cursor: 'pointer',
                    fontSize: theme.typography.fontSize.small,
                    textDecoration: 'underline',
                } },
                "Show more (",
                filteredItems.length - maxItems,
                " more)")),
            isExpanded && hasMore && (React.createElement("button", { type: "button", onClick: () => toggleFacetExpansion(facet.field), style: {
                    marginTop: sizeScale.gap,
                    padding: sizeScale.padding,
                    border: 'none',
                    backgroundColor: 'transparent',
                    color: theme.colors.primary,
                    cursor: 'pointer',
                    fontSize: theme.typography.fontSize.small,
                    textDecoration: 'underline',
                } }, "Show less"))));
    };
    // -------------------------------------------------------------------
    // Default facet group renderer — Checkbox variant
    // -------------------------------------------------------------------
    const renderCheckboxFacet = (facet, _index) => {
        const filteredItems = filterItems(facet.items, facet.field);
        const isExpanded = expandedFacets[facet.field] || false;
        const visibleItems = isExpanded ? filteredItems : filteredItems.slice(0, maxItems);
        return (React.createElement("div", { key: facet.field, className: facetsTheme.facet, style: {
                marginBottom: theme.spacing.large,
                padding: theme.spacing.medium,
                backgroundColor: 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
            } },
            React.createElement("h3", { className: facetsTheme.facetTitle, style: {
                    margin: 0,
                    marginBottom: theme.spacing.medium,
                    color: theme.colors.text,
                } }, facet.label || facet.field),
            renderSearchInput(facet),
            React.createElement("div", { className: facetsTheme.facetList, role: "listbox", "aria-label": `${facet.label || facet.field} filters`, tabIndex: 0, onKeyDown: (e) => handleListKeyDown(e, visibleItems, facet) }, visibleItems.map((item, itemIndex) => renderItem(item, facet, itemIndex))),
            renderShowMoreLess(facet, filteredItems)));
    };
    // -------------------------------------------------------------------
    // Color-swatch facet group renderer
    // -------------------------------------------------------------------
    const renderColorSwatchFacet = (facet, _index) => {
        const filteredItems = filterItems(facet.items, facet.field);
        const isExpanded = expandedFacets[facet.field] || false;
        const visibleItems = isExpanded ? filteredItems : filteredItems.slice(0, maxItems);
        return (React.createElement("div", { key: facet.field, className: facetsTheme.facet, style: {
                marginBottom: theme.spacing.large,
                padding: theme.spacing.medium,
                backgroundColor: 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
            } },
            React.createElement("h3", { className: facetsTheme.facetTitle, style: {
                    margin: 0,
                    marginBottom: theme.spacing.medium,
                    color: theme.colors.text,
                } }, facet.label || facet.field),
            renderSearchInput(facet),
            React.createElement("div", { className: facetsTheme.facetList, role: "listbox", "aria-label": `${facet.label || facet.field} filters`, tabIndex: 0, onKeyDown: (e) => handleListKeyDown(e, visibleItems, facet), style: {
                    display: 'flex',
                    flexWrap: 'wrap',
                    gap: sizeScale.gap,
                } }, visibleItems.map((item, itemIndex) => renderItem(item, facet, itemIndex))),
            renderShowMoreLess(facet, filteredItems)));
    };
    // -------------------------------------------------------------------
    // Collapsible facet group renderer
    // -------------------------------------------------------------------
    const renderCollapsibleFacet = (facet, _index) => {
        const isOpen = isFacetGroupOpen(facet.field);
        const filteredItems = filterItems(facet.items, facet.field);
        const isItemsExpanded = expandedFacets[facet.field] || false;
        // Note: For collapsible, the expandedFacets state controls the collapse/expand
        // of the group itself. We use a separate concept for Show more/less within items.
        // To avoid collision, Show more/less for collapsible uses the same expandedFacets
        // key prefixed with `_items_`.
        const isShowMoreExpanded = expandedFacets[`_items_${facet.field}`] || false;
        const visibleItems = isShowMoreExpanded ? filteredItems : filteredItems.slice(0, maxItems);
        const hasMore = filteredItems.length > maxItems;
        return (React.createElement("div", { key: facet.field, className: facetsTheme.facet, style: {
                marginBottom: theme.spacing.large,
                backgroundColor: 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
                overflow: 'hidden',
            } },
            React.createElement("button", { type: "button", className: clsx(facetsTheme.collapsibleHeader), onClick: () => toggleCollapsible(facet.field), "aria-expanded": isOpen, "aria-controls": `facet-group-${facet.field}`, style: {
                    display: 'flex',
                    alignItems: 'center',
                    justifyContent: 'space-between',
                    width: '100%',
                    padding: theme.spacing.medium,
                    border: 'none',
                    backgroundColor: 'transparent',
                    cursor: 'pointer',
                    textAlign: 'left',
                } },
                React.createElement("span", { className: facetsTheme.facetTitle, style: {
                        color: theme.colors.text,
                        flex: 1,
                    } }, facet.label || facet.field),
                React.createElement("span", { className: clsx(facetsTheme.collapsibleIcon) },
                    React.createElement(ChevronIcon, { expanded: isOpen, color: theme.colors.textSecondary || theme.colors.text }))),
            isOpen && (React.createElement("div", { id: `facet-group-${facet.field}`, style: {
                    padding: `0 ${theme.spacing.medium} ${theme.spacing.medium}`,
                } },
                renderSearchInput(facet),
                React.createElement("div", { className: facetsTheme.facetList, role: "listbox", "aria-label": `${facet.label || facet.field} filters`, tabIndex: 0, onKeyDown: (e) => handleListKeyDown(e, visibleItems, facet) }, visibleItems.map((item, itemIndex) => renderItem(item, facet, itemIndex))),
                showMore && hasMore && !isShowMoreExpanded && (React.createElement("button", { type: "button", onClick: () => setExpandedFacets((prev) => ({
                        ...prev,
                        [`_items_${facet.field}`]: true,
                    })), style: {
                        marginTop: sizeScale.gap,
                        padding: sizeScale.padding,
                        border: 'none',
                        backgroundColor: 'transparent',
                        color: theme.colors.primary,
                        cursor: 'pointer',
                        fontSize: theme.typography.fontSize.small,
                        textDecoration: 'underline',
                    } },
                    "Show more (",
                    filteredItems.length - maxItems,
                    " more)")),
                isShowMoreExpanded && hasMore && (React.createElement("button", { type: "button", onClick: () => setExpandedFacets((prev) => ({
                        ...prev,
                        [`_items_${facet.field}`]: false,
                    })), style: {
                        marginTop: sizeScale.gap,
                        padding: sizeScale.padding,
                        border: 'none',
                        backgroundColor: 'transparent',
                        color: theme.colors.primary,
                        cursor: 'pointer',
                        fontSize: theme.typography.fontSize.small,
                        textDecoration: 'underline',
                    } }, "Show less"))))));
    };
    // -------------------------------------------------------------------
    // Render-type detection for numeric / range facets
    // -------------------------------------------------------------------
    const determineFacetRenderType = (fieldName, stats) => {
        // If explicit range config exists for this field → range buttons
        if (facetRanges?.some((rc) => rc.field === fieldName)) {
            return 'range-buttons';
        }
        // If stats with valid min/max → range slider
        if (stats && typeof stats.min === 'number' && typeof stats.max === 'number' && stats.min !== stats.max) {
            return 'range-slider';
        }
        return 'list';
    };
    // -------------------------------------------------------------------
    // Range button facet renderer
    // -------------------------------------------------------------------
    const renderRangeButtonFacet = (facet, _index) => {
        const rangeConfig = facetRanges?.find((rc) => rc.field === facet.field);
        if (!rangeConfig)
            return null;
        // Build a lookup from item value → count
        const countMap = new Map();
        facet.items.forEach((item) => countMap.set(item.value, item.count));
        // Detect currently active range from refinements
        const activeMin = refinements.find((r) => r.field === facet.field && r.value.startsWith('>='));
        const activeMax = refinements.find((r) => r.field === facet.field && r.value.startsWith('<='));
        const activeFromVal = activeMin ? parseFloat(activeMin.value.slice(2)) : undefined;
        const activeToVal = activeMax ? parseFloat(activeMax.value.slice(2)) : undefined;
        const isRangeActive = (range) => {
            const fromMatch = range.from === undefined
                ? activeFromVal === undefined
                : activeFromVal === range.from;
            const toMatch = range.to === undefined
                ? activeToVal === undefined
                : activeToVal === range.to;
            return fromMatch && toMatch;
        };
        const handleRangeClick = (range) => {
            // Clear existing range refinements for this field
            refinements
                .filter((r) => r.field === facet.field)
                .forEach((r) => removeRefinement(facet.field, r.value, false));
            if (isRangeActive(range)) {
                // Was active → just clear (already removed above), trigger search
                addRefinement(facet.field, '__noop__', false);
                removeRefinement(facet.field, '__noop__', true);
                return;
            }
            // Set new range
            if (range.from !== undefined) {
                addRefinement(facet.field, `>=${range.from}`, false);
            }
            if (range.to !== undefined) {
                addRefinement(facet.field, `<=${range.to}`, true);
            }
            else if (range.from !== undefined) {
                // Only "from" set — trigger search
                addRefinement(facet.field, `>=${range.from}`, true);
            }
        };
        const hasActiveRange = activeMin !== undefined || activeMax !== undefined;
        const handleClear = () => {
            refinements
                .filter((r) => r.field === facet.field)
                .forEach((r) => removeRefinement(facet.field, r.value, false));
            // Trigger search after clearing
            addRefinement(facet.field, '__noop__', false);
            removeRefinement(facet.field, '__noop__', true);
        };
        return (React.createElement("div", { key: facet.field, className: facetsTheme.facet, style: {
                marginBottom: theme.spacing.large,
                padding: theme.spacing.medium,
                backgroundColor: 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
            } },
            React.createElement("h3", { className: facetsTheme.facetTitle, style: {
                    margin: 0,
                    marginBottom: theme.spacing.medium,
                    color: theme.colors.text,
                } }, facet.label || facet.field),
            React.createElement("div", { style: {
                    display: 'flex',
                    flexWrap: 'wrap',
                    gap: sizeScale.gap,
                } }, rangeConfig.ranges.map((range) => {
                const count = countMap.get(range.label) ?? 0;
                const active = isRangeActive(range);
                return (React.createElement("button", { key: range.label, type: "button", className: clsx(facetsTheme.rangeButton, active && facetsTheme.rangeButtonActive), disabled: count === 0 && !active, onClick: () => handleRangeClick(range), style: {
                        display: 'inline-flex',
                        alignItems: 'center',
                        gap: '0.35em',
                        padding: `${sizeScale.padding} 0.75em`,
                        fontSize: sizeScale.font,
                        border: `1px solid ${active ? 'var(--seekora-primary, ' + theme.colors.primary + ')' : 'var(--seekora-facet-border, ' + theme.colors.border + ')'}`,
                        borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.full,
                        backgroundColor: active ? 'var(--seekora-primary, ' + theme.colors.primary + ')' : 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                        color: active ? 'var(--seekora-primary-text, #fff)' : theme.colors.text,
                        cursor: count === 0 && !active ? 'not-allowed' : 'pointer',
                        opacity: count === 0 && !active ? 0.5 : 1,
                        transition: 'all 0.2s ease',
                    } },
                    range.label,
                    showCounts && (React.createElement("span", { className: clsx(facetsTheme.rangeButtonCount), style: {
                            fontSize: theme.typography.fontSize.small,
                            opacity: 0.8,
                        } },
                        "(",
                        count,
                        ")"))));
            })),
            hasActiveRange && (React.createElement("button", { type: "button", className: clsx(facetsTheme.rangeClear), onClick: handleClear, style: {
                    marginTop: sizeScale.gap,
                    padding: sizeScale.padding,
                    border: 'none',
                    backgroundColor: 'transparent',
                    color: theme.colors.primary,
                    cursor: 'pointer',
                    fontSize: theme.typography.fontSize.small,
                    textDecoration: 'underline',
                } }, "Clear"))));
    };
    // -------------------------------------------------------------------
    // Range slider facet renderer
    // -------------------------------------------------------------------
    const renderRangeSliderFacet = (facet, _index) => {
        if (!facet.stats)
            return null;
        const { min: statsMin, max: statsMax } = facet.stats;
        // Auto-detect formatting for common field names
        const fieldLower = facet.field.toLowerCase();
        const isPriceField = fieldLower.includes('price') || fieldLower.includes('cost') || fieldLower.includes('amount');
        const formatValue = isPriceField
            ? (v) => `$${v.toFixed(2)}`
            : (v) => v.toString();
        // Determine step: use 0.01 for price, 1 for integer ranges, 0.1 otherwise
        const range = statsMax - statsMin;
        const step = isPriceField ? 0.01 : range > 10 ? 1 : 0.1;
        // Check if there's an active range refinement
        const hasActiveRange = refinements.some((r) => r.field === facet.field && (r.value.startsWith('>=') || r.value.startsWith('<=')));
        const handleClear = () => {
            refinements
                .filter((r) => r.field === facet.field && (r.value.startsWith('>=') || r.value.startsWith('<=')))
                .forEach((r) => removeRefinement(facet.field, r.value, false));
            // Trigger search after clearing
            addRefinement(facet.field, '__noop__', false);
            removeRefinement(facet.field, '__noop__', true);
        };
        return (React.createElement("div", { key: facet.field, className: facetsTheme.facet, style: {
                marginBottom: theme.spacing.large,
                padding: theme.spacing.medium,
                backgroundColor: 'var(--seekora-facet-bg, ' + theme.colors.background + ')',
                border: `1px solid var(--seekora-facet-border, ${theme.colors.border})`,
                borderRadius: typeof theme.borderRadius === 'string' ? theme.borderRadius : theme.borderRadius.medium,
            } },
            React.createElement("div", { style: { display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: theme.spacing.small } },
                React.createElement("h3", { className: facetsTheme.facetTitle, style: {
                        margin: 0,
                        color: theme.colors.text,
                    } }, facet.label || facet.field),
                hasActiveRange && (React.createElement("button", { type: "button", className: clsx(facetsTheme.rangeClear), onClick: handleClear, style: {
                        padding: '0.15em 0.5em',
                        border: 'none',
                        backgroundColor: 'transparent',
                        color: theme.colors.primary,
                        cursor: 'pointer',
                        fontSize: theme.typography.fontSize.small,
                        textDecoration: 'underline',
                    } }, "Clear"))),
            React.createElement(RangeSlider, { field: facet.field, min: statsMin, max: statsMax, step: step, formatValue: formatValue, syncWithState: true })));
    };
    // -------------------------------------------------------------------
    // Default facet renderer dispatcher
    // -------------------------------------------------------------------
    const defaultRenderFacet = (facet, index) => {
        const renderType = determineFacetRenderType(facet.field, facet.stats);
        if (renderType === 'range-buttons') {
            return renderRangeButtonFacet(facet, index);
        }
        if (renderType === 'range-slider') {
            return renderRangeSliderFacet(facet, index);
        }
        switch (variant) {
            case 'color-swatch':
                return renderColorSwatchFacet(facet, index);
            case 'collapsible':
                return renderCollapsibleFacet(facet, index);
            case 'checkbox':
            default:
                return renderCheckboxFacet(facet, index);
        }
    };
    // -------------------------------------------------------------------
    // Empty state
    // -------------------------------------------------------------------
    if (facets.length === 0) {
        log.verbose('Facets: No facets to display', {
            hasResults: !!results,
            resultsType: results ? typeof results : 'null',
        });
        // Return a placeholder instead of null for debugging
        if (process.env.NODE_ENV === 'development') {
            return (React.createElement("div", { style: { padding: theme.spacing.small, color: theme.colors.textSecondary, fontSize: theme.typography.fontSize.small } }, "No facets available"));
        }
        return null;
    }
    // -------------------------------------------------------------------
    // Render
    // -------------------------------------------------------------------
    return (React.createElement("div", { className: clsx(facetsTheme.container, className), style: {
            ...CSS_VAR_DEFAULTS,
            ...style,
        } }, facets.map((facet, index) => {
        return renderFacet
            ? renderFacet(facet, index)
            : defaultRenderFacet(facet, index);
    })));
};
