Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion app/layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ export default function RootLayout({
<body className={`font-sans ${GeistSans.variable} ${GeistMono.variable} antialiased`}>
<Navigation />
<div className="pt-20">
<Suspense fallback={<div>Loading...</div>}>{children}</Suspense>
<Suspense fallback={<div className="flex h-screen items-center justify-center">Loading...</div>}>{children}</Suspense>
</div>
<Analytics />
</body>
Expand Down
50 changes: 7 additions & 43 deletions app/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,17 +30,6 @@ export default async function HomePage() {
.order("match_date", { ascending: false })
.limit(3)

// Fetch top teams from standings
const { data: topTeams } = await supabase
.from("tournament_standings")
.select(`
*,
team:teams(name)
`)
.order("points", { ascending: false })
.order("nrr", { ascending: false })
.limit(4)

return (
<div className="min-h-screen">
{/* Hero Section */}
Expand Down Expand Up @@ -73,7 +62,7 @@ export default async function HomePage() {
</section>

{/* Stats Overview */}
<section className="py-16 px-6">
{/* <section className="py-16 px-6">
<div className="max-w-7xl mx-auto">
<div className="grid grid-cols-1 md:grid-cols-4 gap-6 mb-12">
<Card className="glass glass-hover text-center">
Expand Down Expand Up @@ -106,7 +95,7 @@ export default async function HomePage() {
</Card>
</div>
</div>
</section>
</section> */}

{/* Live Scores Section */}
<section className="py-16 px-6">
Expand All @@ -121,7 +110,11 @@ export default async function HomePage() {

{/* Live Standings */}
<section className="py-16 px-6">
<div className="max-w-4xl mx-auto">
<div className="max-w-7xl mx-auto">
<h2 className="text-3xl font-bold mb-8 text-center flex items-center justify-center gap-3">
<div className="w-3 h-3 bg-primary rounded-full animate-pulse"></div>
Live Standings
</h2>
<LiveStandings />
<div className="text-center mt-8">
<Button variant="outline" className="glass glass-hover bg-transparent" asChild>
Expand Down Expand Up @@ -159,35 +152,6 @@ export default async function HomePage() {
</div>
</section>

{/* Top Teams */}
<section className="py-16 px-6">
<div className="max-w-7xl mx-auto">
<h2 className="text-3xl font-bold mb-8 text-center">Tournament Standings</h2>
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-6">
{topTeams?.map((standing, index) => (
<Card key={standing.team_id} className="glass glass-hover">
<CardContent>
<div className="space-y-2">
<div className="flex justify-between">
<span className="text-sm text-muted-foreground">Points</span>
<span className="font-semibold">{standing.points}</span>
</div>
<div className="flex justify-between">
<span className="text-sm text-muted-foreground">Matches</span>
<span className="font-semibold">{standing.matches_played}</span>
</div>
<div className="flex justify-between">
<span className="text-sm text-muted-foreground">NRR</span>
<span className="font-semibold">{standing.nrr.toFixed(3)}</span>
</div>
</div>
</CardContent>
</Card>
))}
</div>
</div>
</section>

{/* Navigation */}
<section className="py-16 px-6">
<div className="max-w-4xl mx-auto">
Expand Down
185 changes: 123 additions & 62 deletions components/live-score-card.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -43,69 +43,130 @@ export function LiveScoreCard() {

return (
<Card key={match.id} className="glass glass-hover border-primary/30">
<CardHeader>
<div className="flex justify-between items-center">
<Badge className="neon-glow bg-primary/20 text-primary border-primary/50">
<div className="w-2 h-2 bg-primary rounded-full animate-pulse mr-2"></div>
LIVE
</Badge>
<div className="flex items-center gap-2 text-sm text-muted-foreground">
<MapPin className="h-4 w-4" />
{match.venue}
</div>
</div>
</CardHeader>
<CardContent className="space-y-6">
{/* Team 1 */}
<div className="flex justify-between items-center p-4 glass rounded-lg">
<div>
<h3 className="text-xl font-bold">{match.team1?.name}</h3>
<p className="text-sm text-muted-foreground">Innings {team1Score?.innings || 1}</p>
</div>
<div className="text-right">
<div className="text-2xl font-bold text-primary">
{team1Score?.runs || 0}/{team1Score?.wickets || 0}
</div>
<div className="text-sm text-muted-foreground">({team1Score?.overs || 0.0} overs)</div>
<div className="text-xs text-secondary">RR: {team1Score?.current_rr?.toFixed(2) || "0.00"}</div>
</div>
</div>
<CardHeader>
<div className="flex justify-between items-center">
<Badge className="neon-glow bg-primary/20 text-primary border-primary/50">
<div className="w-2 h-2 bg-primary rounded-full animate-pulse mr-2"></div>
LIVE
</Badge>
<div className="flex items-center gap-2 text-sm text-muted-foreground">
<MapPin className="h-4 w-4" />
{match.venue}
</div>
</div>
</CardHeader>
<CardContent className="space-y-6">
<div className="grid grid-cols-1 md:grid-cols-3 gap-3">
{/* Team 1 - Stacked Layout */}
<div className="p-4 glass rounded-lg">
<div className="flex items-center gap-3 mb-3">
<div className="w-10 h-10 rounded-full bg-primary/20 flex items-center justify-center">
<span className="text-sm font-bold text-primary">{match.team1?.shortCode || 'T1'}</span>
</div>
Comment on lines +63 to +65

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[P1] Extend TeamInfo to cover short codes

The new Matches typings only give a team name, yet the live score card renders match.team1?.shortCode as part of the UI. With the stricter typing introduced in this commit, running npx tsc --noEmit fails (TS2339: Property 'shortCode' does not exist on type 'TeamInfo'). Either add an optional shortCode field to TeamInfo or stop referencing it so type checking doesn’t break.

Useful? React with 👍 / 👎.

<div>
<h3 className="text-xl font-bold">{match.team1?.name}</h3>
<p className="text-sm text-muted-foreground">Innings {team1Score?.innings || 1}</p>
</div>
</div>

{/* Score Stacked Below Team Info */}
<div className="grid grid-cols-2 gap-4 text-center">
<div className="space-y-1">
<div className="text-3xl font-bold text-primary">
{team1Score?.runs || 0}<span className="text-red-400">/</span>{team1Score?.wickets || 0}
</div>
<div className="text-sm text-muted-foreground">Runs/Wickets</div>
</div>
<div className="space-y-1">
<div className="text-lg font-bold text-primary">{team1Score?.overs?.toFixed(1) || 0.0}</div>
<div className="text-sm text-muted-foreground">Overs</div>
<div className="text-xs text-secondary">RR: {team1Score?.current_rr?.toFixed(2) || "0.00"}</div>
</div>
</div>
</div>

{/* Team 2 */}
<div className="flex justify-between items-center p-4 glass rounded-lg">
<div>
<h3 className="text-xl font-bold">{match.team2?.name}</h3>
<p className="text-sm text-muted-foreground">Innings {team2Score?.innings || 1}</p>
</div>
<div className="text-right">
<div className="text-2xl font-bold text-primary">
{team2Score?.runs || 0}/{team2Score?.wickets || 0}
</div>
<div className="text-sm text-muted-foreground">({team2Score?.overs || 0.0} overs)</div>
{team2Score?.required_rr && (
<div className="text-xs text-secondary">Req RR: {team2Score.required_rr.toFixed(2)}</div>
)}
</div>
</div>
{/* Match Center Info */}
<div className="glass rounded-lg p-4 text-center space-y-3">
{team2Score?.required_rr && (
<div className="space-y-1">
<div className="text-lg font-bold">Target: {team1Score?.runs || 0}</div>
<div className="text-sm text-muted-foreground">
Need {team1Score?.runs - (team2Score?.runs || 0)} runs •
Req RR: {team2Score.required_rr.toFixed(2)}
</div>
</div>
)}

<div className="space-y-2">
<h4 className="font-semibold text-sm">{match.currentOver?.number || 6}th over</h4>
<div className="flex justify-center gap-1">
{match.currentOver?.balls?.map((ball, index) => (
Comment on lines +101 to +103

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[P1] Match type missing current over data

The UI now reads match.currentOver?.number and iterates over match.currentOver?.balls, but the newly added Match interface in lib/types.ts doesn’t define a currentOver field. This causes npx tsc --noEmit to fail with TS2339 and makes the types unusable for editor assistance. Consider extending the Match type (e.g. currentOver?: { number: number; balls: string[] }) or guarding the UI with any casting.

Useful? React with 👍 / 👎.

<span key={index} className={`w-6 h-6 rounded-full flex items-center justify-center text-xs font-bold ${
ball === 'W' ? 'bg-red-500/30 text-red-300' :
ball === '4' ? 'bg-green-500/30 text-green-300' :
ball === '6' ? 'bg-purple-500/30 text-purple-300' :
'bg-white/10 text-muted-foreground'
}`}>
{ball}
</span>
)) || ['.', '.', '.', '.', '.', '.'].map((ball, index) => (
<span key={index} className="w-6 h-6 rounded-full bg-white/10 flex items-center justify-center text-muted-foreground text-xs">
{ball}
</span>
))}
</div>
</div>
</div>

<div className="flex gap-3">
<Button size="sm" className="flex-1" asChild>
<Link href={`/match/${match.id}`}>
<Target className="mr-2 h-4 w-4" />
Ball by Ball
</Link>
</Button>
<Button size="sm" variant="secondary" className="flex-1" asChild>
<Link href={`/match/${match.id}/scorecard`}>
<TrendingUp className="mr-2 h-4 w-4" />
Scorecard
</Link>
</Button>
</div>
</CardContent>
</Card>
)
})}
{/* Team 2 - Stacked Layout */}
<div className="p-4 glass rounded-lg">
<div className="flex items-center gap-3 mb-3">
<div className="w-10 h-10 rounded-full bg-primary/20 flex items-center justify-center">
<span className="text-sm font-bold text-primary">{match.team2?.shortCode || 'T2'}</span>
</div>
<div>
<h3 className="text-xl font-bold">{match.team2?.name}</h3>
<p className="text-sm text-muted-foreground">Innings {team2Score?.innings || 1}</p>
</div>
</div>

{/* Score Stacked Below Team Info */}
<div className="grid grid-cols-2 gap-4 text-center">
<div className="space-y-1">
<div className="text-3xl font-bold text-primary">
{team2Score?.runs || 0}<span className="text-red-400">/</span>{team2Score?.wickets || 0}
</div>
<div className="text-sm text-muted-foreground">Runs/Wickets</div>
</div>
<div className="space-y-1">
<div className="text-lg font-bold text-primary">{team2Score?.overs?.toFixed(1) || 0.0}</div>
<div className="text-sm text-muted-foreground">Overs</div>
{team2Score?.required_rr ? (
<div className="text-xs text-secondary">Req RR: {team2Score.required_rr.toFixed(2)}</div>
) : (
<div className="text-xs text-secondary">RR: {team2Score?.current_rr?.toFixed(2) || "0.00"}</div>
)}
</div>
</div>
</div>
</div>
)

<div className="flex gap-3">
<Button size="sm" className="flex-1" asChild>
<Link href={`/match/${match.id}`}>
<Target className="mr-2 h-4 w-4" />
Ball by Ball
</Link>
</Button>
<Button size="sm" variant="secondary" className="flex-1" asChild>
<Link href={`/match/${match.id}/scorecard`}>
<TrendingUp className="mr-2 h-4 w-4" />
Scorecard
</Link>
</Button>
</div>
</CardContent>
</Card>)
})}
</div>)
}
12 changes: 0 additions & 12 deletions components/live-standings.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,6 @@ export function LiveStandings() {
if (loading) {
return (
<Card className="glass">
<CardHeader>
<CardTitle className="text-2xl flex items-center gap-3">
<Trophy className="h-8 w-8 text-primary" />
Tournament Standings
</CardTitle>
</CardHeader>
<CardContent>
<div className="animate-pulse space-y-4">
{[...Array(5)].map((_, i) => (
Expand All @@ -33,12 +27,6 @@ export function LiveStandings() {

return (
<Card className="glass">
<CardHeader>
<CardTitle className="text-2xl flex items-center gap-3">
<Trophy className="h-8 w-8 text-primary" />
Live Standings
</CardTitle>
</CardHeader>
<CardContent>
<div className="overflow-x-auto">
<table className="w-full">
Expand Down
3 changes: 2 additions & 1 deletion lib/realtime.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,10 @@

import { createClient } from "@/lib/supabase/client"
import { useEffect, useMemo, useState } from "react"
import { Matches } from "./types"

export function useRealtimeMatches() {
const [matches, setMatches] = useState<any[]>([])
const [matches, setMatches] = useState<Matches>([])
const [loading, setLoading] = useState(true)
const supabase = useMemo(() => createClient(), [])

Expand Down
36 changes: 36 additions & 0 deletions lib/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
export interface TeamInfo {
name: string;
}

export interface ScoreboardEntry {
id: string;
runs: number;
overs: number;
innings: 1 | 2;
team_id: string;
wickets: number;
match_id: string;
current_rr: number;
updated_at: string;
required_rr: number | null;
}

export interface Match {
id: string;
team1_id: string;
team2_id: string;
venue: string;
match_date: string;
status: "completed" | "ongoing" | "upcoming"; // expanded based on possible values
winner_id: string | null;
toss_winner_id: string;
elected_to: "bat" | "bowl";
created_at: string;
overs_per_innings: number;
team1: TeamInfo;
team2: TeamInfo;
winner: TeamInfo | null;
scoreboard: ScoreboardEntry[];
}

export type Matches = Match[];