import { useState, useEffect } from "react";
import { useParams, Link } from "react-router-dom";
import {
Heart,
ArrowLeft,
Tag,
User,
Calendar,
Star,
Phone,
Mail,
} from "lucide-react";
const ProductDetail = () => {
const { id } = useParams();
const [product, setProduct] = useState(null);
const [loading, setLoading] = useState({
product: true,
reviews: true,
submitting: false,
});
const [error, setError] = useState({
product: null,
reviews: null,
submit: null,
});
const [isFavorite, setIsFavorite] = useState(false);
const [showContactOptions, setShowContactOptions] = useState(false);
const [currentImage, setCurrentImage] = useState(0);
const [reviews, setReviews] = useState([]);
const [showReviewForm, setShowReviewForm] = useState(false);
const storedUser = JSON.parse(sessionStorage.getItem("user"));
const [reviewForm, setReviewForm] = useState({
rating: 3,
comment: "",
name: "",
});
// Add this function to handle review input changes
const handleReviewInputChange = (e) => {
const { id, value } = e.target;
setReviewForm((prev) => ({
...prev,
[id]: value,
}));
};
// Add this function to handle star rating selection
const handleRatingChange = (rating) => {
setReviewForm((prev) => ({
...prev,
rating,
}));
};
const handleSubmitReview = async (e) => {
e.preventDefault(); // Prevent form default behavior
try {
setLoading((prev) => ({ ...prev, submitting: true }));
setError((prev) => ({ ...prev, submit: null }));
const reviewData = {
productId: id,
rating: reviewForm.rating,
comment: reviewForm.comment,
userId: storedUser.ID,
};
const response = await fetch(`http://localhost:3030/api/review/add`, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify(reviewData),
});
const result = await response.json();
// Check if API returned an error message even with 200 status
if (!result.success) {
throw new Error(result.message || "Failed to submit review");
}
alert("Review submitted successfully!");
setReviewForm({
rating: 3,
comment: "",
name: "",
});
setShowReviewForm(false);
try {
setLoading((prev) => ({ ...prev, reviews: true }));
const reviewsResponse = await fetch(
`http://localhost:3030/api/review/${id}`,
);
const reviewsResult = await reviewsResponse.json();
if (reviewsResult.success) {
setReviews(reviewsResult.data || []);
setError((prev) => ({ ...prev, reviews: null }));
} else {
throw new Error(reviewsResult.message || "Error fetching reviews");
}
} catch (reviewsError) {
console.error("Error fetching reviews:", reviewsError);
setError((prev) => ({ ...prev, reviews: reviewsError.message }));
} finally {
setLoading((prev) => ({ ...prev, reviews: false }));
}
} catch (error) {
console.error("Error submitting review:", error);
alert(`Error: ${error.message}`);
setError((prev) => ({
...prev,
submit: error.message,
}));
} finally {
setLoading((prev) => ({ ...prev, submitting: false }));
}
};
// Fetch product data
useEffect(() => {
const fetchProduct = async () => {
try {
setLoading((prev) => ({ ...prev, product: true }));
const response = await fetch(`http://localhost:3030/api/product/${id}`);
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const result = await response.json();
if (result.success) {
setProduct(result.data);
setError((prev) => ({ ...prev, product: null }));
} else {
throw new Error(result.message || "Error fetching product");
}
} catch (error) {
console.error("Error fetching product:", error);
setError((prev) => ({ ...prev, product: error.message }));
} finally {
setLoading((prev) => ({ ...prev, product: false }));
}
};
fetchProduct();
}, [id]);
// Fetch reviews data
useEffect(() => {
const fetchReviews = async () => {
try {
setLoading((prev) => ({ ...prev, reviews: true }));
const response = await fetch(`http://localhost:3030/api/review/${id}`);
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const result = await response.json();
if (result.success) {
setReviews(result.data || []);
setError((prev) => ({ ...prev, reviews: null }));
} else {
throw new Error(result.message || "Error fetching reviews");
}
} catch (error) {
console.error("Error fetching reviews:", error);
setError((prev) => ({ ...prev, reviews: error.message }));
setReviews([]);
} finally {
setLoading((prev) => ({ ...prev, reviews: false }));
}
};
fetchReviews();
}, [id]);
// Handle favorite toggle with error handling
const toggleFavorite = async () => {
try {
const response = await fetch(
"http://localhost:3030/api/product/add_to_favorite",
{
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
userID: 1, // Replace with actual user ID
productsID: id,
}),
},
);
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const result = await response.json();
if (result.success) {
setIsFavorite(!isFavorite);
} else {
throw new Error(result.message || "Failed to toggle favorite");
}
} catch (error) {
console.error("Error toggling favorite:", error);
alert(`Failed to add to favorites: ${error.message}`);
}
};
// Image navigation
const nextImage = () => {
if (product?.images?.length > 0) {
setCurrentImage((prev) =>
prev === product.images.length - 1 ? 0 : prev + 1,
);
}
};
const prevImage = () => {
if (product?.images?.length > 0) {
setCurrentImage((prev) =>
prev === 0 ? product.images.length - 1 : prev - 1,
);
}
};
const selectImage = (index) => {
setCurrentImage(index);
};
// Function to render stars based on rating
const renderStars = (rating) => {
const stars = [];
for (let i = 1; i <= 5; i++) {
stars.push(
{error.product}
Back to Listings{product.Description || "No description available"}
Member since {product.SellerJoinDate || "N/A"}