def create_initial_default_prize_structures(): site_sport_manager = SiteSportManager() for sport in SiteSportManager.SPORTS: created_default_prize_structures = 0 site_sport = site_sport_manager.get_site_sport(sport) for buyin in DefaultPrizeStructureManager.default_buyin_amounts: for size, payout_spots in DefaultPrizeStructureManager.default_contest_sizes: # get the prize structure based on the buyin and # of payout spots prize_structures = PrizeStructure.objects.filter( generator__buyin=buyin, generator__payout_spots=payout_spots) prize_structure = None # loop until we find it for ps in prize_structures: if size == ps.get_entries(): prize_structure = ps break # we found it if prize_structure is None: logger.warning( ("No PrizeStructure for buyin: %s payout_spots: %s. You can add them " "manually though!") % (buyin, payout_spots)) # raise Exception(err_msg) else: # # create the default prize structures for the SiteSport dps = DefaultPrizeStructure() dps.site_sport = site_sport dps.prize_structure = prize_structure dps.save() created_default_prize_structures += 1 logger.info("%s created_default_prize_structures for %s" % ( created_default_prize_structures, sport))
def get_player_stats_model_class(self): site_sport_manager = SiteSportManager() site_sport = site_sport_manager.get_site_sport(self.sport) player_stats_model_classes = site_sport_manager.get_player_stats_classes( site_sport) return player_stats_model_classes[ 0] # return first element - nfl only has 1
def __init__(self, sport, prize_structure, start, duration, draft_group=None, user_entry_limit=None, entry_cap=None, set_name=True): """ :param sport: the name of the sport :param prize_structure: the prize.models.PrizeStructure :param start: datetime object, the scheduled start time :param duration: the integer number of minutes from the start until the end that makes a range of datetime objects, between which to use the sport's games. :param draft_group: if specified, the DraftGroup to use. otherwise get an existing one using the DraftGroupManager class. """ site_sport_manager = SSM() self.sport = sport self.site_sport = site_sport_manager.get_site_sport(self.sport) # validate and set the start datetime self.start = self.validate_start(start) # validate and set the duration (integer minutes) self.duration = self.validate_duration(duration) # validate and set the prize_structure model self.prize_structure = self.validate_prize_structure(prize_structure) # if a draft_group is specified, validate it self.draft_group = draft_group if self.draft_group is not None: self.draft_group = self.validate_draft_group(draft_group) # set the user entry limit (the max # of Entrys from one user for this ContestPool) self.user_entry_limit = self.USER_ENTRY_LIMIT if user_entry_limit is not None: self.user_entry_limit = user_entry_limit # set the entry cap (if there is one, typically there is not) self.entry_cap = self.ENTRY_CAP if entry_cap is not None: self.entry_cap = entry_cap # whether or not to set a name at creation time self.set_name = set_name # skill level slm = SkillLevelManager() self.skill_level = slm.get_for_amount(self.prize_structure.buyin)
def __init__(self, sport): self.sport = sport self.verbose = False self.debug_limit = 0 self.pbp_parent_api = 'pbp' self.stats_parent_api = 'stats' self.delay_seconds = 5 self.delay_seconds_behind = 0 ssm = SiteSportManager() self.site_sport = ssm.get_site_sport(self.sport) self.player_class = ssm.get_player_class(self.site_sport)
def create_player_stats(sport=DEFAULT_SPORT): """ return a newly created player who could fit in the default roster. if 'roster' is None, we will call Dummy.create_roster() and use that data :param sport: :param roster: :return: """ # ('QB',1,0,True) :['QB'], position = None for rs_tuple, pos_list in Dummy.DEFAULT_ROSTER_MAP.items(): for pos_name in pos_list: site_sport, c = SiteSport.objects.get_or_create(name=sport) position, c = Position.objects.get_or_create( name=pos_name, site_sport=site_sport) break break if position is None: raise Exception( '>>>>> Dummy.create_player_stats() couldnt find any positions in roster' ) dt_now = timezone.now() unix_ts = dt_now.strftime('%s') # unix timestamp as srid ... not bad ssm = SiteSportManager() site_sport = ssm.get_site_sport(sport) game = Dummy.create_game(srid='game' + unix_ts, site_sport=site_sport) player = Dummy.create_player(srid='player' + unix_ts, position=position, team=game.home, site_sport=site_sport) if sport == Dummy.DEFAULT_SPORT: site_sport = None # hack for backwards compatability, to not break older code player_stats = Dummy.create_player_stats_model(game, player, site_sport) return player_stats
def handle(self, *args, **options): """ calculate a single players salary (for debugging purposes) using the sports main salary algorithm. this command will infer the sport using SiteSportManager so all that needs to be specified is the player srid! """ # collect the player srids passed as arguments player_srids = [] for srid in options['player']: player_srids.append(srid) player_srid = player_srids[0] # get the first one print('looking for player:', str(player_srid)) # find the sports.<sport>.models.Player object ssm = SiteSportManager() player = None site_sport = None # the sport (the string name) of the sport the player was found in for sport in SiteSportManager.SPORTS: site_sport = ssm.get_site_sport(sport) player_class = ssm.get_player_class(site_sport) try: player = player_class.objects.get(srid=player_srid) break except player_class.DoesNotExist: #self.stdout.write('checked %s for Player object but they werent found'%sport) pass # hopefully we found the player by now if player is None: self.stdout.write('player [%s] not found in any sport!' % player_srid) return # else: # self.stdout.write('player:', str(player)) # generate the salary for this player specifically, printing out all the player stats # objects used and the weighting involved in the calculations for debugging purposes. sg = SportSalaryGenerator(sport=site_sport.name, debug_srid=player_srid) sg.generate_salaries()
def create_player_stats_model(self, game_srid, player_srid, my_player_stats_instance): """ create a new PlayerStats model instance from the fields of the 'mongo_obj' :param mongo_obj: :return: """ site_sport_manager = SiteSportManager() site_sport = site_sport_manager.get_site_sport('nfl') player_model_class = site_sport_manager.get_player_class(site_sport) game_model_class = site_sport_manager.get_game_class(site_sport) try: player = player_model_class.objects.get(srid=player_srid) except player_model_class.DoesNotExist: # if they were never in the database, they wont be in draft group and we should not # deal with that here! - Probably means they are defensive players. return player_stats_model_class = self.get_player_stats_model_class() # get new instance player_stats = player_stats_model_class() # set all properties with these fieldnames to 0 player_stats.position = player.position # use the position from their Player object player_stats.srid_game = game_srid player_stats.game = game_model_class.objects.get(srid=game_srid) player_stats.srid_player = player_srid player_stats.player = player for fieldname, var in my_player_stats_instance.get_vars().items(): setattr(player_stats, fieldname, var) player_stats.save() logger.info( 'Missing PlayerStats model created for player: %s | srid: %s' % (player, player_srid))
def get_player_model_class(self): if self.player_model_class is None: ssm = SiteSportManager() site_sport = ssm.get_site_sport(self.sport) self.player_model_class = ssm.get_player_class(site_sport) return self.player_model_class
def get_player_model_class(self, sport): ssm = SiteSportManager() site_sport = ssm.get_site_sport(sport) sport_player_model_class = ssm.get_player_class(site_sport) return sport_player_model_class
class ScheduleDay(object): """ This is a factory that produces SportDays for each type of sport (MlbDay, NhlDay, etc). A SportDay is an object that has some properties that tell us when games for that sport usually start. With this info a Block is created. A block is a group of IRL games. """ tzinfo_est = pytz_timezone('America/New_York') datetime_format_date = '%Y-%m-%d' datetime_format_time = '%I:%M %p' default_season_types = ['reg', 'pst'] class SportDay(object): tzinfo_est = pytz_timezone('America/New_York') datetime_format_date = '%Y-%m-%d' datetime_format_time = '%I:%M %p' weekday = None saturday = None sunday = None weekday_values = [0, 1, 2, 3, 4] saturday_values = [5] sunday_values = [6] def __init__(self, site_sport, datetime_obj, games): self.site_sport = site_sport self.the_datetime = datetime_obj self.games = games # self.get_data() self.data = { 'weekday': None, 'type': None, 'total': None, 'include': None, 'exclude': None, 'include_times': None, 'exclude_times': None, 'include_pct': None, } self.get_data() def get_excluded_game_ids(self): return self.data['exclude'] def get_excluded_games(self): return self.games.filter(pk__in=self.get_excluded_game_ids()) def get_included_game_ids(self): return self.data['include'] def get_included_games(self): return self.games.filter(pk__in=self.get_included_game_ids()) def get_cutoff(self): """ get the 'cutoff_time' from the internal data """ return self.data['cutoff_time'] # def get_cutoff_datetime(self): # return self.data['cutoff_datetime'] def get_data(self): if self.games.count() == 0: return None weekday = None # 0 - 6 day index. its poorly named, but its NOT the self.weekday time() cutoff include = [] exclude = [] include_times = [] exclude_times = [] for game in self.games: if weekday is None: # weekday = game.start.weekday() # ... i think its actually this: weekday = self.get_local_datetime(game.start).weekday() datetime_start_est = self.get_local_datetime(game.start) if weekday in [0, 1, 2, 3, 4] and self.include_in_weekday_block(datetime_start_est): include.append(game.pk) include_times.append(self.get_str_local_time(game.start)) elif weekday in [5] and self.include_in_saturday_block(datetime_start_est): include.append(game.pk) include_times.append(self.get_str_local_time(game.start)) elif weekday in [6] and self.include_in_sunday_block(datetime_start_est): include.append(game.pk) include_times.append(self.get_str_local_time(game.start)) else: exclude.append(game.pk) exclude_times.append(self.get_str_local_time(game.start)) # self.data = { # 'weekday' : weekday, # 'type' : self.weekday_to_str(weekday), # 'total' : self.games.count(), # 'include' : include, # 'exclude' : exclude, # 'include_times' : include_times, # 'exclude_times' : exclude_times, # 'include_pct' : float(float(len(include)) / float(self.games.count())) # } self.save_internal_data(weekday, self.weekday_to_str(weekday), self.games.count(), include, exclude, include_times, exclude_times) return self.data def save_internal_data(self, weekday, type, total, include, exclude, include_times, exclude_times): self.data = { 'weekday': weekday, 'type': type, 'total': total, 'include': include, 'exclude': exclude, 'include_times': include_times, 'exclude_times': exclude_times, 'include_pct': float(float(len(include)) / float(total)), 'cutoff_time': self.get_weekday_cutoff_time(weekday), } def __str__(self): include_pct = self.data['include_pct'] if include_pct is None: include_pct = 0.0 else: include_pct = int(include_pct * 100.0) included = self.data['include'] if included is None: included = 0 else: included = len(included) return 'type: %s, weekday:%s, included games:%s pct (%s of %s) >>> included times %s ((excluded times %s))' \ '' % (self.data['type'], self.data['weekday'], include_pct, included, str(self.data['total']), str(self.data['include_times']), str(self.data['exclude_times'])) def weekday_to_str(self, weekday): if weekday in self.weekday_values: return 'Weekday' elif weekday in self.saturday_values: return 'Saturday' elif weekday in self.sunday_values: return 'Sunday' def get_weekday_cutoff_time(self, weekday): """ this is an internal method. use method get_cutoff() to retrieve the datetime.time() specifically related to the day of this instance after this sportday has been updated """ if weekday in self.weekday_values: return self.weekday elif weekday in self.saturday_values: return self.saturday elif weekday in self.sunday_values: return self.sunday def get_local_datetime(self, utc_datetime_obj): return utc_datetime_obj.astimezone(self.tzinfo_est) def get_str_local_time(self, datetime_obj): local_dt = datetime_obj.astimezone(self.tzinfo_est) return local_dt.strftime(self.datetime_format_time) def get_str_local_date(self, datetime_obj): local_dt = datetime_obj.astimezone(self.tzinfo_est) return local_dt.strftime(self.datetime_format_date) def include_in_weekday_block(self, datetime_obj): return datetime_obj.time() >= self.weekday def include_in_saturday_block(self, datetime_obj): return datetime_obj.time() >= self.saturday def include_in_sunday_block(self, datetime_obj): return datetime_obj.time() >= self.sunday class MlbDay(SportDay): weekday = time(19, 0) # 7pm + saturday = time(16, 0) # 4pm + sunday = time(13, 0) # 1pm + def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) class NhlDay(SportDay): weekday = time(19, 0) # 7pm + saturday = time(19, 0) # 7pm + sunday = time(15, 0) # 3pm + def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) class NbaDay(SportDay): weekday = time(19, 0) # 7pm + saturday = time(19, 0) # 7pm + sunday = time(18, 0) # 6pm + def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) class NflDay(SportDay): weekday = time(19, 0) # 7pm + (thursday night games) saturday = time(13, 0) # 1pm + (saturday games) sunday = time(13, 0) # 1pm + (sunday games) def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) @staticmethod def factory(sport): if sport == 'nba': return ScheduleDay.NbaDay if sport == 'nhl': return ScheduleDay.NhlDay if sport == 'mlb': return ScheduleDay.MlbDay if sport == 'nfl': return ScheduleDay.NflDay else: raise Exception('ScheduleDay for sport: %s - UNIMPLEMENTED' % sport) # def get_data(self): # if self.games.count() == 0: # return None # # weekday = None # include = [] # exclude = [] # include_times = [] # exclude_times = [] # for game in self.games: # # if weekday is None: # weekday = game.start.weekday() # # datetime_start_est = self.get_local_datetime(game.start) # if weekday in [0,1,2,3,4] and self.include_in_weekday_block(datetime_start_est): # include.append(game.pk) # include_times.append(self.get_str_local_time(game.start)) # elif weekday in [5] and self.include_in_saturday_block(datetime_start_est): # include.append(game.pk) # include_times.append(self.get_str_local_time(game.start)) # elif weekday in [6] and self.include_in_sunday_block(datetime_start_est): # include.append(game.pk) # include_times.append(self.get_str_local_time(game.start)) # else: # exclude.append(game.pk) # exclude_times.append(self.get_str_local_time(game.start)) # # self.data = { # 'weekday' : weekday, # 'type' : self.weekday_to_str(weekday), # 'total' : self.games.count(), # 'include' : include, # 'exclude' : exclude, # 'include_times' : include_times, # 'exclude_times' : exclude_times, # 'include_pct' : float(float(len(include)) / float(self.games.count())) # } # # return self.data def __init__(self, sport, season=None, season_types=None): self.data = None self.sport = sport self.sport_day_class = ScheduleDay.factory(self.sport) self.site_sport_manager = SiteSportManager() self.site_sport = self.site_sport_manager.get_site_sport(self.sport) self.game_model_class = self.site_sport_manager.get_game_class(self.site_sport) self.season = season # season is None, only get games for the season type after 'now' self.season_types = season_types if self.season_types is None: self.season_types = self.default_season_types # setup the datetime range with a start and end self.start = None self.end = None def get_data(self): return self.data def update_range(self, days_ago): """ add timedelta(days=days) to the start and end datetime object :param days_ago: :return: """ dfs_date_range = DfsDate.get_current_dfs_date_range() # set our dfsday range to start on the first day of the games we found self.start = dfs_date_range[0] - timedelta(days=days_ago) self.end = dfs_date_range[1] - timedelta(days=days_ago) def get_day_range(self): return self.start, self.end def get_days_since(self, datetime_obj): td = (timezone.now() - datetime_obj) return abs(td.days) + 1 def increment_day_range(self): self.start = self.start + timedelta(days=1) self.end = self.end + timedelta(days=1) def update(self, verbose=False): """ update the list of dfs days, with tuples of the start times and lists of all the games with their own unique start times """ # if running for the first time, its very likely you wont want to add 1 day to start time # dfs_date_tomorrow = DfsDate.get_current_dfs_date_range()[0] + timedelta(days=1) dfs_date_tomorrow = DfsDate.get_current_dfs_date_range()[0] logger.info("Looking for games later than: %s" % dfs_date_tomorrow) games = [] # default self.data = [] if self.season is None: # we are going to have to find the following dfs day... and check gte its start time games = self.game_model_class.objects.filter( start__gte=dfs_date_tomorrow, season__season_type__in=self.season_types).order_by('start') # oldest first else: games = self.game_model_class.objects.filter( season__season_year=self.season, season__season_type__in=self.season_types).order_by('start') # oldest first if games.count() <= 0: logger.info('0 games found. exiting...') return else: logger.info('%s games found, as old as %s' % (games.count(), games[0].start)) # days_ago = self.get_days_since(games[0].start) self.update_range(days_ago) day_range = self.get_day_range() # logger.info('first day (dt range)', str(day_range)) # Weekdays@7pm or later # Saturdays@7pm or later # Sundays@6pm or later # idx = 0 while games.filter(start__gte=self.get_day_range()[0]).count() > 0: # get all the games for the dfs day daily_games = games.filter(start__range=self.get_day_range()) if daily_games.count() >= 2: # there must be more than 2 games for DFS! dt = self.get_day_range()[0] date_str = self.get_str_local_date(dt) self.data.append((date_str, self.sport_day_class(self.site_sport, dt, daily_games))) # self.increment_day_range() def get_str_local_time(self, datetime_obj): local_dt = datetime_obj.astimezone(self.tzinfo_est) return local_dt.strftime(self.datetime_format_time) def get_str_local_date(self, datetime_obj): local_dt = datetime_obj.astimezone(self.tzinfo_est) return local_dt.strftime(self.datetime_format_date) def show_time_blocks(self): self.update() for date_str, sport_day in self.data: print(date_str, str(sport_day))
class Dummy(object): DEFAULT_SPORT = 'test' DEFAULT_ROSTER_MAP = { ('QB', 1, 0, True): ['QB'], ('WR', 1, 1, True): ['WR'], ('FX', 1, 2, False): ['RB', 'WR', 'TE'] } # # DEFAULT_SPORT_FIELD_FOR_FANTASY_POINTS = { # 'nfl' : ['pass_yds', 'rush_yds', 'rec_yds'], # 'nba' : ['assists', 'rebounds', 'blocks'], # # } # this class will iterate these to create dummy teams # if game or player objects need foreign keys to them DEFAULT_TEAMS = [('away', 'AWAY'), ('home', 'HOME')] def __init__(self, sport): """ Create dummy objects. This could interfere with the live site, and is strictly meant for testing environments, and specifically the "./manage.py test" tool """ self.ssm = SiteSportManager() self.site_sport = self.ssm.get_site_sport(sport) def generate(self): """ essentially does what generate_salaries() does, but for the sport this class was instantiated with, whereas generate_salaries() is a static method which uses the default sport and GameChild / PlayerChild tables. Use to this to make more realistic instances in the database of players/games/playerstats/salaries/etc... """ # clear out any existing rosters with the same sport, because theyll be recreated Dummy.remove_existing_rosters_for_sport(site_sport=self.site_sport) # prerequisite calls to create_roster(), create_player_stats_list() Dummy.create_roster(sport=self.site_sport.name) Dummy.create_player_stats_list(site_sport=self.site_sport, round_start_times=True) # players = Dummy.create_players(n=players, site_sport=site_sport) # -done # games = Dummy.create_games(n=games, site_sport=site_sport) # -done # create_player_stats_model( players,games) # -done salary_conf = Dummy.create_salary_config() # -done no changes pool = Pool() # -done no changes pool.site_sport = self.site_sport # -done use member variable pool.salary_config = salary_conf # -done no changes pool.active = True # -done default True so its useable pool.save() Dummy.create_trailing_game_weight(salary_conf, 3, 3) # -done Dummy.create_trailing_game_weight(salary_conf, 7, 2) # -done Dummy.create_trailing_game_weight(salary_conf, 10, 1) # -done # # the SiteSportManager.get_player_stats_class() # method actually returns a list of sport.<sport>.PlayerStats subclasses for the sport player_stats_classes = self.ssm.get_player_stats_class( self.site_sport) # -done generator = SalaryGenerator(player_stats_classes, pool) # -done generator.generate_salaries() # -done return generator # -done @staticmethod def remove_existing_rosters_for_sport(site_sport): """ call this at the beginning of create_rosters() to ensure that if the rosters already exist when a Dummy instance gets used in a test, we break down, and recreate the proper rosters. without adding more (which it doesnt/shouldnt handle nicely) :return: """ if site_sport == None: raise Exception( 'Dummy.remove_existing_rosters_for_sport() - site_sport not set yet' ) rsps = RosterSpotPosition.objects.filter( roster_spot__site_sport=site_sport) rsps.delete() rps = RosterSpot.objects.filter(site_sport=site_sport) rps.delete() # Shared setup methods for the test cases @staticmethod def create_roster(sport=DEFAULT_SPORT, roster=DEFAULT_ROSTER_MAP): """ example usage: the top level keys are tuples, the lists contain positions, each tuple key has the form: ('roster spot name',amount,idx,is_primary_boolean) >>> roster = { ... ('QB',1,0,True) :['QB'], ... ('WR',1,1,True) :['WR'], ... ('FX',1,1,False) :['RB','WR','TE'] ... } >>> site_sport = Dummy.create_roster(sport='mysport', roster=roster ) #example! :param sport: :param roster: :return: """ ret_roster_spot_position_list = [] # order the incoming roster dict by the idx ordered_roster = OrderedDict( sorted(roster.items(), key=lambda k: k[0][2])) site_sport, created = SiteSport.objects.get_or_create(name=sport) # print(site_sport, 'site_sport') # create the roster spot mappings for rs_tuple, pos_names_list in ordered_roster.items(): roster_spot_name = rs_tuple[0] roster_spot_amount = rs_tuple[1] roster_spot_idx = rs_tuple[2] primary = rs_tuple[3] # print('roster spot: %s, amount:%s, idx:%s, is_primary:%s' % (roster_spot_name, # roster_spot_amount, roster_spot_idx, primary)) for pos_name in pos_names_list: # # 'c' is a boolean indicating whether the object was created or not position, c = Position.objects.get_or_create( name=pos_name, site_sport=site_sport) # print(' ', position) roster_spot, c = RosterSpot.objects.get_or_create( name=roster_spot_name, amount=roster_spot_amount, idx=roster_spot_idx, site_sport=site_sport) # print(' ', roster_spot) roster_spot_position, c = RosterSpotPosition.objects.get_or_create( position=position, roster_spot=roster_spot, is_primary=primary) ret_roster_spot_position_list.append(roster_spot_position) # print(' ', roster_spot_position) # print('...created!') return ret_roster_spot_position_list @staticmethod def create_player_stats(sport=DEFAULT_SPORT): """ return a newly created player who could fit in the default roster. if 'roster' is None, we will call Dummy.create_roster() and use that data :param sport: :param roster: :return: """ # ('QB',1,0,True) :['QB'], position = None for rs_tuple, pos_list in Dummy.DEFAULT_ROSTER_MAP.items(): for pos_name in pos_list: site_sport, c = SiteSport.objects.get_or_create(name=sport) position, c = Position.objects.get_or_create( name=pos_name, site_sport=site_sport) break break if position is None: raise Exception( '>>>>> Dummy.create_player_stats() couldnt find any positions in roster' ) dt_now = timezone.now() unix_ts = dt_now.strftime('%s') # unix timestamp as srid ... not bad ssm = SiteSportManager() site_sport = ssm.get_site_sport(sport) game = Dummy.create_game(srid='game' + unix_ts, site_sport=site_sport) player = Dummy.create_player(srid='player' + unix_ts, position=position, team=game.home, site_sport=site_sport) if sport == Dummy.DEFAULT_SPORT: site_sport = None # hack for backwards compatability, to not break older code player_stats = Dummy.create_player_stats_model(game, player, site_sport) return player_stats @staticmethod def create_team(srid=None, alias=None, site_sport=None): """ Creates a team with a random srid - based on current milliseconds. """ if not srid: srid = "srid-%s" % int(round(time.time() * 1000)), if not alias: alias = "alias-%s" % int(round(time.time() * 1000)), if site_sport is None: t, created = TeamChild.objects.get_or_create(srid=srid, alias=alias) else: ssm = SiteSportManager() team_model = ssm.get_team_class(site_sport) t, created = team_model.objects.get_or_create(srid=srid, alias=alias) return t @staticmethod def create_game(srid=None, status='scheduled', away=None, home=None, site_sport=None, round_start_times=False): # site_sport, created = SiteSport.objects.get_or_create(name=sport) ssm = SiteSportManager() season_model_class = ssm.get_season_class(site_sport) dum_srid = '%s' % site_sport dum_season_year = 2016 dum_season_type = 'reg' dum_season, created = season_model_class.objects.get_or_create( srid=dum_srid, season_year=dum_season_year, season_type=dum_season_type, ) if srid is None: srid = "srid-%s" % int(round(time.time() * 1000)), if away is None: away = Dummy.create_team(alias='AWAY', site_sport=site_sport) if home is None: home = Dummy.create_team(alias='HOME', site_sport=site_sport) dt_now = timezone.now() if round_start_times: # zero out the seconds and microseconds! dt_now = dt_now.replace(dt_now.year, dt_now.month, dt_now.day, dt_now.hour, dt_now.minute, 0, 0) if site_sport is None: game = GameChild() else: ssm = SiteSportManager() game_model = ssm.get_game_class(site_sport) game = game_model() game.season = dum_season # cant be None game.srid = srid game.start = dt_now game.status = status game.away = away game.home = home game.save() return game @staticmethod def create_player(srid, position, team, site_sport=None): player = PlayerChild() player.srid = srid player.first_name = "Jon" player.last_name = "Doe" player.position = position player.team = team player.save() return player @staticmethod def create_player_stats_model(game, player, site_sport=None): """ If site_sport is not specified, defaults to use PlayerStatsChild model may not work to well for baseball since there are 2 PlayerStats types (hitter/pitcher) """ player_stats = None if site_sport is None: player_stats = PlayerStatsChild() else: ssm = SiteSportManager() player_stats_model_list = ssm.get_player_stats_class(site_sport) player_stats_model = player_stats_model_list[0] player_stats = player_stats_model() player_stats.fantasy_points = randint(0, 100) player_stats.game = game player_stats.player = player player_stats.srid_game = game.srid player_stats.srid_player = player.srid player_stats.position = player.position player_stats.save(fantasy_points_override=player_stats.fantasy_points) return player_stats @staticmethod def create_games(n=20, site_sport=None, round_start_times=False): # site_sport, created = SiteSport.objects.get_or_create(name=sport) dt_now = timezone.now() unix_ts = int( dt_now.strftime('%s')) # unix timestamp as srid ... not bad games = [] ssm = SiteSportManager() season_model_class = ssm.get_season_class(site_sport) # dum_srid = '%s'%site_sport # dum_season_year = 2016 # dum_season_type = 'reg' # dum_season, created = season_model_class.objects.get_or_create(srid=dum_srid, # season_year=dum_season_year, season_type=dum_season_type) for x in range(0, n): game = Dummy.create_game(srid='%s' % (unix_ts + x), site_sport=site_sport, round_start_times=round_start_times) # game.season = dum_season # cant be null game.start = game.start + timedelta( minutes=x) # stagger each game by 1 minute game.save() games.append(game) return games @staticmethod def create_players(n=20, teams=DEFAULT_TEAMS, site_sport=None): """ calls Dummy.create_roster() and then creates X players using the positions from the roster """ team_list = [] for t in teams: team, create = TeamChild.objects.get_or_create(srid=t[0], alias=t[1]) team_list.append(team) n_teams = len(team_list) dt_now = timezone.now() unix_ts = int(dt_now.strftime('%s')) if site_sport is None: Dummy.create_roster() Dummy.create_roster(sport=site_sport) positions = Position.objects.all() size = len(positions) players = [] for x in range(0, n): pos_idx = x % (size) players.append( Dummy.create_player(srid='%s' % (unix_ts + x), position=positions[pos_idx], team=team_list[x % n_teams], site_sport=site_sport)) return players @staticmethod def create_player_stats_list(players=20, games=20, site_sport=None, round_start_times=False): """ calls Dummy.create_roster() as a preqrequisite 'players' is the number of players we want to create 'games' is the number of games for which we will generate player stats for each player for :param players: :param games: :return: """ player_stats_list = [] players = Dummy.create_players( n=players, site_sport=site_sport ) # n=20 is the default argument which creates 20 players games = Dummy.create_games(n=games, site_sport=site_sport, round_start_times=round_start_times ) # n=20 is default for game as well for game in games: for player in players: player_stats_list.append( Dummy.create_player_stats_model(game, player, site_sport)) # print(len(player_stats_list), 'player_stats objects created. here are the first 15...') # for ps in player_stats_list[:15]: # print(' ', str(ps)) return player_stats_list @staticmethod def create_salary_config(): salary_conf = SalaryConfig() salary_conf.trailing_games = 10 salary_conf.days_since_last_game_flag = 10 salary_conf.min_games_flag = 7 salary_conf.min_player_salary = 3000 salary_conf.max_team_salary = 50000 salary_conf.min_avg_fppg_allowed_for_avg_calc = 5 salary_conf.save() return salary_conf @staticmethod def generate_salaries(sport=DEFAULT_SPORT, pool_active=True): """ internally, in this order, calls: - create_roster() - create_player_stats_list() returns the SalaryGenerator which created the salaries. """ # prerequisite calls to create_roster(), create_player_stats_list() Dummy.create_roster(sport=sport) site_sport, created = SiteSport.objects.get_or_create(name=sport) Dummy.create_player_stats_list(site_sport=site_sport) # # create the config and the pool site_sport, c = SiteSport.objects.get_or_create(name=sport) salary_conf = Dummy.create_salary_config() pool = Pool() pool.site_sport = site_sport pool.salary_config = salary_conf pool.active = pool_active pool.save() Dummy.create_trailing_game_weight(salary_conf, 3, 3) Dummy.create_trailing_game_weight(salary_conf, 7, 2) Dummy.create_trailing_game_weight(salary_conf, 10, 1) # # now use SalaryGenerator class on these objects player_stats_classes = [PlayerStatsChild] generator = SalaryGenerator(player_stats_classes, pool) generator.generate_salaries() return generator @staticmethod def create_trailing_game_weight(salary_config, through, weight): trailing_game_weight = TrailingGameWeight() trailing_game_weight.salary = salary_config trailing_game_weight.through = through trailing_game_weight.weight = weight trailing_game_weight.save()