diff --git a/src/components/Content.js b/src/components/Content.js index d9989e9..506740b 100644 --- a/src/components/Content.js +++ b/src/components/Content.js @@ -27,13 +27,13 @@ const withRouter = (ClassComponent) => { }; }; -function getCachedCategoryData(categoryId) { +function getCachedCategoryData(categoryId, language = 'de') { if (!window.productCache) { window.productCache = {}; } try { - const cacheKey = `categoryProducts_${categoryId}`; + const cacheKey = `categoryProducts_${categoryId}_${language}`; const cachedData = window.productCache[cacheKey]; if (cachedData) { @@ -165,7 +165,7 @@ function getFilteredProducts(unfilteredProducts, attributes, t) { return {filteredProducts,activeAttributeFilters:activeAttributeFiltersWithNames,activeManufacturerFilters:activeManufacturerFiltersWithNames,activeAvailabilityFilters}; } -function setCachedCategoryData(categoryId, data) { +function setCachedCategoryData(categoryId, data, language = 'de') { if (!window.productCache) { window.productCache = {}; } @@ -174,7 +174,7 @@ function setCachedCategoryData(categoryId, data) { } try { - const cacheKey = `categoryProducts_${categoryId}`; + const cacheKey = `categoryProducts_${categoryId}_${language}`; if(data.products) for(const product of data.products) { window.productDetailCache[product.id] = product; } @@ -197,40 +197,77 @@ class Content extends Component { unfilteredProducts: [], filteredProducts: [], attributes: [], - childCategories: [] + childCategories: [], + lastFetchedLanguage: props.i18n?.language || 'de' }; } componentDidMount() { - if(this.props.params.categoryId) {this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: []}, () => { + const currentLanguage = this.props.i18n?.language || 'de'; + if(this.props.params.categoryId) {this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: [], lastFetchedLanguage: currentLanguage}, () => { this.fetchCategoryData(this.props.params.categoryId); })} else if (this.props.searchParams?.get('q')) { - this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: []}, () => { + this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: [], lastFetchedLanguage: currentLanguage}, () => { this.fetchSearchData(this.props.searchParams?.get('q')); }) } } componentDidUpdate(prevProps) { - if(this.props.params.categoryId && (prevProps.params.categoryId !== this.props.params.categoryId)) { + const currentLanguage = this.props.i18n?.language || 'de'; + const categoryChanged = this.props.params.categoryId && (prevProps.params.categoryId !== this.props.params.categoryId); + const searchChanged = this.props.searchParams?.get('q') && (prevProps.searchParams?.get('q') !== this.props.searchParams?.get('q')); + + if(categoryChanged) { window.currentSearchQuery = null; - this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: []}, () => { + this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: [], lastFetchedLanguage: currentLanguage}, () => { this.fetchCategoryData(this.props.params.categoryId); - }); + }); + return; // Don't check language change if category changed } - else if (this.props.searchParams?.get('q') && (prevProps.searchParams?.get('q') !== this.props.searchParams?.get('q'))) { - this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: []}, () => { + else if (searchChanged) { + this.setState({loaded: false, unfilteredProducts: [], filteredProducts: [], attributes: [], categoryName: null, childCategories: [], lastFetchedLanguage: currentLanguage}, () => { this.fetchSearchData(this.props.searchParams?.get('q')); - }) + }); + return; // Don't check language change if search changed } - // Re-filter products when language changes to update translated filter names - const languageChanged = this.props.i18n && prevProps.i18n && this.props.i18n.language !== prevProps.i18n.language; - const tFunctionChanged = this.props.t !== prevProps.t; + // Re-fetch products when language changes to get translated content + const languageChanged = currentLanguage !== this.state.lastFetchedLanguage; - if(languageChanged || tFunctionChanged) { - this.filterProducts(); + console.log('Content componentDidUpdate:', { + languageChanged, + lastFetchedLang: this.state.lastFetchedLanguage, + currentLang: currentLanguage, + prevPropsLang: prevProps.i18n?.language, + hasCategoryId: !!this.props.params.categoryId, + categoryId: this.props.params.categoryId, + hasSearchQuery: !!this.props.searchParams?.get('q') + }); + + if(languageChanged) { + console.log('Content: Language changed! Re-fetching data...'); + // Re-fetch current data with new language + // Note: Language is now part of the cache key, so it will automatically fetch fresh data + if(this.props.params.categoryId) { + // Re-fetch category data with new language + console.log('Content: Re-fetching category', this.props.params.categoryId); + this.setState({loaded: false, lastFetchedLanguage: currentLanguage}, () => { + this.fetchCategoryData(this.props.params.categoryId); + }); + } else if(this.props.searchParams?.get('q')) { + // Re-fetch search data with new language + console.log('Content: Re-fetching search', this.props.searchParams?.get('q')); + this.setState({loaded: false, lastFetchedLanguage: currentLanguage}, () => { + this.fetchSearchData(this.props.searchParams?.get('q')); + }); + } else { + // If not viewing category or search, just re-filter existing products + console.log('Content: Just re-filtering existing products'); + this.setState({lastFetchedLanguage: currentLanguage}); + this.filterProducts(); + } } } @@ -267,7 +304,8 @@ class Content extends Component { fetchCategoryData(categoryId) { - const cachedData = getCachedCategoryData(categoryId); + const currentLanguage = this.props.languageContext?.currentLanguage || this.props.i18n?.language || 'de'; + const cachedData = getCachedCategoryData(categoryId, currentLanguage); if (cachedData) { this.processDataWithCategoryTree(cachedData, categoryId); return; @@ -282,7 +320,7 @@ class Content extends Component { window.socketManager.on(`productList:${categoryId}`,(response) => { console.log("getCategoryProducts full response", response); receivedFullResponse = true; - setCachedCategoryData(categoryId, response); + setCachedCategoryData(categoryId, response, currentLanguage); if (response && response.products !== undefined) { this.processDataWithCategoryTree(response, categoryId); } else { @@ -290,7 +328,6 @@ class Content extends Component { } }); - const currentLanguage = this.props.languageContext?.currentLanguage || this.props.i18n?.language || 'de'; window.socketManager.emit( "getCategoryProducts", { categoryId: categoryId, language: currentLanguage, requestTranslation: currentLanguage === 'de' ? false : true }, @@ -298,7 +335,7 @@ class Content extends Component { console.log("getCategoryProducts stub response", response); // Only process stub response if we haven't received the full response yet if (!receivedFullResponse) { - setCachedCategoryData(categoryId, response); + setCachedCategoryData(categoryId, response, currentLanguage); if (response && response.products !== undefined) { this.processDataWithCategoryTree(response, categoryId); } else { diff --git a/src/components/ProductFilters.js b/src/components/ProductFilters.js index ab10948..0aad490 100644 --- a/src/components/ProductFilters.js +++ b/src/components/ProductFilters.js @@ -48,14 +48,37 @@ class ProductFilters extends Component { } componentDidUpdate(prevProps) { - // Regenerate availability values when language changes - // Check both i18n.language and the t function itself + // Regenerate values when products, attributes, or language changes + const productsChanged = this.props.products !== prevProps.products; + const attributesChanged = this.props.attributes !== prevProps.attributes; const languageChanged = this.props.i18n && prevProps.i18n && this.props.i18n.language !== prevProps.i18n.language; const tFunctionChanged = this.props.t !== prevProps.t; - if(languageChanged || tFunctionChanged) { + if(languageChanged) { + console.log('ProductFilters: Language changed, will update when new data arrives'); + } + + if(productsChanged || languageChanged || tFunctionChanged) { + console.log('ProductFilters: Updating manufacturers and availability', { + productsChanged, + languageChanged, + tFunctionChanged, + productCount: this.props.products?.length + }); + const uniqueManufacturerArray = this._getUniqueManufacturers(this.props.products); const availabilityValues = this._getAvailabilityValues(this.props.products); - this.setState({availabilityValues}); + this.setState({uniqueManufacturerArray, availabilityValues}); + } + + if(attributesChanged || (languageChanged && this.props.attributes)) { + console.log('ProductFilters: Updating attributes', { + attributesChanged, + languageChanged, + attributeCount: this.props.attributes?.length, + firstAttribute: this.props.attributes?.[0] + }); + const attributeGroups = this._getAttributeGroups(this.props.attributes); + this.setState({attributeGroups}); } } @@ -128,19 +151,6 @@ class ProductFilters extends Component { return attributeGroups; } - shouldComponentUpdate(nextProps) { - if(nextProps.products !== this.props.products) { - const uniqueManufacturerArray = this._getUniqueManufacturers(nextProps.products); - const availabilityValues = this._getAvailabilityValues(nextProps.products); - this.setState({uniqueManufacturerArray, availabilityValues}); - } - if(nextProps.attributes !== this.props.attributes) { - const attributeGroups = this._getAttributeGroups(nextProps.attributes); - this.setState({attributeGroups}); - } - return true; - } - generateAttributeFilters = () => { const filters = []; const sortedAttributeGroups = Object.values(this.state.attributeGroups)