Example #1
0
def merge(request):
    '''A simple merge view. The merge.mako template does the work.'''
    s = DBSession()

    # only do a merge if we have all of the required data
    if request.params.has_key("csrf_token"):
        # check the token to prevent request forgery
        st = request.session.get_csrf_token()
        check_csrf_token(request)

        if request.params.has_key("w_pid") and request.params.has_key("l_pid"):
            w_pid = request.params.get("w_pid")
            l_pid = request.params.get("l_pid")

            # do the merge, hope for the best!
            try:
                s.execute("select merge_players(:w_pid, :l_pid)", {
                    "w_pid": w_pid,
                    "l_pid": l_pid
                })

                s.commit()

                request.session.flash(
                    "Successfully merged player %s into %s!" % (l_pid, w_pid),
                    "success")

            except:
                s.rollback()

                request.session.flash(
                    "Could not merge player %s into %s." % (l_pid, w_pid),
                    "failure")

    return {}
Example #2
0
def search_q(nick=None, server_name=None, map_name=None, create_dt=None,
        gametypes=[]):
    session     = DBSession()
    result_type = None
    q           = None

    # player-only searches
    if nick and not server_name and not map_name and not create_dt \
        and len(gametypes) < 1:
        result_type = "player"
        q = session.query(Player)
        if nick:
            q = q.filter(
                    func.upper(Player.stripped_nick).like('%'+nick.upper()+'%')).\
                    filter(Player.player_id > 2).\
                    filter(Player.active_ind == True).\
                    order_by(Player.player_id)

    # server-only searches
    elif server_name and not nick and not map_name and not create_dt and len(gametypes) < 1:
        result_type = "server"
        q = session.query(Server)
        if server_name:
            q = q.filter(func.upper(Server.name).like('%'+server_name.upper()+'%'))\
                .filter(Server.active_ind)\
                .order_by(Server.server_id)

    # map-only searches
    elif map_name and not nick and not server_name and not create_dt \
        and len(gametypes) < 1:
        result_type = "map"
        q = session.query(Map)
        if map_name:
            q = q.filter(func.upper(Map.name).\
                    like('%'+map_name.upper()+'%')).\
                    order_by(Map.map_id)

    # game searches (all else)
    else:
        result_type = "game"
        q = session.query(Game, Server, Map).\
                filter(Game.server_id == Server.server_id).\
                filter(Server.active_ind).\
                filter(Game.map_id == Map.map_id).\
                order_by(Game.game_id.desc())
        if len(gametypes) > 0:
            q = q.filter(Game.game_type_cd.in_(gametypes))
        if nick:
            q = q.filter(func.upper(PlayerGameStat.stripped_nick).\
                    like('%'+nick.upper()+'%')).\
                filter(PlayerGameStat.game_id == Game.game_id)
        if map_name:
            q = q.filter(func.upper(Map.name).\
                    like('%'+map_name.upper()+'%'))
        if server_name:
            q = q.filter(func.upper(Server.name).\
                    like('%'+server_name.upper()+'%'))

    return (result_type, q)
Example #3
0
def submit_stats(request):
    """
    Entry handler for POST stats submissions.
    """
    # placeholder for the actual session
    session = None

    try:
        log.debug("\n----- BEGIN REQUEST BODY -----\n" + request.body +
                  "----- END REQUEST BODY -----\n\n")

        (idfp, status) = verify_request(request)
        try:
            submission = Submission(request.body, request.headers)
        except:
            msg = "Invalid submission"
            log.debug(msg)
            raise pyramid.httpexceptions.HTTPUnprocessableEntity(
                body=msg, content_type="text/plain")

        do_precondition_checks(request.registry.settings, submission)

        #######################################################################
        # Actual setup (inserts/updates) below here
        #######################################################################
        session = DBSession()

        # All game types create Game, Server, Map, and Player records
        # the same way.
        server = get_or_create_server(
            session=session,
            hashkey=idfp,
            name=submission.server_name,
            revision=submission.revision,
            ip_addr=get_remote_addr(request),
            port=submission.port_number,
            impure_cvars=submission.impure_cvar_changes)

        gmap = get_or_create_map(session, submission.map_name)

        game = create_game(session=session,
                           game_type_cd=submission.game_type_cd,
                           mod=submission.mod,
                           server_id=server.server_id,
                           map_id=gmap.map_id,
                           match_id=submission.match_id,
                           start_dt=datetime.datetime.utcnow(),
                           duration=submission.duration)

        events_by_hashkey = {
            elem["P"]: elem
            for elem in submission.humans + submission.bots
        }
        players_by_hashkey = get_or_create_players(session, events_by_hashkey)

        pgstats = []
        elo_pgstats = []
        player_ids = []
        hashkeys_by_player_id = {}
        for hashkey, player in players_by_hashkey.items():
            events = events_by_hashkey[hashkey]

            pgstat = create_game_stat(session, game, gmap, player, events)
            pgstats.append(pgstat)

            if should_do_frag_matrix(submission.game_type_cd):
                create_frag_matrix(session, submission.player_indexes, pgstat,
                                   events)

            # player ranking opt-out
            if 'r' in events and events['r'] == '0':
                log.debug(
                    "Excluding player {} from ranking calculations (opt-out)".
                    format(pgstat.player_id))
            else:
                elo_pgstats.append(pgstat)

            if player.player_id > 1:
                create_anticheats(session, pgstat, game, player, events)

            if player.player_id > 2:
                player_ids.append(player.player_id)
                hashkeys_by_player_id[player.player_id] = hashkey

            if should_do_weapon_stats(
                    submission.game_type_cd) and player.player_id > 1:
                create_weapon_stats(session, submission.version, game, player,
                                    pgstat, events)

        # player_ids for human players get stored directly on games for fast indexing
        game.players = player_ids

        for events in submission.teams:
            create_team_stat(session, game, events)

        if server.elo_ind and gametype_elo_eligible(submission.game_type_cd):
            ep = EloProcessor(session, game, elo_pgstats)
            ep.save(session)
            elos = ep.wip
        else:
            elos = {}

        session.commit()
        log.debug('Success! Stats recorded.')

        # ranks are fetched after we've done the "real" processing
        ranks = get_ranks(session, player_ids, submission.game_type_cd)

        # plain text response
        request.response.content_type = 'text/plain'

        return {
            "now": calendar.timegm(datetime.datetime.utcnow().timetuple()),
            "server": server,
            "game": game,
            "gmap": gmap,
            "player_ids": player_ids,
            "hashkeys": hashkeys_by_player_id,
            "elos": elos,
            "ranks": ranks,
        }

    except Exception as e:
        if session:
            session.rollback()
        raise e