This is a Redux slice implementation using @reduxjs/toolkit
. It manages the state for products, including loading, best-selling products, random products, wishlist data, and user preferences.
- Async Thunk: Fetches product data from an external API.
- Reducers: Handles local state updates for random products, best-selling products, and user-liked products.
- Extra Reducers: Handles loading states for asynchronous actions.
-
Install dependencies:
npm install @reduxjs/toolkit axios
-
Import the slice into your Redux store:
import { configureStore } from "@reduxjs/toolkit"; import HomepageReducer from "./path-to/your-slice"; const store = configureStore({ reducer: { homepage: HomepageReducer, }, }); export default store;
const initialState = {
isLoading: true,
Data: [],
randomProduct: [],
BestSellingProducts: [],
wishlistData: [],
error: "",
productsILiked: [],
};
Fetches product data from the Fake Store API:
export const gitProductItem = createAsyncThunk(
"student/gitProductItem",
async (name, thunkAPI) => {
try {
const res = await axios("https://fakestoreapi.com/products");
return res.data;
} catch (error) {
return thunkAPI.rejectWithValue(error.message);
}
}
);
Filters 5 random products from the dataset:
gitRandomProduct(state) {
const randomNumbersArray = Array.from(
{ length: 5 },
() => Math.floor(Math.random() * 20) + 1
);
state.randomProduct = state.Data.filter((data) =>
randomNumbersArray.includes(data.id)
);
}
Sorts and selects the top 3 products based on rating:
gitBestSellingProducts(state) {
state.BestSellingProducts = state.Data.map((data) => data)
.sort((a, b) => b.rating.rate - a.rating.rate)
.slice(0, 3);
}
Adds or removes products from the user’s liked products:
getProductsILiked(state, action) {
const findProduct = state.Data.find((data) => data.id === action.payload);
if (findProduct) {
if (!state.productsILiked.some((e) => e.id === action.payload)) {
state.productsILiked.push(findProduct);
} else {
state.productsILiked = state.productsILiked.filter(
(arr) => arr.id !== findProduct.id
);
}
}
}
Handles async actions:
extraReducers: (builder) => {
builder
.addCase(gitProductItem.pending, (state) => {
state.isLoading = true;
})
.addCase(gitProductItem.fulfilled, (state, action) => {
state.isLoading = false;
state.Data = action.payload;
})
.addCase(gitProductItem.rejected, (state) => {
state.isLoading = false;
state.error = true;
});
}
export const {
gitRandomProduct,
gitBestSellingProducts,
getProductsILiked,
} = HomepageReducer.actions;
Dispatching actions:
import { useDispatch, useSelector } from "react-redux";
import { gitProductItem, gitRandomProduct } from "./path-to/your-slice";
const MyComponent = () => {
const dispatch = useDispatch();
const { Data, randomProduct, isLoading } = useSelector(
(state) => state.homepage
);
useEffect(() => {
dispatch(gitProductItem());
}, [dispatch]);
return isLoading ? (
<p>Loading...</p>
) : (
<div>
<h1>Products</h1>
<button onClick={() => dispatch(gitRandomProduct())}>
Get Random Products
</button>
{/* Render products */}
</div>
);
};