matias-cataife commited on
Commit
00dbec9
·
verified ·
1 Parent(s): bb5937d

browse MV db: routes/player.py

Browse files
Files changed (1) hide show
  1. routes/player.py +35 -25
routes/player.py CHANGED
@@ -1,4 +1,4 @@
1
- """GET /api/player/{player_id}?season=... — full detail row."""
2
 
3
  import json
4
  import math
@@ -10,11 +10,19 @@ from data import get_player
10
 
11
  router = APIRouter()
12
 
 
 
 
 
 
 
 
 
 
 
13
 
14
  def _clean(v):
15
- if v is None:
16
- return None
17
- if isinstance(v, float) and (math.isnan(v) or pd.isna(v)):
18
  return None
19
  if isinstance(v, (pd.Timestamp,)):
20
  return v.isoformat()
@@ -26,17 +34,7 @@ def player_detail(player_id: str, season: str):
26
  res = get_player(player_id, season)
27
  if not res:
28
  raise HTTPException(404, f'player {player_id} season {season} not found')
29
-
30
  row = res['row']
31
- blocks = {k.replace('block_', ''): float(v) for k, v in row.items()
32
- if k.startswith('block_') and pd.notna(v)}
33
-
34
- cm = row.get('comp_minutes')
35
- if isinstance(cm, str) and cm.strip().startswith('{'):
36
- try:
37
- cm = json.loads(cm)
38
- except Exception:
39
- cm = None
40
 
41
  inj = row.get('tm_injuries')
42
  if isinstance(inj, str) and inj.strip().startswith('['):
@@ -47,6 +45,17 @@ def player_detail(player_id: str, season: str):
47
  elif not isinstance(inj, list):
48
  inj = None
49
 
 
 
 
 
 
 
 
 
 
 
 
50
  return {
51
  'playerId': str(row['playerId']),
52
  'season': row.get('Temporada'),
@@ -56,18 +65,19 @@ def player_detail(player_id: str, season: str):
56
  'pos': row.get('Posicion'),
57
  'minutos': int(row.get('Minutos totales') or 0),
58
  'partidos': int(row.get('Partidos jugados') or 0),
59
- 'n_competitions': int(row.get('n_competitions') or 1),
60
- 'comp_minutes': cm,
61
- 'age': _clean(row.get('age')) or _clean(row.get('tm_age')),
62
- 'nationality': _clean(row.get('nationality')) or _clean(row.get('tm_nationality')),
63
- 'foot': _clean(row.get('foot')) or _clean(row.get('tm_foot')),
64
- 'height': _clean(row.get('height')) or _clean(row.get('tm_height')),
65
- 'mv': _clean(row.get('tm_market_value')),
66
- 'contract': _clean(row.get('tm_contract_until')) or _clean(row.get('contract_end_date')),
67
- 'photo': _clean(row.get('tm_photo')),
 
68
  'tm_id': _clean(row.get('tm_id')),
69
  'tm_url': _clean(row.get('tm_url')),
70
- 'blocks': blocks,
71
- 'history': res['history'],
72
  'injuries': inj,
 
73
  }
 
1
+ """GET /api/player/{player_id}?season=... — full detail for the browse drawer."""
2
 
3
  import json
4
  import math
 
10
 
11
  router = APIRouter()
12
 
13
+ # identity / meta columns excluded from the generic "stats" grid
14
+ META_COLS = {
15
+ 'playerId', 'tm_id', 'Jugador', 'Temporada', 'nationality', 'age', 'date_of_birth',
16
+ 'Equipo', 'Competencia', 'Posicion', 'Posiciones', 'Estado', 'teamId', 'comps_list',
17
+ 'comp_minutes', 'n_competitions', 'Minutos totales', 'Partidos jugados',
18
+ 'mv_eos', 'mv_eos_prev', 'tm_mv_now', 'mv_source', 'match_path', 'match_conf',
19
+ 'tm_position', 'tm_foot', 'tm_height', 'tm_contract_until', 'tm_url', 'tm_injuries',
20
+ 'n_opta_ids',
21
+ }
22
+
23
 
24
  def _clean(v):
25
+ if v is None or (isinstance(v, float) and (math.isnan(v) or pd.isna(v))):
 
 
26
  return None
27
  if isinstance(v, (pd.Timestamp,)):
28
  return v.isoformat()
 
34
  res = get_player(player_id, season)
35
  if not res:
36
  raise HTTPException(404, f'player {player_id} season {season} not found')
 
37
  row = res['row']
 
 
 
 
 
 
 
 
 
38
 
39
  inj = row.get('tm_injuries')
40
  if isinstance(inj, str) and inj.strip().startswith('['):
 
45
  elif not isinstance(inj, list):
46
  inj = None
47
 
48
+ history = [{k: _clean(v) for k, v in h.items()} for h in res['history']]
49
+
50
+ # all remaining numeric stat columns, non-null
51
+ stats = {}
52
+ for k, v in row.items():
53
+ if k in META_COLS:
54
+ continue
55
+ cv = _clean(v)
56
+ if cv is not None and isinstance(cv, (int, float)):
57
+ stats[k] = round(float(cv), 3)
58
+
59
  return {
60
  'playerId': str(row['playerId']),
61
  'season': row.get('Temporada'),
 
65
  'pos': row.get('Posicion'),
66
  'minutos': int(row.get('Minutos totales') or 0),
67
  'partidos': int(row.get('Partidos jugados') or 0),
68
+ 'age': _clean(row.get('age')),
69
+ 'nationality': _clean(row.get('nationality')),
70
+ 'foot': _clean(row.get('tm_foot')),
71
+ 'height': _clean(row.get('tm_height')),
72
+ 'mv_eos': _clean(row.get('mv_eos')),
73
+ 'mv_eos_prev': _clean(row.get('mv_eos_prev')),
74
+ 'mv_now': _clean(row.get('tm_mv_now')),
75
+ 'mv_source': _clean(row.get('mv_source')),
76
+ 'match_conf': _clean(row.get('match_conf')),
77
+ 'contract': _clean(row.get('tm_contract_until')),
78
  'tm_id': _clean(row.get('tm_id')),
79
  'tm_url': _clean(row.get('tm_url')),
80
+ 'history': history,
 
81
  'injuries': inj,
82
+ 'stats': stats,
83
  }