import { ref, computed, watch } from "vue"; import { useSharedState } from "../../sharedState/composables/useSharedState"; import { useSearchStateManager } from "../../sharedState/composables/useSearchStateManager"; import { useBarneoConfig } from "../../../config/BarneoConfigManager"; import type { SortWidgetConfig, SortOption, SortState } from "../types"; export function useSortWidget(config?: SortWidgetConfig) { const sharedState = useSharedState(); const configManager = useBarneoConfig(); const searchStateManager = useSearchStateManager(configManager.apiService, { productsWidget: configManager.productsWidgetConfig, }); // Состояние виджета const state = ref({ currentSort: config?.defaultSort || "relevance", isLoading: false, error: null, }); // Стандартные опции сортировки const defaultSortOptions: SortOption[] = [ { value: "relevance", label: "По релевантности", }, { value: "name", label: "По алфавиту" }, { value: "price", label: "По возрастанию цены", }, { value: "-price", label: "По убыванию цены", }, { value: "popular", label: "По популярности", }, ]; // Опции сортировки (из конфига или по умолчанию) const sortOptions = computed(() => { return config?.options || defaultSortOptions; }); // Активная опция сортировки (синхронизирована с sharedState) const activeSortOption = computed(() => { return sortOptions.value.find( (option) => option.value === sharedState.searchState.sort ); }); // Состояние загрузки (синхронизировано с sharedState) const isLoading = computed(() => { const loading = sharedState.searchState.isLoading; return loading; }); // Обработчик изменения сортировки const handleSortChange = async (sortValue: string) => { if (sharedState.searchState.sort === sortValue || isLoading.value) { return; } try { // Очищаем предыдущую ошибку state.value.error = null; // Отслеживаем использование сортировки для аналитики try { await configManager.apiService.useSearchFunction("filter"); } catch (err) { // Игнорируем ошибки отслеживания } // Обновляем сортировку в sharedState sharedState.setSort(sortValue); // Сбрасываем пагинацию при изменении сортировки sharedState.resetPagination(); // Преобразуем активные фильтры в формат для API const filters: Record = {}; sharedState.searchState.activeFilters.forEach((filter) => { const selectedValues = filter.values .filter((value) => value.isSelected) .map((value) => value.id); if (selectedValues.length > 0) { // Маппинг внутренних кодов фильтров на названия полей API switch (filter.code) { case "brand": filters.brands = selectedValues; break; case "category": filters.category_ids = selectedValues; break; case "country": filters.countries = selectedValues; break; default: filters[filter.code] = selectedValues; } } }); // Преобразуем range фильтры в формат для API const products: Array<{ code: string; value_gte?: string; value_lte?: string; }> = []; sharedState.searchState.activeProducts.forEach((product) => { if (product.value_gte || product.value_lte) { products.push({ code: product.code, value_gte: product.value_gte, value_lte: product.value_lte, }); } }); // Выполняем поиск с текущими параметрами из sharedState await searchStateManager.performSearchWithFilters( sharedState.searchState.query, { filters, products: products.length > 0 ? products : undefined, activeFilters: sharedState.searchState.activeFilters.map( (filter) => ({ id: filter.id, name: filter.name, code: filter.code, values: filter.values.map((value) => ({ id: value.id, name: value.name, isSelected: value.isSelected, })), }) ), pagination: sharedState.searchState.pagination, sort: sortValue, } ); // Очищаем ошибку при успешном выполнении state.value.error = null; } catch (error) { state.value.error = error instanceof Error ? error.message : "Ошибка при изменении сортировки"; console.error("Sort change error:", error); } }; // Синхронизация с sharedState watch( () => sharedState.searchState.sort, (newSort) => { if (newSort && newSort !== state.value.currentSort) { state.value.currentSort = newSort; } } ); // Сброс сортировки const resetSort = () => { const defaultSort = config?.defaultSort || "relevance"; sharedState.setSort(defaultSort); }; return { state, sortOptions, activeSortOption, isLoading, handleSortChange, resetSort, }; }