Problem Summary:
The “Featured” component is not initially displaying the medicine products data because the medicine products are not yet fetched from the API. The component is re-rendering as the medicine products fetching process is initiated, but the data is not available until the request completes successfully.
Detailed Analysis:
Initial Rendering: The “Featured” component renders without displaying the medicine products data because the initial state of the medicineProducts array is empty.
Fetching Process Initiation: The FETCH_MEDICINE_PRODUCTS_REQUEST action is dispatched, triggering the asynchronous process of fetching medicine products from the API.
State Update and Re-render: The reducer updates the isLoading state to true, indicating that data is being fetched. The component re-renders due to this state change, but the medicine products data is still not available from the API.
Extension Loading: An extension, possibly related to loading or data fetching, is loaded. This suggests that additional resources or functionalities are being prepared to handle the incoming data.
Resolution:
The problem will be resolved once the medicine products fetching process completes successfully and the FETCH_MEDICINE_PRODUCTS_SUCCESS action is dispatched. The reducer will update the medicineProducts state with the fetched data, and the component will re-render again, displaying the updated data.
here is // Featured.js
// Featured.js
import { connect } from "react-redux";
import React, { useEffect } from "react";
import Product from "./Product"; // Assuming the Product component is in the same directory
import { fetchMedicineProductsRequest } from "../redux/actions/productAction";
function Featured({ medicineProducts, isLoading, error, fetchMedicineProducts }) {
useEffect(() => {
console.log('Component mounted');
fetchMedicineProducts();
}, [fetchMedicineProducts]);
console.log("Component: Rendering", { isLoading, error, medicineProducts });
return (
<div className="featured-container">
<div className="container-header">
<h2>Featured Products</h2>
<div className="content-link">
<a className="link-underline" href="#home">
View All
</a>
</div>
</div>
<div className="featured-content">
{isLoading ? (
<div>Fetching Featured Products...</div>
) : error ? (
<div>Error: {error.message}</div>
) : (
<div className="products">
{medicineProducts.map((product) => (
<Product
key={product.id}
subtitle="Essential for Women/Men"
title={product.name}
desc={product.description}
/>
))}
</div>
)}
</div>
</div>
);
}
const mapStateToProps = (state) => ({
medicineProducts: state.medicineProducts.medicineProducts,
isLoading: state.medicineProducts.isLoading,
error: state.medicineProducts.error,
});
const mapDispatchToProps = {
fetchMedicineProducts: fetchMedicineProductsRequest,
};
export default connect(mapStateToProps, mapDispatchToProps)(Featured);
and this is // productAction.js
import {
FETCH_MEDICINE_PRODUCTS_REQUEST,
FETCH_MEDICINE_PRODUCTS_SUCCESS,
FETCH_MEDICINE_PRODUCTS_FAILURE,
} from '../types';
import axios from '../../axiosConfig';
export const fetchMedicineProductsRequest = () => ({
type: FETCH_MEDICINE_PRODUCTS_REQUEST,
});
export const fetchMedicineProductsSuccess = (data) => ({
type: FETCH_MEDICINE_PRODUCTS_SUCCESS,
payload: data,
});
export const fetchMedicineProductsFailure = (error) => ({
type: FETCH_MEDICINE_PRODUCTS_FAILURE,
payload: error,
});
export const fetchMedicineProducts = () => async (dispatch) => {
console.log("Action: fetchMedicineProductsRequest");
dispatch(fetchMedicineProductsRequest());
try {
const response = await axios.get('/api/products/');
console.log("Action: Successful response", response.data);
if (response.status !== 200) {
throw new Error('Error!');
}
dispatch(fetchMedicineProductsSuccess(response.data.products));
} catch (error) {
console.log("Action: Error", error.message);
dispatch(fetchMedicineProductsFailure(error.message));
}
};
// productReducer.js
// productReducer.js
import * as types from '../types';
const initialState = {
medicineProducts: [],
isLoading: false,
error: null,
};
const medicineProductsReducer = (state = initialState, action) => {
switch (action.type) {
case types.FETCH_MEDICINE_PRODUCTS_REQUEST:
console.log("Reducer: FETCH_MEDICINE_PRODUCTS_REQUEST");
return { ...state, isLoading: true, error: null };
case types.FETCH_MEDICINE_PRODUCTS_SUCCESS:
console.log("Reducer: FETCH_MEDICINE_PRODUCTS_SUCCESS", action.payload);
return { ...state, isLoading: false, medicineProducts: action.payload };
case types.FETCH_MEDICINE_PRODUCTS_FAILURE:
return { ...state, isLoading: false, error: action.payload };
default:
return state;
}
};
export default medicineProductsReducer;
Postman API call:

The problem will be resolved once the medicine products fetching process completes successfully and the FETCH_MEDICINE_PRODUCTS_SUCCESS action is dispatched. The reducer will update the medicineProducts state with the fetched data, and the component will re-render again, displaying the updated data.