import {defineStore} from "pinia";
import ftch from "@/utils/ftch.js";
import {md5} from 'js-md5';
import {toRaw} from "vue";

export const useProductsStore = defineStore('products', {
    state: () => ({
        products: {
            data: [],
            meta: {
                hasMore: true,
            },
        },
        filters: null,
        filtersFullUrl: '',
        search: '',
        page: 1,
        isLoading: false,
        isLoadingMore: false,
        loadFinished: false,
        savedScrollY: 0,
        currentLoadedParamsHash: null,
        lastCategoryId: null,
        scrollPositions: {}, // Сохраняем позиции скролла для каждой категории
    }),

    getters: {
        paramsHash: (state) => md5(JSON.stringify(toRaw(state.getParams()))),
        paramsHashForRouter: (state) => md5(JSON.stringify({
            search: state.search,
            filters: toRaw(state.filters),
        })),
    },

    actions: {
        getParams() {
            return {
                page: this.page,
                search: this.search,
                filters: toRaw(this.filters),
            };
        },

        async fetchProducts() {
            try {
                console.debug('Current params hash: ', this.currentLoadedParamsHash);
                if (this.products.data.length > 0 && this.paramsHash === this.currentLoadedParamsHash) {
                    console.debug('Loading products from cache');
                    return new Promise((resolve, reject) => {
                        resolve(this.products);
                    });
                }

                console.debug('Requested param cache: ', this.paramsHash);
                console.debug('Invalidate cache. Fetch products from server.', this.getParams());
                const response = await ftch('products', null, this.getParams());
                this.currentLoadedParamsHash = this.paramsHash;
                console.debug('Products loaded from server.');
                console.debug('New params hash: ', this.currentLoadedParamsHash);

                return {
                    meta: response.meta,
                    data: response.data,
                };
            } catch (error) {
                console.error("Failed to load products");
                console.error(error);
            } finally {
            }
        },

        async loadProducts(filters = null) {
            if (this.isLoading) return;

            try {
                console.debug('Load products with filters', filters);
                this.reset();
                this.isLoading = true;
                this.page = 1;
                this.loadFinished = false;
                this.search = '';
                this.filters = filters;
                this.products = await this.fetchProducts();
            } catch (e) {
                console.error('Ошибка загрузки', e);
            } finally {
                this.isLoading = false;
                this.loadFinished = true;
            }
        },

        async loadMore() {
            if (this.isLoading || this.isLoadingMore || this.products.meta.hasMore === false) return;

            try {
                this.isLoadingMore = true;
                this.page++;
                console.debug('Load more products for page: ', this.page);
                const response = await this.fetchProducts();
                this.products.meta = response.meta;
                this.products.data.push(...response.data);
            } catch (e) {
                console.error('Ошибка загрузки', e);
            } finally {
                this.isLoadingMore = false;
                this.loadFinished = true;
                this.isLoading = false;
            }
        },

        reset() {
            this.isLoading = false;
            this.page = 1;
            this.loadFinished = false;
            this.search = '';
            this.products = {
                data: [],
                meta: {
                    hasMore: true,
                },
            };
        },

        saveScrollPosition(categoryId, position) {
            if (categoryId) {
                this.scrollPositions[categoryId] = position;
                this.savedScrollY = position;
            }
        },

        getScrollPosition(categoryId) {
            return this.scrollPositions[categoryId] || 0;
        },
    },
});
