import datetime
+import time
import re
from pyramid.response import Response
from pyramid.view import view_config
+from webhelpers.paginate import Page, PageURL
from xonstat.models import *
+from xonstat.util import page_url
from sqlalchemy.orm.exc import MultipleResultsFound, NoResultFound
+from sqlalchemy import desc
import logging
@view_config(renderer='player_index.mako')
def player_index(request):
players = DBSession.query(Player)
+
log.debug("testing logging; entered PlayerHandler.index()")
return {'players':players}
player_id = request.matchdict['id']
try:
player = DBSession.query(Player).filter_by(player_id=player_id).one()
- recent_games = DBSession.query("game_id", "server_name", "map_name").\
- from_statement("select g.game_id, s.name as server_name, m.name as map_name "
- "from player_game_stats gs, games g, servers s, maps m "
- "where gs.player_id=:player_id "
- "and gs.game_id = g.game_id "
- "and g.server_id = s.server_id "
- "and g.map_id = m.map_id "
- "order by g.start_dt desc "
- "limit 10 offset 1").\
- params(player_id=player_id).all()
+ recent_games = DBSession.query(PlayerGameStat, Game, Server, Map).\
+ filter(PlayerGameStat.player_id == player_id).\
+ filter(PlayerGameStat.game_id == Game.game_id).\
+ filter(Game.server_id == Server.server_id).\
+ filter(Game.map_id == Map.map_id).\
+ order_by(Game.game_id.desc())[0:10]
- log.debug(recent_games)
except Exception as e:
- raise e
player = None
- return {'player':player, 'recent_games':recent_games}
+ recent_games = None
+ return {'player':player,
+ 'recent_games':recent_games}
+
+
+def player_game_index(request):
+ player_id = request.matchdict['player_id']
+ current_page = request.matchdict['page']
+
+ try:
+ player = DBSession.query(Player).filter_by(player_id=player_id).one()
+
+ games_q = DBSession.query(PlayerGameStat, Game, Server, Map).\
+ filter(PlayerGameStat.player_id == player_id).\
+ filter(PlayerGameStat.game_id == Game.game_id).\
+ filter(Game.server_id == Server.server_id).\
+ filter(Game.map_id == Map.map_id).\
+ order_by(Game.game_id.desc())
+
+ games = Page(games_q, current_page, url=page_url)
+
+
+ except Exception as e:
+ player = None
+ games = None
+ raise e
+
+ return {'player':player,
+ 'games':games}
+
+
+def player_weapon_stats(request):
+ game_id = request.matchdict['game_id']
+ pgstat_id = request.matchdict['pgstat_id']
+ try:
+ pwstats = DBSession.query(PlayerWeaponStat).\
+ filter_by(game_id=game_id).\
+ filter_by(player_game_stat_id=pgstat_id).\
+ order_by(PlayerWeaponStat.weapon_cd).\
+ all()
+
+ except Exception as e:
+ pwstats = None
+ return {'pwstats':pwstats}
##########################################################################
# This is the game views area - only views pertaining to Xonotic
# games and their related information goes here
##########################################################################
+def game_index(request):
+ if 'page' in request.matchdict:
+ current_page = request.matchdict['page']
+ else:
+ current_page = 1
+
+ games_q = DBSession.query(Game, Server, Map).\
+ filter(Game.server_id == Server.server_id).\
+ filter(Game.map_id == Map.map_id).\
+ order_by(Game.game_id.desc())
+
+ games = Page(games_q, current_page, url=page_url)
+
+ return {'games':games}
+
+
def game_info(request):
game_id = request.matchdict['id']
try:
- game = DBSession.query(Game).filter_by(game_id=game_id).one()
- except:
- game = None
- return {'game':game}
+ notfound = False
+
+ (start_dt, game_type_cd, server_id, server_name, map_id, map_name) = \
+ DBSession.query("start_dt", "game_type_cd", "server_id",
+ "server_name", "map_id", "map_name").\
+ from_statement("select g.start_dt, g.game_type_cd, "
+ "g.server_id, s.name as server_name, g.map_id, "
+ "m.name as map_name "
+ "from games g, servers s, maps m "
+ "where g.game_id = :game_id "
+ "and g.server_id = s.server_id "
+ "and g.map_id = m.map_id").\
+ params(game_id=game_id).one()
+
+ player_game_stats = DBSession.query(PlayerGameStat).\
+ from_statement("select * from player_game_stats "
+ "where game_id = :game_id "
+ "order by score desc").\
+ params(game_id=game_id).all()
+ except Exception as inst:
+ notfound = True
+ start_dt = None
+ game_type_cd = None
+ server_id = None
+ server_name = None
+ map_id = None
+ map_name = None
+ player_game_stats = None
+
+ return {'notfound':notfound,
+ 'start_dt':start_dt,
+ 'game_type_cd':game_type_cd,
+ 'server_id':server_id,
+ 'server_name':server_name,
+ 'map_id':map_id,
+ 'map_name':map_name,
+ 'player_game_stats':player_game_stats}
##########################################################################
server_id = request.matchdict['id']
try:
server = DBSession.query(Server).filter_by(server_id=server_id).one()
- except:
+ recent_games = DBSession.query(Game, Server, Map).\
+ filter(Game.server_id == server_id).\
+ filter(Game.server_id == Server.server_id).\
+ filter(Game.map_id == Map.map_id).\
+ order_by(Game.game_id.desc())[0:10]
+
+ except Exception as e:
server = None
- return {'server':server}
+ recent_games = None
+ return {'server':server,
+ 'recent_games':recent_games}
+
+
+def server_game_index(request):
+ server_id = request.matchdict['server_id']
+ current_page = request.matchdict['page']
+
+ try:
+ server = DBSession.query(Server).filter_by(server_id=server_id).one()
+
+ games_q = DBSession.query(Game, Server, Map).\
+ filter(Game.server_id == server_id).\
+ filter(Game.server_id == Server.server_id).\
+ filter(Game.map_id == Map.map_id).\
+ order_by(Game.game_id.desc())
+
+ games = Page(games_q, current_page, url=page_url)
+ except Exception as e:
+ server = None
+ games = None
+ raise e
+
+ return {'games':games,
+ 'server':server}
##########################################################################
def create_player_weapon_stats(session=None, player=None,
- game=None, player_events=None):
+ game=None, pgstat=None, player_events=None):
pwstats = []
for (key,value) in player_events.items():
matched = re.search("acc-(.*?)-cnt-fired", key)
if matched:
- log.debug("Matched key: {0}".format(key))
weapon_cd = matched.group(1)
pwstat = PlayerWeaponStat()
pwstat.player_id = player.player_id
pwstat.game_id = game.game_id
+ pwstat.player_game_stat_id = pgstat.player_game_stat_id
pwstat.weapon_cd = weapon_cd
- try:
- pwstat.max = int(player_events['acc-' + weapon_cd + '-fired'])
- except:
- pwstat.max = 0
- try:
- pwstat.actual = int(player_events['acc-' + weapon_cd + '-hit'])
- except:
- pwstat.actual = 0
- try:
- pwstat.fired = int(player_events['acc-' + weapon_cd + '-cnt-fired'])
- except:
- pwstat.fired = 0
- try:
- pwstat.hit = int(player_events['acc-' + weapon_cd + '-cnt-hit'])
- except:
- pwstat.hit = 0
- try:
- pwstat.frags = int(player_events['acc-' + weapon_cd + '-frags'])
- except:
- pwstat.frags = 0
+
+ if 'n' in player_events:
+ pwstat.nick = player_events['n']
+ else:
+ pwstat.nick = player_events['P']
+
+ if 'acc-' + weapon_cd + '-cnt-fired' in player_events:
+ pwstat.fired = int(round(float(
+ player_events['acc-' + weapon_cd + '-cnt-fired'])))
+ if 'acc-' + weapon_cd + '-fired' in player_events:
+ pwstat.max = int(round(float(
+ player_events['acc-' + weapon_cd + '-fired'])))
+ if 'acc-' + weapon_cd + '-cnt-hit' in player_events:
+ pwstat.hit = int(round(float(
+ player_events['acc-' + weapon_cd + '-cnt-hit'])))
+ if 'acc-' + weapon_cd + '-hit' in player_events:
+ pwstat.actual = int(round(float(
+ player_events['acc-' + weapon_cd + '-hit'])))
+ if 'acc-' + weapon_cd + '-frags' in player_events:
+ pwstat.frags = int(round(float(
+ player_events['acc-' + weapon_cd + '-frags'])))
session.add(pwstat)
pwstats.append(pwstat)
if key in 'V' 'T' 'G' 'M' 'S' 'C' 'R' 'W':
game_meta[key] = value
- if key == 't':
- current_team = value
-
if key == 'P':
# if we were working on a player record already, append
# it and work on a new one (only set team info)
if len(player_events) != 0:
players.append(player_events)
- player_events = {'t':current_team}
+ player_events = {}
player_events[key] = value
-
+
if key == 'e':
(subkey, subvalue) = value.split(' ', 1)
player_events[subkey] = subvalue
-
if key == 'n':
player_events[key] = value
+ if key == 't':
+ player_events[key] = value
except:
# no key/value pair - move on to the next line
pass
return (game_meta, players)
+def create_player_stats(session=None, player=None, game=None,
+ player_events=None):
+ if 'joins' in player_events and 'matches' in player_events\
+ and 'scoreboardvalid' in player_events:
+ pgstat = create_player_game_stat(session=session,
+ player=player, game=game, player_events=player_events)
+ if not re.search('^bot#\d+$', player_events['P']):
+ create_player_weapon_stats(session=session,
+ player=player, game=game, pgstat=pgstat,
+ player_events=player_events)
+
+
@view_config(renderer='stats_submit.mako')
def stats_submit(request):
try:
'S' not in game_meta:
log.debug("Required game meta fields (T, G, M, or S) missing. "\
"Can't continue.")
- raise Exception
+ raise Exception("Required game meta fields (T, G, M, or S) missing.")
+ has_real_players = False
+ for player_events in players:
+ if not player_events['P'].startswith('bot'):
+ if 'joins' in player_events and 'matches' in player_events\
+ and 'scoreboardvalid' in player_events:
+ has_real_players = True
+
+ if not has_real_players:
+ raise Exception("No real players found. Stats ignored.")
+
server = get_or_create_server(session=session, name=game_meta['S'])
gmap = get_or_create_map(session=session, name=game_meta['M'])
else:
winner = None
- # FIXME: don't use python now() here, convert from epoch T value
- game = create_game(session=session, start_dt=datetime.datetime.now(),
+ game = create_game(session=session,
+ start_dt=datetime.datetime(
+ *time.gmtime(float(game_meta['T']))[:6]),
server_id=server.server_id, game_type_cd=game_meta['G'],
map_id=gmap.map_id, winner=winner)
# find or create a record for each player
# and add stats for each if they were present at the end
# of the game
- has_real_players = False
for player_events in players:
- if not player_events['P'].startswith('bot'):
- has_real_players = True
player = get_or_create_player(session=session,
hashkey=player_events['P'])
- if 'joins' in player_events and 'matches' in player_events\
- and 'scoreboardvalid' in player_events:
- pgstat = create_player_game_stat(session=session,
- player=player, game=game, player_events=player_events)
- #pwstats = create_player_weapon_stats(session=session,
- #player=player, game=game, player_events=player_events)
+ log.debug('Creating stats for %s' % player_events['P'])
+ create_player_stats(session=session, player=player, game=game,
+ player_events=player_events)
- if has_real_players:
- session.commit()
- log.debug('Success! Stats recorded.')
- return Response('200 OK')
- else:
- session.rollback()
- log.debug('No real players found. Stats ignored.')
- return {'msg':'No real players found. Stats ignored.'}
+ session.commit()
+ log.debug('Success! Stats recorded.')
+ return Response('200 OK')
except Exception as e:
session.rollback()
raise e