def test_team_updated(self): affected_refs = { 'key': {ndb.Key(Team, 'frc254'), ndb.Key(Team, 'frc604')}, } cache_keys = [ q.cache_key for q in get_affected_queries.team_updated(affected_refs) ] self.assertEqual(len(cache_keys), 16) self.assertTrue(TeamQuery('frc254').cache_key in cache_keys) self.assertTrue(TeamQuery('frc604').cache_key in cache_keys) self.assertTrue(TeamListQuery(0).cache_key in cache_keys) self.assertTrue(TeamListQuery(1).cache_key in cache_keys) self.assertTrue(TeamListYearQuery(2015, 0).cache_key in cache_keys) self.assertTrue(TeamListYearQuery(2015, 1).cache_key in cache_keys) self.assertTrue(TeamListYearQuery(2010, 1).cache_key in cache_keys) self.assertTrue(DistrictTeamsQuery('2015fim').cache_key in cache_keys) self.assertTrue(DistrictTeamsQuery('2015mar').cache_key in cache_keys) self.assertTrue(DistrictTeamsQuery('2016ne').cache_key in cache_keys) self.assertTrue(EventTeamsQuery('2015casj').cache_key in cache_keys) self.assertTrue(EventTeamsQuery('2015cama').cache_key in cache_keys) self.assertTrue(EventTeamsQuery('2010cama').cache_key in cache_keys) self.assertTrue( EventEventTeamsQuery('2015casj').cache_key in cache_keys) self.assertTrue( EventEventTeamsQuery('2015cama').cache_key in cache_keys) self.assertTrue( EventEventTeamsQuery('2010cama').cache_key in cache_keys)
def test_districtteam_updated(self): affected_refs = { 'district_key': {ndb.Key(District, '2015fim'), ndb.Key(District, '2015mar')}, 'team': {ndb.Key(Team, 'frc254'), ndb.Key(Team, 'frc604')} } cache_keys = [q.cache_key for q in get_affected_queries.districtteam_updated(affected_refs)] self.assertEqual(len(cache_keys), 4) self.assertTrue(DistrictTeamsQuery('2015fim').cache_key in cache_keys) self.assertTrue(DistrictTeamsQuery('2015mar').cache_key in cache_keys) self.assertTrue(TeamDistrictsQuery('frc254').cache_key in cache_keys) self.assertTrue(TeamDistrictsQuery('frc604').cache_key in cache_keys)
def team_updated(affected_refs): team_keys = filter(None, affected_refs['key']) event_team_keys_future = EventTeam.query( EventTeam.team.IN([team_key for team_key in team_keys ])).fetch_async(None, keys_only=True) district_team_keys_future = DistrictTeam.query( DistrictTeam.team.IN([team_key for team_key in team_keys ])).fetch_async(None, keys_only=True) queries_and_keys = [] for team_key in team_keys: queries_and_keys.append((TeamQuery(team_key.id()))) page_num = _get_team_page_num(team_key.id()) queries_and_keys.append((TeamListQuery(page_num))) for et_key in event_team_keys_future.get_result(): year = int(et_key.id()[:4]) event_key = et_key.id().split('_')[0] page_num = _get_team_page_num(et_key.id().split('_')[1]) queries_and_keys.append((TeamListYearQuery(year, page_num))) queries_and_keys.append((EventTeamsQuery(event_key))) for dt_key in district_team_keys_future.get_result(): district_key = dt_key.id().split('_')[0] queries_and_keys.append((DistrictTeamsQuery(district_key))) return queries_and_keys
def _render(self, district_abbrev, year=None): self._set_district(district_abbrev) district_teams = DistrictTeamsQuery('{}{}'.format(self.year, self.district_abbrev)).fetch() district_teams_dict = [ModelToDict.teamConverter(team) for team in district_teams] return json.dumps(district_teams_dict, ensure_ascii=True)
def _render(self, district_key, model_type=None): teams, self._last_modified = DistrictTeamsQuery(district_key).fetch( dict_version=3, return_updated=True) if model_type is not None: teams = filter_team_properties(teams, model_type) return json.dumps(teams, ensure_ascii=True, indent=True, sort_keys=True)
def _render(self, district_abbrev, year=None): self._set_district(district_abbrev, self.year) if self.year < 2009: return json.dumps([], ensure_ascii=True) events_future = DistrictEventsQuery( District.renderKeyName(self.year, district_abbrev)).fetch_async() district_teams_future = DistrictTeamsQuery("{}{}".format( year, district_abbrev)).fetch_async() events = events_future.get_result() if not events: return json.dumps([], ensure_ascii=True) EventHelper.sort_events(events) team_totals = DistrictHelper.calculate_rankings( events, district_teams_future.get_result(), self.year) rankings = [] current_rank = 1 for key, points in team_totals: point_detail = {} point_detail["rank"] = current_rank point_detail["team_key"] = key point_detail["event_points"] = {} for event in points["event_points"]: event_key = event[0].key_name point_detail["event_points"][event_key] = event[1] event_details = Event.get_by_id(event_key) point_detail["event_points"][event[0].key_name][ 'district_cmp'] = True if event_details.event_type_enum == EventType.DISTRICT_CMP else False if "rookie_bonus" in points: point_detail["rookie_bonus"] = points["rookie_bonus"] else: point_detail["rookie_bonus"] = 0 point_detail["point_total"] = points["point_total"] rankings.append(point_detail) current_rank += 1 return json.dumps(rankings)
def districtteam_updated(affected_refs): district_keys = filter(None, affected_refs['district_key']) team_keys = filter(None, affected_refs['team']) queries_and_keys = [] for district_key in district_keys: queries_and_keys.append(DistrictTeamsQuery(district_key.id())) for team_key in team_keys: queries_and_keys.append(TeamDistrictsQuery(team_key.id())) return queries_and_keys
def _render(self, district_abbrev, year=None): self._set_district(district_abbrev, self.year) if self.year < 2009: return json.dumps([], ensure_ascii=True) events_future = DistrictEventsQuery(District.renderKeyName(self.year, district_abbrev)).fetch_async() district_teams_future = DistrictTeamsQuery("{}{}".format(year, district_abbrev)).fetch_async() events = events_future.get_result() if not events: return json.dumps([], ensure_ascii=True) EventHelper.sort_events(events) team_totals = DistrictHelper.calculate_rankings(events, district_teams_future.get_result(), self.year) rankings = [] current_rank = 1 for key, points in team_totals: point_detail = {} point_detail["rank"] = current_rank point_detail["team_key"] = key point_detail["event_points"] = {} for event in points["event_points"]: event_key = event[0].key_name point_detail["event_points"][event_key] = event[1] event_details = Event.get_by_id(event_key) point_detail["event_points"][event[0].key_name]['district_cmp'] = True if event_details.event_type_enum == EventType.DISTRICT_CMP else False if "rookie_bonus" in points: point_detail["rookie_bonus"] = points["rookie_bonus"] else: point_detail["rookie_bonus"] = 0 point_detail["point_total"] = points["point_total"] rankings.append(point_detail) current_rank += 1 return json.dumps(rankings)
def get(self, district_key): district = District.get_by_id(district_key) if not district: self.response.out.write( "District {} does not exist!".format(district_key)) return events_future = DistrictEventsQuery(district_key).fetch_async() teams_future = DistrictTeamsQuery(district_key).fetch_async() events = events_future.get_result() for event in events: event.prep_details() EventHelper.sort_events(events) team_totals = DistrictHelper.calculate_rankings( events, teams_future, district.year) rankings = [] current_rank = 1 for key, points in team_totals: point_detail = {} point_detail["rank"] = current_rank point_detail["team_key"] = key point_detail["event_points"] = [] for event, event_points in points["event_points"]: event_points['event_key'] = event.key.id() event_points['district_cmp'] = ( event.event_type_enum == EventType.DISTRICT_CMP or event.event_type_enum == EventType.DISTRICT_CMP_DIVISION) point_detail["event_points"].append(event_points) point_detail["rookie_bonus"] = points.get("rookie_bonus", 0) point_detail["point_total"] = points["point_total"] rankings.append(point_detail) current_rank += 1 if rankings: district.rankings = rankings DistrictManipulator.createOrUpdate(district) if 'X-Appengine-Taskname' not in self.request.headers: # Only write out if not in taskqueue self.response.out.write( "Finished calculating rankings for: {}".format(district_key))
def _render(self, district_abbrev, year=None, explicit_year=False): district = DistrictQuery('{}{}'.format(year, district_abbrev)).fetch() if not district: self.abort(404) events_future = DistrictEventsQuery(district.key_name).fetch_async() # needed for district teams district_teams_future = DistrictTeamsQuery(district.key_name).fetch_async() # needed for valid_years history_future = DistrictHistoryQuery(district.abbreviation).fetch_async() # needed for valid_districts districts_in_year_future = DistrictsInYearQuery(district.year).fetch_async() # needed for active team statuses live_events = [] if year == datetime.datetime.now().year: # Only show active teams for current year live_events = EventHelper.getWeekEvents() live_eventteams_futures = [] for event in live_events: live_eventteams_futures.append(EventTeamsQuery(event.key_name).fetch_async()) events = events_future.get_result() EventHelper.sort_events(events) events_by_key = {} for event in events: events_by_key[event.key.id()] = event week_events = EventHelper.groupByWeek(events) valid_districts = set() districts_in_year = districts_in_year_future.get_result() for dist in districts_in_year: valid_districts.add((dist.display_name, dist.abbreviation)) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) team_keys = set([t.key.id() for t in teams]) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] # Currently Competing Team Status event_team_keys = [] for event, teams_future in zip(live_events, live_eventteams_futures): for team in teams_future.get_result(): if team.key.id() in team_keys: event_team_keys.append(ndb.Key(EventTeam, '{}_{}'.format(event.key.id(), team.key.id()))) # Should be in context cache ndb.get_multi(event_team_keys) # Warms context cache live_events_with_teams = [] for event, teams_future in zip(live_events, live_eventteams_futures): teams_and_statuses = [] has_teams = False for team in teams_future.get_result(): if team.key.id() in team_keys: has_teams = True event_team = EventTeam.get_by_id('{}_{}'.format(event.key.id(), team.key.id())) # Should be in context cache status_str = { 'alliance': EventTeamStatusHelper.generate_team_at_event_alliance_status_string(team.key.id(), event_team.status), 'playoff': EventTeamStatusHelper.generate_team_at_event_playoff_status_string(team.key.id(), event_team.status), } teams_and_statuses.append(( team, event_team.status, status_str )) if has_teams: teams_and_statuses.sort(key=lambda x: x[0].team_number) live_events_with_teams.append((event, teams_and_statuses)) live_events_with_teams.sort(key=lambda x: x[0].name) live_events_with_teams.sort(key=lambda x: EventHelper.distantFutureIfNoStartDate(x[0])) live_events_with_teams.sort(key=lambda x: EventHelper.distantFutureIfNoEndDate(x[0])) # Get valid years district_history = history_future.get_result() valid_years = map(lambda d: d.year, district_history) valid_years = sorted(valid_years) self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': valid_years, 'valid_districts': valid_districts, 'district_name': district.display_name, 'district_abbrev': district_abbrev, 'week_events': week_events, 'events_by_key': events_by_key, 'rankings': district.rankings, 'advancement': district.advancement, 'teams_a': teams_a, 'teams_b': teams_b, 'live_events_with_teams': live_events_with_teams, }) return jinja2_engine.render('district_details.html', self.template_values)
def _render(self, district_abbrev, year=None, explicit_year=False): district_type = DistrictType.abbrevs[district_abbrev] event_keys = Event.query(Event.year == year, Event.event_district_enum == district_type).fetch(None, keys_only=True) if not event_keys: self.abort(404) # needed for district teams district_key = '{}{}'.format(year, district_abbrev) district_teams_future = DistrictTeamsQuery(district_key).fetch_async() # needed for valid_years all_cmp_event_keys_future = Event.query(Event.event_district_enum == district_type, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # needed for valid_districts district_cmp_keys_future = Event.query(Event.year == year, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # to compute valid_districts event_futures = ndb.get_multi_async(event_keys) event_team_keys_future = EventTeam.query(EventTeam.event.IN(event_keys)).fetch_async(None, keys_only=True) team_futures = ndb.get_multi_async(set([ndb.Key(Team, et_key.id().split('_')[1]) for et_key in event_team_keys_future.get_result()])) events = [event_future.get_result() for event_future in event_futures] EventHelper.sort_events(events) district_cmp_futures = ndb.get_multi_async(district_cmp_keys_future.get_result()) team_totals = DistrictHelper.calculate_rankings(events, team_futures, year) valid_districts = set() for district_cmp_future in district_cmp_futures: district_cmp = district_cmp_future.get_result() cmp_dis_type = district_cmp.event_district_enum if cmp_dis_type is None: logging.warning("District event {} has unknown district type!".format(district_cmp.key.id())) else: valid_districts.add((DistrictType.type_names[cmp_dis_type], DistrictType.type_abbrevs[cmp_dis_type])) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': sorted(set([int(event_key.id()[:4]) for event_key in all_cmp_event_keys_future.get_result()])), 'valid_districts': valid_districts, 'district_name': DistrictType.type_names[district_type], 'district_abbrev': district_abbrev, 'events': events, 'team_totals': team_totals, 'teams_a': teams_a, 'teams_b': teams_b, }) path = os.path.join(os.path.dirname(__file__), '../templates/district_details.html') return template.render(path, self.template_values)
def _render(self, district_abbrev, year=None, explicit_year=False): district_type = DistrictType.abbrevs[district_abbrev] event_keys = Event.query(Event.year == year, Event.event_district_enum == district_type).fetch(None, keys_only=True) if not event_keys: self.abort(404) # needed for district teams district_key = '{}{}'.format(year, district_abbrev) district_teams_future = DistrictTeamsQuery(district_key).fetch_async() # needed for valid_years all_cmp_event_keys_future = Event.query(Event.event_district_enum == district_type, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # needed for valid_districts district_cmp_keys_future = Event.query(Event.year == year, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # to compute valid_districts # Needed for active team statuses live_events = EventHelper.getWeekEvents() live_eventteams_futures = [] for event in live_events: live_eventteams_futures.append(EventTeamsQuery(event.key_name).fetch_async()) event_futures = ndb.get_multi_async(event_keys) event_team_keys_future = EventTeam.query(EventTeam.event.IN(event_keys)).fetch_async(None, keys_only=True) team_futures = ndb.get_multi_async(set([ndb.Key(Team, et_key.id().split('_')[1]) for et_key in event_team_keys_future.get_result()])) events = [event_future.get_result() for event_future in event_futures] EventHelper.sort_events(events) district_cmp_futures = ndb.get_multi_async(district_cmp_keys_future.get_result()) team_totals = DistrictHelper.calculate_rankings(events, team_futures, year) valid_districts = set() for district_cmp_future in district_cmp_futures: district_cmp = district_cmp_future.get_result() cmp_dis_type = district_cmp.event_district_enum if cmp_dis_type is None: logging.warning("District event {} has unknown district type!".format(district_cmp.key.id())) else: valid_districts.add((DistrictType.type_names[cmp_dis_type], DistrictType.type_abbrevs[cmp_dis_type])) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] # Currently Competing Team Status live_events_with_teams = EventTeamStatusHelper.buildEventTeamStatus(live_events, live_eventteams_futures, teams) live_events_with_teams.sort(key=lambda x: x[0].name) self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': sorted(set([int(event_key.id()[:4]) for event_key in all_cmp_event_keys_future.get_result()])), 'valid_districts': valid_districts, 'district_name': DistrictType.type_names[district_type], 'district_abbrev': district_abbrev, 'events': events, 'team_totals': team_totals, 'teams_a': teams_a, 'teams_b': teams_b, 'live_events_with_teams': live_events_with_teams, }) path = os.path.join(os.path.dirname(__file__), '../templates/district_details.html') return template.render(path, self.template_values)
def _render(self, district_abbrev, year=None, explicit_year=False): district = DistrictQuery('{}{}'.format(year, district_abbrev)).fetch() if not district: self.abort(404) events_future = DistrictEventsQuery(district.key_name).fetch_async() # needed for district teams district_teams_future = DistrictTeamsQuery(district.key_name).fetch_async() # needed for valid_years history_future = DistrictHistoryQuery(district.abbreviation).fetch_async() # needed for valid_districts districts_in_year_future = DistrictsInYearQuery(district.year).fetch_async() # Temp disabled on 2017-02-18 -fangeugene # # Needed for active team statuses # live_events = [] # if year == datetime.datetime.now().year: # Only show active teams for current year # live_events = EventHelper.getWeekEvents() # live_eventteams_futures = [] # for event in live_events: # live_eventteams_futures.append(EventTeamsQuery(event.key_name).fetch_async()) events = events_future.get_result() EventHelper.sort_events(events) events_by_key = {} for event in events: events_by_key[event.key.id()] = event week_events = EventHelper.groupByWeek(events) valid_districts = set() districts_in_year = districts_in_year_future.get_result() for dist in districts_in_year: valid_districts.add((dist.display_name, dist.abbreviation)) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] # Temp disabled on 2017-02-18 -fangeugene # # Currently Competing Team Status # live_events_with_teams = EventTeamStatusHelper.buildEventTeamStatus(live_events, live_eventteams_futures, teams) # live_events_with_teams.sort(key=lambda x: x[0].name) # Get valid years district_history = history_future.get_result() valid_years = map(lambda d: d.year, district_history) valid_years = sorted(valid_years) self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': valid_years, 'valid_districts': valid_districts, 'district_name': district.display_name, 'district_abbrev': district_abbrev, 'week_events': week_events, 'events_by_key': events_by_key, 'rankings': district.rankings, 'teams_a': teams_a, 'teams_b': teams_b, # 'live_events_with_teams': live_events_with_teams, # Temp disabled on 2017-02-18 -fangeugene }) return jinja2_engine.render('district_details.html', self.template_values)
def _render(self, district_abbrev, year=None, explicit_year=False): district = DistrictQuery('{}{}'.format(year, district_abbrev)).fetch() if not district: self.abort(404) events_future = DistrictEventsQuery(district.key_name).fetch_async() # needed for district teams district_teams_future = DistrictTeamsQuery( district.key_name).fetch_async() # needed for valid_years history_future = DistrictHistoryQuery( district.abbreviation).fetch_async() # needed for valid_districts districts_in_year_future = DistrictsInYearQuery( district.year).fetch_async() # needed for active team statuses live_events = [] if year == datetime.datetime.now( ).year: # Only show active teams for current year live_events = EventHelper.getWeekEvents() live_eventteams_futures = [] for event in live_events: live_eventteams_futures.append( EventTeamsQuery(event.key_name).fetch_async()) events = events_future.get_result() EventHelper.sort_events(events) events_by_key = {} for event in events: events_by_key[event.key.id()] = event week_events = EventHelper.groupByWeek(events) valid_districts = set() districts_in_year = districts_in_year_future.get_result() for dist in districts_in_year: valid_districts.add((dist.display_name, dist.abbreviation)) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) team_keys = set([t.key.id() for t in teams]) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] # Currently Competing Team Status event_team_keys = [] for event, teams_future in zip(live_events, live_eventteams_futures): for team in teams_future.get_result(): if team.key.id() in team_keys: event_team_keys.append( ndb.Key(EventTeam, '{}_{}'.format( event.key.id(), team.key.id()))) # Should be in context cache ndb.get_multi(event_team_keys) # Warms context cache live_events_with_teams = [] for event, teams_future in zip(live_events, live_eventteams_futures): teams_and_statuses = [] has_teams = False for team in teams_future.get_result(): if team.key.id() in team_keys: has_teams = True event_team = EventTeam.get_by_id('{}_{}'.format( event.key.id(), team.key.id())) # Should be in context cache status_str = { 'alliance': EventTeamStatusHelper. generate_team_at_event_alliance_status_string( team.key.id(), event_team.status), 'playoff': EventTeamStatusHelper. generate_team_at_event_playoff_status_string( team.key.id(), event_team.status), } teams_and_statuses.append( (team, event_team.status, status_str)) if has_teams: teams_and_statuses.sort(key=lambda x: x[0].team_number) live_events_with_teams.append((event, teams_and_statuses)) live_events_with_teams.sort(key=lambda x: x[0].name) live_events_with_teams.sort( key=lambda x: EventHelper.distantFutureIfNoStartDate(x[0])) live_events_with_teams.sort( key=lambda x: EventHelper.distantFutureIfNoEndDate(x[0])) # Get valid years district_history = history_future.get_result() valid_years = map(lambda d: d.year, district_history) valid_years = sorted(valid_years) self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': valid_years, 'valid_districts': valid_districts, 'district_name': district.display_name, 'district_abbrev': district_abbrev, 'week_events': week_events, 'events_by_key': events_by_key, 'rankings': district.rankings, 'advancement': district.advancement, 'teams_a': teams_a, 'teams_b': teams_b, 'live_events_with_teams': live_events_with_teams, }) return jinja2_engine.render('district_details.html', self.template_values)
def _render(self, district_abbrev, year=None, explicit_year=False): district_type = DistrictType.abbrevs[district_abbrev] event_keys = Event.query(Event.year == year, Event.event_district_enum == district_type).fetch(None, keys_only=True) if not event_keys: self.abort(404) # needed for district teams district_key = '{}{}'.format(year, district_abbrev) district_teams_future = DistrictTeamsQuery(district_key).fetch_async() # needed for valid_years all_cmp_event_keys_future = Event.query(Event.event_district_enum == district_type, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # needed for valid_districts district_cmp_keys_future = Event.query(Event.year == year, Event.event_type_enum == EventType.DISTRICT_CMP).fetch_async(None, keys_only=True) # to compute valid_districts # Needed for active team statuses live_events = [] if year == datetime.datetime.now().year: # Only show active teams for current year live_events = EventHelper.getWeekEvents() live_eventteams_futures = [] for event in live_events: live_eventteams_futures.append(EventTeamsQuery(event.key_name).fetch_async()) event_futures = ndb.get_multi_async(event_keys) event_team_keys_future = EventTeam.query(EventTeam.event.IN(event_keys)).fetch_async(None, keys_only=True) team_futures = ndb.get_multi_async(set([ndb.Key(Team, et_key.id().split('_')[1]) for et_key in event_team_keys_future.get_result()])) events = [event_future.get_result() for event_future in event_futures] EventHelper.sort_events(events) week_events = EventHelper.groupByWeek(events) district_cmp_futures = ndb.get_multi_async(district_cmp_keys_future.get_result()) team_totals = DistrictHelper.calculate_rankings(events, team_futures, year) valid_districts = set() for district_cmp_future in district_cmp_futures: district_cmp = district_cmp_future.get_result() cmp_dis_type = district_cmp.event_district_enum if cmp_dis_type is None: logging.warning("District event {} has unknown district type!".format(district_cmp.key.id())) else: valid_districts.add((DistrictType.type_names[cmp_dis_type], DistrictType.type_abbrevs[cmp_dis_type])) valid_districts = sorted(valid_districts, key=lambda (name, _): name) teams = TeamHelper.sortTeams(district_teams_future.get_result()) num_teams = len(teams) middle_value = num_teams / 2 if num_teams % 2 != 0: middle_value += 1 teams_a, teams_b = teams[:middle_value], teams[middle_value:] # Currently Competing Team Status live_events_with_teams = EventTeamStatusHelper.buildEventTeamStatus(live_events, live_eventteams_futures, teams) live_events_with_teams.sort(key=lambda x: x[0].name) self.template_values.update({ 'explicit_year': explicit_year, 'year': year, 'valid_years': sorted(set([int(event_key.id()[:4]) for event_key in all_cmp_event_keys_future.get_result()])), 'valid_districts': valid_districts, 'district_name': DistrictType.type_names[district_type], 'district_abbrev': district_abbrev, 'week_events': week_events, 'team_totals': team_totals, 'teams_a': teams_a, 'teams_b': teams_b, 'live_events_with_teams': live_events_with_teams, }) return jinja2_engine.render('district_details.html', self.template_values)