diff --git a/frontend/app/shows/[id]/page.tsx b/frontend/app/shows/[id]/page.tsx index 3b64ecb..3fe4b07 100644 --- a/frontend/app/shows/[id]/page.tsx +++ b/frontend/app/shows/[id]/page.tsx @@ -86,29 +86,44 @@ export default async function ShowDetailPage({ params }: { params: Promise<{ id: {show.performances && show.performances.length > 0 ? (
{show.performances.map((perf: any) => ( -
- {perf.position}. -
- {perf.song?.title || "Unknown Song"} - {perf.segue && >} +
+
+ {perf.position}. +
+ {perf.song?.title || "Unknown Song"} + {perf.segue && >} +
+ + {/* Nicknames */} + {perf.nicknames && perf.nicknames.length > 0 && ( +
+ {perf.nicknames.map((nick: any) => ( + + "{nick.nickname}" + + ))} +
+ )} + + {/* Suggest Nickname Button */} +
+ +
- {/* Nicknames */} - {perf.nicknames && perf.nicknames.length > 0 && ( -
- {perf.nicknames.map((nick: any) => ( - - "{nick.nickname}" - - ))} -
- )} - - {/* Suggest Nickname Button */} - + {/* Rating Column */} +
+ + + +
))}
diff --git a/frontend/components/social/entity-rating.tsx b/frontend/components/social/entity-rating.tsx index 508c50b..98bf66d 100644 --- a/frontend/components/social/entity-rating.tsx +++ b/frontend/components/social/entity-rating.tsx @@ -5,11 +5,12 @@ import { StarRating } from "@/components/ui/star-rating" import { getApiUrl } from "@/lib/api-config" interface EntityRatingProps { - entityType: "show" | "song" | "venue" | "tour" + entityType: "show" | "song" | "venue" | "tour" | "performance" entityId: number + compact?: boolean } -export function EntityRating({ entityType, entityId }: EntityRatingProps) { +export function EntityRating({ entityType, entityId, compact = false }: EntityRatingProps) { const [userRating, setUserRating] = useState(0) const [averageRating, setAverageRating] = useState(0) const [loading, setLoading] = useState(false) @@ -22,15 +23,7 @@ export function EntityRating({ entityType, entityId }: EntityRatingProps) { .catch(err => console.error("Failed to fetch avg rating", err)) // Fetch user rating (if logged in) - const token = localStorage.getItem("token") - if (token) { - // We don't have a direct "get my rating" endpoint in the snippet I saw, - // but we can infer it or maybe we need to add one. - // For now, let's assume we can't easily get *my* rating without a specific endpoint - // or filtering the list. - // Actually, the backend `create_rating` checks for existing. - // Let's just implement setting it for now. - } + // TODO: Implement fetching user's existing rating }, [entityType, entityId]) const handleRate = async (score: number) => { @@ -58,7 +51,11 @@ export function EntityRating({ entityType, entityId }: EntityRatingProps) { const data = await res.json() setUserRating(data.score) - // Refresh average? + + // Re-fetch average to keep it lively + fetch(`${getApiUrl()}/social/ratings/average?${entityType}_id=${entityId}`) + .then(res => res.json()) + .then(setAverageRating) } catch (err) { console.error(err) alert("Error submitting rating") @@ -67,6 +64,19 @@ export function EntityRating({ entityType, entityId }: EntityRatingProps) { } } + if (compact) { + return ( +
+ + {averageRating > 0 && ( + + {averageRating.toFixed(1)} + + )} +
+ ) + } + return (
diff --git a/frontend/components/ui/star-rating.tsx b/frontend/components/ui/star-rating.tsx index f3f2faf..287fd17 100644 --- a/frontend/components/ui/star-rating.tsx +++ b/frontend/components/ui/star-rating.tsx @@ -2,17 +2,20 @@ import { useState } from "react" import { Star } from "lucide-react" import { cn } from "@/lib/utils" + interface RatingProps { value: number onChange?: (value: number) => void readonly?: boolean className?: string + size?: "sm" | "md" } -export function StarRating({ value, onChange, readonly = false, className }: RatingProps) { +export function StarRating({ value, onChange, readonly = false, className, size = "md" }: RatingProps) { const [hoverValue, setHoverValue] = useState(null) const stars = Array.from({ length: 10 }, (_, i) => i + 1) + const starSize = size === "sm" ? "h-3 w-3" : "h-4 w-4" return (
@@ -31,7 +34,7 @@ export function StarRating({ value, onChange, readonly = false, className }: Rat >