152 lines
4.1 KiB
Python
152 lines
4.1 KiB
Python
from typing import List, Dict, Optional, Union, Any
|
|
from sqlalchemy.orm import Session
|
|
from datetime import datetime
|
|
|
|
def calculate_goal_difference(goals_for: int, goals_against: int) -> int:
|
|
"""
|
|
Calculate goal difference for a team.
|
|
|
|
Args:
|
|
goals_for: Goals scored by team
|
|
goals_against: Goals conceded by team
|
|
|
|
Returns:
|
|
int: Goal difference
|
|
"""
|
|
return goals_for - goals_against
|
|
|
|
def update_team_stats(
|
|
team: Any,
|
|
match_result: str,
|
|
goals_scored: int,
|
|
goals_conceded: int
|
|
) -> None:
|
|
"""
|
|
Update team statistics after a match.
|
|
|
|
Args:
|
|
team: Team object to update
|
|
match_result: Result of match ('W', 'D', 'L')
|
|
goals_scored: Goals scored in match
|
|
goals_conceded: Goals conceded in match
|
|
"""
|
|
team.matches_played += 1
|
|
team.goals_for += goals_scored
|
|
team.goals_against += goals_conceded
|
|
team.goal_difference = calculate_goal_difference(team.goals_for, team.goals_against)
|
|
|
|
if match_result == 'W':
|
|
team.wins += 1
|
|
team.points += 3
|
|
elif match_result == 'D':
|
|
team.draws += 1
|
|
team.points += 1
|
|
else:
|
|
team.losses += 1
|
|
|
|
def get_team_standings(db: Session, season: str, league: str) -> List[Dict]:
|
|
"""
|
|
Get sorted team standings for a league season.
|
|
|
|
Args:
|
|
db: Database session
|
|
season: Season to get standings for
|
|
league: League to get standings for
|
|
|
|
Returns:
|
|
List of teams sorted by points and goal difference
|
|
"""
|
|
teams = db.query(Glory).filter(
|
|
Glory.season == season,
|
|
Glory.league == league,
|
|
Glory.is_active == True
|
|
).all()
|
|
|
|
sorted_teams = sorted(
|
|
teams,
|
|
key=lambda x: (-x.points, -x.goal_difference, -x.goals_for)
|
|
)
|
|
|
|
standings = []
|
|
for position, team in enumerate(sorted_teams, 1):
|
|
team.position = position
|
|
standings.append({
|
|
"position": position,
|
|
"team_name": team.team_name,
|
|
"points": team.points,
|
|
"matches_played": team.matches_played,
|
|
"wins": team.wins,
|
|
"draws": team.draws,
|
|
"losses": team.losses,
|
|
"goals_for": team.goals_for,
|
|
"goals_against": team.goals_against,
|
|
"goal_difference": team.goal_difference
|
|
})
|
|
|
|
return standings
|
|
|
|
def validate_team_data(team_data: Dict[str, Any]) -> Dict[str, str]:
|
|
"""
|
|
Validate team data before creation/update.
|
|
|
|
Args:
|
|
team_data: Dictionary containing team data
|
|
|
|
Returns:
|
|
Dict containing error messages if validation fails
|
|
"""
|
|
errors = {}
|
|
|
|
if not team_data.get("team_name"):
|
|
errors["team_name"] = "Team name is required"
|
|
|
|
if not team_data.get("league"):
|
|
errors["league"] = "League is required"
|
|
|
|
if not team_data.get("season"):
|
|
errors["season"] = "Season is required"
|
|
|
|
if team_data.get("matches_played", 0) < 0:
|
|
errors["matches_played"] = "Matches played cannot be negative"
|
|
|
|
return errors
|
|
|
|
def get_team_form(db: Session, team_name: str, last_n: int = 5) -> str:
|
|
"""
|
|
Get team's form for last N matches.
|
|
|
|
Args:
|
|
db: Database session
|
|
team_name: Name of team
|
|
last_n: Number of recent matches to consider
|
|
|
|
Returns:
|
|
String representing form (e.g. 'WWDLL')
|
|
"""
|
|
team = db.query(Glory).filter(
|
|
Glory.team_name == team_name,
|
|
Glory.is_active == True
|
|
).first()
|
|
|
|
if not team:
|
|
return ""
|
|
|
|
form = ""
|
|
total_matches = team.wins + team.draws + team.losses
|
|
|
|
if total_matches < last_n:
|
|
last_n = total_matches
|
|
|
|
# This is simplified - in real app would need to query actual match results
|
|
for _ in range(last_n):
|
|
if team.wins > 0:
|
|
form += "W"
|
|
team.wins -= 1
|
|
elif team.draws > 0:
|
|
form += "D"
|
|
team.draws -= 1
|
|
elif team.losses > 0:
|
|
form += "L"
|
|
team.losses -= 1
|
|
|
|
return form[::-1] |