sportsball 0.3.127__tar.gz → 0.4.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (261) hide show
  1. {sportsball-0.3.127/sportsball.egg-info → sportsball-0.4.0}/PKG-INFO +66 -2
  2. {sportsball-0.3.127 → sportsball-0.4.0}/README.md +63 -0
  3. sportsball-0.3.127/sportsball.egg-info/requires.txt → sportsball-0.4.0/requirements.txt +2 -1
  4. {sportsball-0.3.127 → sportsball-0.4.0}/setup.py +1 -1
  5. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/__init__.py +1 -1
  6. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_game_model.py +26 -11
  7. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_league_model.py +22 -7
  8. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_odds_model.py +6 -1
  9. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_player_model.py +13 -0
  10. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_team_model.py +7 -3
  11. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_venue_model.py +2 -0
  12. sportsball-0.4.0/sportsball/data/afl/afltables/afl_afltables_coach_model.py +95 -0
  13. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/afl_afltables_game_model.py +3 -0
  14. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/afl_afltables_player_model.py +111 -84
  15. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/afl_afltables_team_model.py +45 -27
  16. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/afl_afltables_venue_model.py +2 -0
  17. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/espn/afl_espn_league_model.py +8 -0
  18. sportsball-0.4.0/sportsball/data/afl/position.py +28 -0
  19. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_bookie_model.py +0 -2
  20. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_game_model.py +3 -0
  21. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_odds_model.py +4 -3
  22. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_team_model.py +3 -0
  23. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_venue_model.py +2 -0
  24. sportsball-0.4.0/sportsball/data/bet.py +94 -0
  25. sportsball-0.4.0/sportsball/data/coach_model.py +26 -0
  26. sportsball-0.4.0/sportsball/data/combined/combined_coach_model.py +31 -0
  27. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_game_model.py +18 -3
  28. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_league_model.py +3 -1
  29. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_player_model.py +48 -1
  30. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_team_model.py +26 -3
  31. sportsball-0.4.0/sportsball/data/dividend_model.py +23 -0
  32. sportsball-0.4.0/sportsball/data/espn/espn_coach_model.py +47 -0
  33. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_game_model.py +42 -6
  34. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_league_model.py +8 -0
  35. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_odds_model.py +5 -2
  36. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_player_model.py +51 -7
  37. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_team_model.py +29 -5
  38. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_venue_model.py +2 -0
  39. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/game_model.py +13 -0
  40. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/google/google_address_model.py +9748 -8202
  41. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_bookie_model.py +8 -0
  42. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_coach_model.py +60 -0
  43. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_dividend_model.py +17 -0
  44. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_game_model.py +242 -0
  45. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_league_model.py +94 -0
  46. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_odds_model.py +18 -0
  47. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_owner_model.py +19 -0
  48. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_player_model.py +203 -0
  49. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_team_model.py +141 -0
  50. sportsball-0.4.0/sportsball/data/hkjc/hkjc/hkjc_hkjc_venue_model.py +43 -0
  51. sportsball-0.4.0/sportsball/data/hkjc/position.py +43 -0
  52. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/espn/nba_espn_league_model.py +9 -0
  53. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nba/nba_nba_game_model.py +4 -1
  54. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nba/nba_nba_team_model.py +3 -0
  55. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/nba_nbacom_game_model.py +4 -1
  56. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/nba_nbacom_player_model.py +13 -0
  57. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/nba_nbacom_team_model.py +3 -0
  58. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/nba_nbacom_venue_model.py +3 -1
  59. sportsball-0.4.0/sportsball/data/nba/position.py +20 -0
  60. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/sportsreference/nba_sportsreference_league_model.py +5 -0
  61. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/espn/ncaab_espn_league_model.py +9 -0
  62. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/sportsreference/ncaab_sportsreference_league_model.py +5 -0
  63. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/espn/ncaaf_espn_league_model.py +9 -0
  64. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/espn/nfl_espn_league_model.py +5 -0
  65. sportsball-0.4.0/sportsball/data/nfl/position.py +10 -0
  66. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/odds_model.py +2 -0
  67. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_game_model.py +4 -1
  68. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_odds_model.py +3 -1
  69. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_team_model.py +3 -0
  70. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_venue_model.py +2 -0
  71. sportsball-0.4.0/sportsball/data/owner_model.py +21 -0
  72. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/player_model.py +54 -1
  73. sportsball-0.4.0/sportsball/data/sex.py +30 -0
  74. sportsball-0.4.0/sportsball/data/species.py +10 -0
  75. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsdb/sportsdb_game_model.py +3 -0
  76. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsdb/sportsdb_team_model.py +3 -0
  77. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsdb/sportsdb_venue_model.py +3 -0
  78. sportsball-0.4.0/sportsball/data/sportsreference/sportsreference_coach_model.py +93 -0
  79. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/sportsreference_game_model.py +20 -5
  80. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/sportsreference_league_model.py +10 -3
  81. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/sportsreference_player_model.py +70 -5
  82. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/sportsreference_team_model.py +65 -2
  83. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/sportsreference_venue_model.py +2 -0
  84. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/team_model.py +14 -0
  85. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/venue_model.py +4 -0
  86. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/wikipedia/wikipedia_venue_model.py +2 -0
  87. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/proxy_session.py +1 -0
  88. {sportsball-0.3.127 → sportsball-0.4.0/sportsball.egg-info}/PKG-INFO +66 -2
  89. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball.egg-info/SOURCES.txt +27 -0
  90. sportsball-0.3.127/requirements.txt → sportsball-0.4.0/sportsball.egg-info/requires.txt +3 -2
  91. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afltables/afl_afltables_game_model_test.py +8 -0
  92. sportsball-0.4.0/tests/data/afl/afltables/afl_afltables_player_model_test.py +87 -0
  93. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/combined/combined_game_model_test.py +11 -6
  94. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/combined/combined_player_model_test.py +9 -0
  95. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/combined/combined_team_model_test.py +76 -5
  96. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/espn/espn_game_model_test.py +8 -7
  97. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/espn/espn_player_model_test.py +8 -4
  98. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/game_model_test.py +3 -0
  99. sportsball-0.4.0/tests/data/hkjc/hkjc/hkjc_hkjc_game_model_test.py +120 -0
  100. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/player_model_test.py +9 -0
  101. sportsball-0.4.0/tests/data/sportsreference/__init__.py +0 -0
  102. sportsball-0.4.0/tests/data/sportsreference/sportsreference_coach_model_test.py +27 -0
  103. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsreference/sportsreference_game_model_test.py +76 -0
  104. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsreference/sportsreference_player_model_test.py +12 -8
  105. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsreference/sportsreference_team_model_test.py +24 -0
  106. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/team_model_test.py +3 -0
  107. sportsball-0.4.0/tests/data/x/__init__.py +0 -0
  108. sportsball-0.3.127/sportsball/data/hkjc/hkjc/hkjc_hkjc_league_model.py +0 -26
  109. sportsball-0.3.127/tests/data/afl/afltables/afl_afltables_player_model_test.py +0 -51
  110. {sportsball-0.3.127 → sportsball-0.4.0}/LICENSE +0 -0
  111. {sportsball-0.3.127 → sportsball-0.4.0}/MANIFEST.in +0 -0
  112. {sportsball-0.3.127 → sportsball-0.4.0}/setup.cfg +0 -0
  113. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/__main__.py +0 -0
  114. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/args.py +0 -0
  115. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/cache.py +0 -0
  116. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/__init__.py +0 -0
  117. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/address_model.py +0 -0
  118. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/__init__.py +0 -0
  119. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/__init__.py +0 -0
  120. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afl/afl_afl_bookie_model.py +0 -0
  121. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/__init__.py +0 -0
  122. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/afltables/afl_afltables_league_model.py +0 -0
  123. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/aussportsbetting/__init__.py +0 -0
  124. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/aussportsbetting/afl_aussportsbetting_league_model.py +0 -0
  125. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/combined/__init__.py +0 -0
  126. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/combined/afl_combined_league_model.py +0 -0
  127. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/espn/__init__.py +0 -0
  128. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/oddsportal/__init__.py +0 -0
  129. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/afl/oddsportal/afl_oddsportal_league_model.py +0 -0
  130. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/__init__.py +0 -0
  131. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/aussportsbetting/aussportsbetting_league_model.py +0 -0
  132. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/bookie_model.py +0 -0
  133. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/__init__.py +0 -0
  134. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_address_model.py +0 -0
  135. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_venue_model.py +0 -0
  136. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/combined_weather_model.py +0 -0
  137. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/combined/null_check.py +0 -0
  138. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/__init__.py +0 -0
  139. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/espn/espn_bookie_model.py +0 -0
  140. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/field_type.py +0 -0
  141. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/google/__init__.py +0 -0
  142. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/google/google_news_model.py +0 -0
  143. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/hkjc/__init__.py +0 -0
  144. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/hkjc/hkjc/__init__.py +0 -0
  145. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/league.py +0 -0
  146. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/league_model.py +0 -0
  147. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/model.py +0 -0
  148. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/__init__.py +0 -0
  149. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/combined/__init__.py +0 -0
  150. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/combined/nba_combined_league_model.py +0 -0
  151. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/espn/__init__.py +0 -0
  152. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nba/__init__.py +0 -0
  153. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nba/nba_nba_league_model.py +0 -0
  154. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/__init__.py +0 -0
  155. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/nbacom/nba_nbacom_league_model.py +0 -0
  156. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/oddsportal/__init__.py +0 -0
  157. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/oddsportal/nba_oddsportal_league_model.py +0 -0
  158. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/sportsdb/__init__.py +0 -0
  159. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/sportsdb/nba_sportsdb_league_model.py +0 -0
  160. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nba/sportsreference/__init__.py +0 -0
  161. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/__init__.py +0 -0
  162. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/combined/__init__.py +0 -0
  163. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/combined/ncaab_combined_league_model.py +0 -0
  164. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/espn/__init__.py +0 -0
  165. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/oddsportal/__init__.py +0 -0
  166. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/oddsportal/ncaab_oddsportal_league_model.py +0 -0
  167. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaab/sportsreference/__init__.py +0 -0
  168. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/__init__.py +0 -0
  169. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/combined/__init__.py +0 -0
  170. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/combined/ncaaf_combined_league_model.py +0 -0
  171. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/espn/__init__.py +0 -0
  172. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/oddsportal/__init__.py +0 -0
  173. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/ncaaf/oddsportal/ncaaf_oddsportal_league_model.py +0 -0
  174. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/news_model.py +0 -0
  175. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/__init__.py +0 -0
  176. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/aussportsbetting/__init__.py +0 -0
  177. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/aussportsbetting/nfl_aussportsbetting_league_model.py +0 -0
  178. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/combined/__init__.py +0 -0
  179. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/combined/nfl_combined_league_model.py +0 -0
  180. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/espn/__init__.py +0 -0
  181. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/oddsportal/__init__.py +0 -0
  182. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/oddsportal/nfl_oddsportal_league_model.py +0 -0
  183. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/sportsdb/__init__.py +0 -0
  184. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/nfl/sportsdb/nfl_sportsdb_league_model.py +0 -0
  185. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/__init__.py +0 -0
  186. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/decrypt.py +0 -0
  187. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_bookie_model.py +0 -0
  188. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/oddsportal/oddsportal_league_model.py +0 -0
  189. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/season_type.py +0 -0
  190. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/social_model.py +0 -0
  191. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsdb/__init__.py +0 -0
  192. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsdb/sportsdb_league_model.py +0 -0
  193. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/sportsreference/__init__.py +0 -0
  194. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/__init__.py +0 -0
  195. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/gribstream/__init__.py +0 -0
  196. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/gribstream/gribstream_weather_model.py +0 -0
  197. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/multi_weather_model.py +0 -0
  198. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/openmeteo/__init__.py +0 -0
  199. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather/openmeteo/openmeteo_weather_model.py +0 -0
  200. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/weather_model.py +0 -0
  201. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/wikipedia/__init__.py +0 -0
  202. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/x/__init__.py +0 -0
  203. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/data/x/x_social_model.py +0 -0
  204. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/logger.py +0 -0
  205. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/loglevel.py +0 -0
  206. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/playwright.py +0 -0
  207. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/session.py +0 -0
  208. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/sportsball.py +0 -0
  209. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/vendor/__init__.py +0 -0
  210. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball/vendor/pygooglenews/__init__.py +0 -0
  211. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball.egg-info/dependency_links.txt +0 -0
  212. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball.egg-info/entry_points.txt +0 -0
  213. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball.egg-info/not-zip-safe +0 -0
  214. {sportsball-0.3.127 → sportsball-0.4.0}/sportsball.egg-info/top_level.txt +0 -0
  215. {sportsball-0.3.127 → sportsball-0.4.0}/tests/__init__.py +0 -0
  216. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/__init__.py +0 -0
  217. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/__init__.py +0 -0
  218. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afl/__init__.py +0 -0
  219. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afl/afl_afl_game_model_test.py +0 -0
  220. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afl/afl_afl_league_model_test.py +0 -0
  221. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afltables/__init__.py +0 -0
  222. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/afl/afltables/afl_afltables_league_model_test.py +0 -0
  223. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/aussportsbetting/__init__.py +0 -0
  224. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/aussportsbetting/aussportsbetting_game_model_test.py +0 -0
  225. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/combined/__init__.py +0 -0
  226. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/espn/__init__.py +0 -0
  227. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/google/__init__.py +0 -0
  228. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/google/google_address_model_test.py +0 -0
  229. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/google/google_news_model_test.py +0 -0
  230. {sportsball-0.3.127/tests/data/nba → sportsball-0.4.0/tests/data/hkjc}/__init__.py +0 -0
  231. {sportsball-0.3.127/tests/data/nba/nba → sportsball-0.4.0/tests/data/hkjc/hkjc}/__init__.py +0 -0
  232. {sportsball-0.3.127/tests/data/nba/sportsdb → sportsball-0.4.0/tests/data/nba}/__init__.py +0 -0
  233. {sportsball-0.3.127/tests/data/nba/sportsreference → sportsball-0.4.0/tests/data/nba/nba}/__init__.py +0 -0
  234. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nba/nba/nba_nba_game_model_test.py +0 -0
  235. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nba/nba/nba_nba_league_model_test.py +0 -0
  236. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nba/nba/nba_nba_team_model_test.py +0 -0
  237. {sportsball-0.3.127/tests/data/ncaab → sportsball-0.4.0/tests/data/nba/sportsdb}/__init__.py +0 -0
  238. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nba/sportsdb/nba_sportsdb_league_model_test.py +0 -0
  239. {sportsball-0.3.127/tests/data/ncaab → sportsball-0.4.0/tests/data/nba}/sportsreference/__init__.py +0 -0
  240. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nba/sportsreference/nba_sportsreference_league_model_test.py +0 -0
  241. {sportsball-0.3.127/tests/data/nfl → sportsball-0.4.0/tests/data/ncaab}/__init__.py +0 -0
  242. {sportsball-0.3.127/tests/data/nfl/sportsdb → sportsball-0.4.0/tests/data/ncaab/sportsreference}/__init__.py +0 -0
  243. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/ncaab/sportsreference/ncaab_sportsreference_league_model_test.py +0 -0
  244. {sportsball-0.3.127/tests/data/oddsportal → sportsball-0.4.0/tests/data/nfl}/__init__.py +0 -0
  245. {sportsball-0.3.127/tests/data → sportsball-0.4.0/tests/data/nfl}/sportsdb/__init__.py +0 -0
  246. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/nfl/sportsdb/nfl_sportsdb_league_model_test.py +0 -0
  247. {sportsball-0.3.127/tests/data/sportsreference → sportsball-0.4.0/tests/data/oddsportal}/__init__.py +0 -0
  248. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/oddsportal/decrypt_test.py +0 -0
  249. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/oddsportal/oddsportal_game_model_test.py +0 -0
  250. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/oddsportal/oddsportal_league_model_test.py +0 -0
  251. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/social_model_test.py +0 -0
  252. {sportsball-0.3.127/tests/data/x → sportsball-0.4.0/tests/data/sportsdb}/__init__.py +0 -0
  253. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsdb/sportsdb_game_model_test.py +0 -0
  254. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsdb/sportsdb_league_model_test.py +0 -0
  255. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsdb/sportsdb_team_model_test.py +0 -0
  256. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsdb/sportsdb_venue_model_test.py +0 -0
  257. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsreference/sportsreference_league_model_test.py +0 -0
  258. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/sportsreference/sportsreference_venue_model_test.py +0 -0
  259. {sportsball-0.3.127 → sportsball-0.4.0}/tests/data/x/x_social_model_test.py +0 -0
  260. {sportsball-0.3.127 → sportsball-0.4.0}/tests/proxy_session_test.py +0 -0
  261. {sportsball-0.3.127 → sportsball-0.4.0}/tests/sportsball_test.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: sportsball
3
- Version: 0.3.127
3
+ Version: 0.4.0
4
4
  Summary: A library for pulling in and normalising sports stats.
5
5
  Home-page: https://github.com/8W9aG/sportsball
6
6
  Author: Will Sackfield
@@ -16,7 +16,7 @@ Requires-Dist: requests>=2.31.0
16
16
  Requires-Dist: requests-cache>=1.2.0
17
17
  Requires-Dist: python-dateutil>=1.16.0
18
18
  Requires-Dist: tqdm>=4.66.2
19
- Requires-Dist: beautifulsoup4>=4.13.3
19
+ Requires-Dist: beautifulsoup4>=4.13.4
20
20
  Requires-Dist: openpyxl>=3.1.5
21
21
  Requires-Dist: joblib>=1.4.2
22
22
  Requires-Dist: pyarrow>=18.0.0
@@ -46,6 +46,7 @@ Requires-Dist: dateparser>=1.2.0
46
46
  Requires-Dist: playwright>=1.51.0
47
47
  Requires-Dist: cchardet>=2.2.0a2
48
48
  Requires-Dist: lxml>=5.3.0
49
+ Requires-Dist: gender-guesser>=0.4.0
49
50
  Dynamic: author
50
51
  Dynamic: author-email
51
52
  Dynamic: classifier
@@ -107,6 +108,7 @@ Python 3.11.6:
107
108
  - [playwright](https://playwright.dev/)
108
109
  - [cchardet](https://github.com/PyYoshi/cChardet)
109
110
  - [lxml](https://lxml.de/)
111
+ - [gender-guesser](https://github.com/lead-ratings/gender-guesser)
110
112
 
111
113
  ## Raison D'être :thought_balloon:
112
114
 
@@ -129,13 +131,17 @@ The supported leagues are:
129
131
  * **Game**: A game within a season.
130
132
  * **Team**: The team within the game. Note that in games with individual players a team exists as a wrapper.
131
133
  * **Player**: A player within the team.
134
+ * **Address**: The address information of a players birth.
135
+ * **Owner**: The owner of the player.
132
136
  * **Odds**: The odds for the team to win the game.
133
137
  * **Bookie**: The bookie publishing the odds.
134
138
  * **News**: News about the team the day before the game.
135
139
  * **Social**: Social posts from the team the day before the game.
140
+ * **Coach**: A coach for the team.
136
141
  * **Venue**: The venue the game was played in.
137
142
  * **Address**: The address information of a venue.
138
143
  * **Weather**: The weather at the address.
144
+ * **Dividend**: The dividends the game pays out.
139
145
 
140
146
  ### Objects
141
147
 
@@ -159,6 +165,7 @@ A representation of the game within a season.
159
165
  * **season_type**: The type of the season the game was played in.
160
166
  * **postponed**: Whether the game was postponed.
161
167
  * **playoff**: Whether the game was a playoff game.
168
+ * **distance**: The distance the game was played over.
162
169
 
163
170
  #### Team
164
171
 
@@ -180,6 +187,29 @@ A representation of a team within a game.
180
187
  * **assists**: The number of times the player on the team made a pass that resulted in a field goal in the game.
181
188
  * **turnovers**: The number of times a player on the team loses possession of the ball in the game.
182
189
  * **marks**: The number of times a player on the team marks the ball in the game.
190
+ * **handballs**: The number of times a player on the team handballs the ball in the game.
191
+ * **disposals**: The number of times a player on the team disposes of the ball in the game.
192
+ * **goals**: The number of times a player on the team scored a goal in the game.
193
+ * **behinds**: The number of times a player on the team scored a behind in the game.
194
+ * **hit_outs**: The number of times a player on the team hit out the ball in the game.
195
+ * **tackles**: The number of times a player on the team tackled another player in the game.
196
+ * **rebounds**: The number of times a player on the team gets a rebound in the game.
197
+ * **insides**: The number of times a player on the team kicks a ball inside 50 in the game.
198
+ * **clearances**: The number of times a player on the team performs a clearance in the game.
199
+ * **clangers**: The number of times a player on the team performs a clanger in the game.
200
+ * **free_kicks_for**: The number of times a player on the team was rewarded a free kick in the game.
201
+ * **free_kicks_against**: The number of times a player on the team gave a player on the other team a free kick in the game.
202
+ * **brownlow_votes**: The number of times a player on the team was given a brownlow vote in the game.
203
+ * **contested_possessions**: The number of times a player on the team got a contested posession in the game.
204
+ * **uncontested_possessions**: The number of times a player on the team got an uncontested posession in the game.
205
+ * **contested_marks**: The number of times a player on the team got a contested mark in the game.
206
+ * **marks_inside**: The number of times a player on the team got a mark inside 50 in the game.
207
+ * **one_percenters**: The number of times a player on the team performs a "one-percenter" in the game.
208
+ * **bounces**: The number of times a player on the team bounces a ball.
209
+ * **goal_assists**: The number of times a player on the team assists another player on the team with a goal in the game.
210
+ * **coaches**: The coaches on the team during the game.
211
+ * **lbw**: Length behind winner, expressed in metres.
212
+ * **dividends**: The dividends the game pays out.
183
213
 
184
214
  #### Player
185
215
 
@@ -219,6 +249,14 @@ A representation of a player within a team within a game.
219
249
  * **goal_assists**: The number of assists on goal the player had in the game.
220
250
  * **percentage_played**: The percentage of the game the player was on the field.
221
251
  * **birth_date**: The birth date of the player.
252
+ * **species**: The species of the player.
253
+ * **handicap_weight**: The handicap weight of the player (in KGs).
254
+ * **father**: The player representing the father of the player.
255
+ * **sex**: The sex of the player.
256
+ * **age**: The age of the player in years.
257
+ * **starting_position**: The starting position of the player.
258
+ * **weight**: The weight of the player in (in KGs).
259
+ * **birth_address**: The address model for the players birth location.
222
260
 
223
261
  #### Odds
224
262
 
@@ -227,6 +265,8 @@ A representation of the odds for a team to win within a game.
227
265
  * **odds**: The decimal odds offered by a bookie for the team to win in the game.
228
266
  * **bookie**: The bookie offering these odds.
229
267
  * **dt**: When the odds were posted.
268
+ * **canonical**: Whether these odds can be treated as canonical for the purposes of backtesting.
269
+ * **bet**: The type of bet the odds represent.
230
270
 
231
271
  #### Venue
232
272
 
@@ -280,6 +320,30 @@ Social media posts one day out from the game.
280
320
  * **views**: The number of views the post has.
281
321
  * **published**: When the post was published.
282
322
 
323
+ #### Coach
324
+
325
+ The coach on the team at the time of the game.
326
+
327
+ * **identifier**: The unique identifier for the coach.
328
+ * **name**: The name of the coach.
329
+ * **birth_date**: The birth date of the coach.
330
+ * **age**: The age of the coach.
331
+
332
+ #### Dividend
333
+
334
+ The dividend payout at the end of the game.
335
+
336
+ * **pool**: The type of bet paying the dividend.
337
+ * **combination**: The combination of team identifiers making up the dividend.
338
+ * **dividend**: The payout of the dividend.
339
+
340
+ #### Owner
341
+
342
+ The owner of a player.
343
+
344
+ * **name**: The name of the owner.
345
+ * **identifier**: The unique identifier of the owner.
346
+
283
347
  ## Caching
284
348
 
285
349
  This library uses very aggressive caching due to the large data requirements. If the requests are about a recent game (generally in the last 7 days) the caching is bypassed. The caching is as follows:
@@ -48,6 +48,7 @@ Python 3.11.6:
48
48
  - [playwright](https://playwright.dev/)
49
49
  - [cchardet](https://github.com/PyYoshi/cChardet)
50
50
  - [lxml](https://lxml.de/)
51
+ - [gender-guesser](https://github.com/lead-ratings/gender-guesser)
51
52
 
52
53
  ## Raison D'être :thought_balloon:
53
54
 
@@ -70,13 +71,17 @@ The supported leagues are:
70
71
  * **Game**: A game within a season.
71
72
  * **Team**: The team within the game. Note that in games with individual players a team exists as a wrapper.
72
73
  * **Player**: A player within the team.
74
+ * **Address**: The address information of a players birth.
75
+ * **Owner**: The owner of the player.
73
76
  * **Odds**: The odds for the team to win the game.
74
77
  * **Bookie**: The bookie publishing the odds.
75
78
  * **News**: News about the team the day before the game.
76
79
  * **Social**: Social posts from the team the day before the game.
80
+ * **Coach**: A coach for the team.
77
81
  * **Venue**: The venue the game was played in.
78
82
  * **Address**: The address information of a venue.
79
83
  * **Weather**: The weather at the address.
84
+ * **Dividend**: The dividends the game pays out.
80
85
 
81
86
  ### Objects
82
87
 
@@ -100,6 +105,7 @@ A representation of the game within a season.
100
105
  * **season_type**: The type of the season the game was played in.
101
106
  * **postponed**: Whether the game was postponed.
102
107
  * **playoff**: Whether the game was a playoff game.
108
+ * **distance**: The distance the game was played over.
103
109
 
104
110
  #### Team
105
111
 
@@ -121,6 +127,29 @@ A representation of a team within a game.
121
127
  * **assists**: The number of times the player on the team made a pass that resulted in a field goal in the game.
122
128
  * **turnovers**: The number of times a player on the team loses possession of the ball in the game.
123
129
  * **marks**: The number of times a player on the team marks the ball in the game.
130
+ * **handballs**: The number of times a player on the team handballs the ball in the game.
131
+ * **disposals**: The number of times a player on the team disposes of the ball in the game.
132
+ * **goals**: The number of times a player on the team scored a goal in the game.
133
+ * **behinds**: The number of times a player on the team scored a behind in the game.
134
+ * **hit_outs**: The number of times a player on the team hit out the ball in the game.
135
+ * **tackles**: The number of times a player on the team tackled another player in the game.
136
+ * **rebounds**: The number of times a player on the team gets a rebound in the game.
137
+ * **insides**: The number of times a player on the team kicks a ball inside 50 in the game.
138
+ * **clearances**: The number of times a player on the team performs a clearance in the game.
139
+ * **clangers**: The number of times a player on the team performs a clanger in the game.
140
+ * **free_kicks_for**: The number of times a player on the team was rewarded a free kick in the game.
141
+ * **free_kicks_against**: The number of times a player on the team gave a player on the other team a free kick in the game.
142
+ * **brownlow_votes**: The number of times a player on the team was given a brownlow vote in the game.
143
+ * **contested_possessions**: The number of times a player on the team got a contested posession in the game.
144
+ * **uncontested_possessions**: The number of times a player on the team got an uncontested posession in the game.
145
+ * **contested_marks**: The number of times a player on the team got a contested mark in the game.
146
+ * **marks_inside**: The number of times a player on the team got a mark inside 50 in the game.
147
+ * **one_percenters**: The number of times a player on the team performs a "one-percenter" in the game.
148
+ * **bounces**: The number of times a player on the team bounces a ball.
149
+ * **goal_assists**: The number of times a player on the team assists another player on the team with a goal in the game.
150
+ * **coaches**: The coaches on the team during the game.
151
+ * **lbw**: Length behind winner, expressed in metres.
152
+ * **dividends**: The dividends the game pays out.
124
153
 
125
154
  #### Player
126
155
 
@@ -160,6 +189,14 @@ A representation of a player within a team within a game.
160
189
  * **goal_assists**: The number of assists on goal the player had in the game.
161
190
  * **percentage_played**: The percentage of the game the player was on the field.
162
191
  * **birth_date**: The birth date of the player.
192
+ * **species**: The species of the player.
193
+ * **handicap_weight**: The handicap weight of the player (in KGs).
194
+ * **father**: The player representing the father of the player.
195
+ * **sex**: The sex of the player.
196
+ * **age**: The age of the player in years.
197
+ * **starting_position**: The starting position of the player.
198
+ * **weight**: The weight of the player in (in KGs).
199
+ * **birth_address**: The address model for the players birth location.
163
200
 
164
201
  #### Odds
165
202
 
@@ -168,6 +205,8 @@ A representation of the odds for a team to win within a game.
168
205
  * **odds**: The decimal odds offered by a bookie for the team to win in the game.
169
206
  * **bookie**: The bookie offering these odds.
170
207
  * **dt**: When the odds were posted.
208
+ * **canonical**: Whether these odds can be treated as canonical for the purposes of backtesting.
209
+ * **bet**: The type of bet the odds represent.
171
210
 
172
211
  #### Venue
173
212
 
@@ -221,6 +260,30 @@ Social media posts one day out from the game.
221
260
  * **views**: The number of views the post has.
222
261
  * **published**: When the post was published.
223
262
 
263
+ #### Coach
264
+
265
+ The coach on the team at the time of the game.
266
+
267
+ * **identifier**: The unique identifier for the coach.
268
+ * **name**: The name of the coach.
269
+ * **birth_date**: The birth date of the coach.
270
+ * **age**: The age of the coach.
271
+
272
+ #### Dividend
273
+
274
+ The dividend payout at the end of the game.
275
+
276
+ * **pool**: The type of bet paying the dividend.
277
+ * **combination**: The combination of team identifiers making up the dividend.
278
+ * **dividend**: The payout of the dividend.
279
+
280
+ #### Owner
281
+
282
+ The owner of a player.
283
+
284
+ * **name**: The name of the owner.
285
+ * **identifier**: The unique identifier of the owner.
286
+
224
287
  ## Caching
225
288
 
226
289
  This library uses very aggressive caching due to the large data requirements. If the requests are about a recent game (generally in the last 7 days) the caching is bypassed. The caching is as follows:
@@ -3,7 +3,7 @@ requests>=2.31.0
3
3
  requests-cache>=1.2.0
4
4
  python-dateutil>=1.16.0
5
5
  tqdm>=4.66.2
6
- beautifulsoup4>=4.13.3
6
+ beautifulsoup4>=4.13.4
7
7
  openpyxl>=3.1.5
8
8
  joblib>=1.4.2
9
9
  pyarrow>=18.0.0
@@ -33,3 +33,4 @@ dateparser>=1.2.0
33
33
  playwright>=1.51.0
34
34
  cchardet>=2.2.0a2
35
35
  lxml>=5.3.0
36
+ gender-guesser>=0.4.0
@@ -26,7 +26,7 @@ def install_requires() -> typing.List[str]:
26
26
 
27
27
  setup(
28
28
  name='sportsball',
29
- version='0.3.127',
29
+ version='0.4.0',
30
30
  description='A library for pulling in and normalising sports stats.',
31
31
  long_description=long_description,
32
32
  long_description_content_type='text/markdown',
@@ -4,4 +4,4 @@
4
4
  import cchardet # type: ignore
5
5
  import lxml # noqa: ignore
6
6
 
7
- __VERSION__ = "0.3.127"
7
+ __VERSION__ = "0.4.0"
@@ -1,6 +1,6 @@
1
1
  """AFL AFL game model."""
2
2
 
3
- # pylint: disable=too-many-statements,protected-access,too-many-arguments,bare-except,duplicate-code
3
+ # pylint: disable=too-many-statements,protected-access,too-many-arguments,bare-except,duplicate-code,too-many-locals
4
4
  import datetime
5
5
  import re
6
6
 
@@ -12,24 +12,32 @@ from playwright.sync_api import Playwright
12
12
  from ....playwright import ensure_install
13
13
  from ...game_model import GameModel
14
14
  from ...league import League
15
+ from ..position import Position, position_from_str
15
16
  from .afl_afl_team_model import create_afl_afl_team_model
16
17
  from .afl_afl_venue_model import create_afl_afl_venue_model
17
18
 
18
19
 
19
- def parse_players_v1(div: Tag) -> list[list[tuple[str, str, str, str]]]:
20
+ def parse_players_v1(div: Tag) -> list[list[tuple[str, str, str, str, Position]]]:
20
21
  """Parses the players from a v1 format."""
21
- teams_players: list[list[tuple[str, str, str, str]]] = [[], []]
22
+ teams_players: list[list[tuple[str, str, str, str, Position]]] = [[], []]
22
23
  for div_positions_row in div.find_all(
23
24
  "div", {"class": re.compile(".*team-lineups__positions-row.*")}
24
25
  ):
25
- row_players: list[list[tuple[str, str, str, str]]] = [[], []]
26
+ row_players: list[list[tuple[str, str, str, str, Position]]] = [[], []]
26
27
  for count, div_team_players in enumerate(
27
28
  div_positions_row.find_all(
28
29
  "div",
29
30
  {"class": re.compile(".*team-lineups__positions-players-container.*")},
30
31
  )
31
32
  ):
32
- team_players: list[tuple[str, str, str, str]] = []
33
+ team_players: list[tuple[str, str, str, str, Position]] = []
34
+ position = None
35
+ for span in div_team_players.find_all(
36
+ "span", {"class": re.compile(".*team-lineups__position-meta-label.*")}
37
+ ):
38
+ position = position_from_str(span.get_text().strip())
39
+ if position is None:
40
+ raise ValueError("position is null")
33
41
  for a in div_team_players.find_all(
34
42
  "a", {"class": re.compile(".*js-player-profile-link.*")}
35
43
  ):
@@ -49,7 +57,9 @@ def parse_players_v1(div: Tag) -> list[list[tuple[str, str, str, str]]]:
49
57
  )
50
58
  if player_number is None:
51
59
  raise ValueError("player_number is null")
52
- team_players.append((player_id, player_number, first_name, second_name))
60
+ team_players.append(
61
+ (player_id, player_number, first_name, second_name, position)
62
+ )
53
63
  row_players[count].extend(team_players)
54
64
  for count, row_players_list in enumerate(row_players):
55
65
  teams_players[count].extend(row_players_list)
@@ -71,8 +81,8 @@ def _extract_dt(soup: BeautifulSoup) -> datetime.datetime:
71
81
 
72
82
 
73
83
  def _extract_players(
74
- soup: BeautifulSoup, players: list[list[tuple[str, str, str, str]]]
75
- ) -> list[list[tuple[str, str, str, str]]]:
84
+ soup: BeautifulSoup, players: list[list[tuple[str, str, str, str, Position]]]
85
+ ) -> list[list[tuple[str, str, str, str, Position]]]:
76
86
  def is_players_empty() -> bool:
77
87
  nonlocal players
78
88
  if not players:
@@ -94,15 +104,17 @@ def _extract_players(
94
104
 
95
105
 
96
106
  def _parse(
97
- html: str, players: list[list[tuple[str, str, str, str]]]
98
- ) -> tuple[list[float], datetime.datetime, list[list[tuple[str, str, str, str]]]]:
107
+ html: str, players: list[list[tuple[str, str, str, str, Position]]]
108
+ ) -> tuple[
109
+ list[float], datetime.datetime, list[list[tuple[str, str, str, str, Position]]]
110
+ ]:
99
111
  soup = BeautifulSoup(html, "lxml")
100
112
  return _extract_odds(soup), _extract_dt(soup), _extract_players(soup, players)
101
113
 
102
114
 
103
115
  def create_afl_afl_game_model(
104
116
  team_names: list[str],
105
- players: list[list[tuple[str, str, str, str]]],
117
+ players: list[list[tuple[str, str, str, str, Position]]],
106
118
  dt: datetime.datetime | None,
107
119
  venue_name: str,
108
120
  session: requests_cache.CachedSession,
@@ -150,4 +162,7 @@ def create_afl_afl_game_model(
150
162
  season_type=None,
151
163
  postponed=None,
152
164
  play_off=None,
165
+ distance=None,
166
+ dividends=[],
167
+ pot=None,
153
168
  )
@@ -16,6 +16,7 @@ from ....playwright import ensure_install
16
16
  from ...game_model import GameModel
17
17
  from ...league import League
18
18
  from ...league_model import LeagueModel
19
+ from ..position import Position, position_from_str
19
20
  from .afl_afl_game_model import create_afl_afl_game_model, parse_players_v1
20
21
 
21
22
 
@@ -71,18 +72,23 @@ def _parse_v1(
71
72
 
72
73
  def _parse_v2_soup(
73
74
  soup: BeautifulSoup, html_url: str
74
- ) -> Iterator[tuple[list[str], list[list[tuple[str, str, str, str]]], str, str]]:
75
+ ) -> Iterator[
76
+ tuple[list[str], list[list[tuple[str, str, str, str, Position]]], str, str]
77
+ ]:
75
78
  for div in soup.find_all("div", {"class": "team-lineups__item"}):
76
79
  team_names = []
77
80
  for span in div.find_all(
78
81
  "span", {"class": re.compile(".*team-lineups-header__name.*")}
79
82
  ):
80
83
  team_names = [x.strip() for x in span.get_text().strip().split(" v ")]
81
- team_players: list[list[tuple[str, str, str, str]]] = [[], []]
84
+ team_players: list[list[tuple[str, str, str, str, Position]]] = [[], []]
82
85
 
83
86
  def process_a_player(
84
- a: Tag, idx: int, team_players: list[list[tuple[str, str, str, str]]]
85
- ) -> list[list[tuple[str, str, str, str]]]:
87
+ a: Tag,
88
+ idx: int,
89
+ team_players: list[list[tuple[str, str, str, str, Position]]],
90
+ div: Tag,
91
+ ) -> list[list[tuple[str, str, str, str, Position]]]:
86
92
  href = a.get("href")
87
93
  if not isinstance(href, str):
88
94
  raise ValueError("href is not a str")
@@ -98,17 +104,26 @@ def _parse_v2_soup(
98
104
  jersey = div_shirt.get_text().strip()
99
105
  if jersey is None:
100
106
  raise ValueError("jersey is null")
101
- team_players[idx].append((player_id, first_name, sur_name, jersey))
107
+ position = None
108
+ for span in div.find_all(
109
+ "span", {"class": re.compile(".*team-lineups__position-meta-label.*")}
110
+ ):
111
+ position = position_from_str(span.get_text().strip())
112
+ if position is None:
113
+ raise ValueError("position is null")
114
+ team_players[idx].append(
115
+ (player_id, first_name, sur_name, jersey, position)
116
+ )
102
117
  return team_players
103
118
 
104
119
  for a in div.find_all(
105
120
  "a", {"class": re.compile(".*team-lineups__player-entry--home-team.*")}
106
121
  ):
107
- team_players = process_a_player(a, 0, team_players)
122
+ team_players = process_a_player(a, 0, team_players, div)
108
123
  for a in div.find_all(
109
124
  "a", {"class": re.compile(".*team-lineups__player-entry--away-team.*")}
110
125
  ):
111
- team_players = process_a_player(a, 1, team_players)
126
+ team_players = process_a_player(a, 1, team_players, div)
112
127
 
113
128
  venue_name: str | None = None
114
129
  for div_info in div.find_all("div", {"class": "team-lineups-header__info"}):
@@ -2,6 +2,7 @@
2
2
 
3
3
  import datetime
4
4
 
5
+ from ...bet import Bet
5
6
  from ...team_model import OddsModel
6
7
  from .afl_afl_bookie_model import create_afl_afl_bookie_model
7
8
 
@@ -10,5 +11,9 @@ def create_afl_afl_odds_model(odds: float) -> OddsModel:
10
11
  """Create an odds model based off aus sports betting."""
11
12
  bookie = create_afl_afl_bookie_model()
12
13
  return OddsModel(
13
- odds=odds, bookie=bookie, dt=datetime.datetime.now(), canonical=True
14
+ odds=odds,
15
+ bookie=bookie,
16
+ dt=datetime.datetime.now(),
17
+ canonical=True,
18
+ bet=str(Bet.WIN),
14
19
  ) # pyright: ignore
@@ -2,12 +2,16 @@
2
2
 
3
3
  # pylint: disable=duplicate-code
4
4
  from ...player_model import PlayerModel
5
+ from ...sex import Sex
6
+ from ...species import Species
7
+ from ..position import Position
5
8
 
6
9
 
7
10
  def create_afl_afl_player_model(
8
11
  identifier: str,
9
12
  player_number: str,
10
13
  name: str,
14
+ position: Position,
11
15
  ) -> PlayerModel:
12
16
  """Create a player model from AFL AFL."""
13
17
  return PlayerModel(
@@ -45,4 +49,13 @@ def create_afl_afl_player_model(
45
49
  goal_assists=None,
46
50
  percentage_played=None,
47
51
  birth_date=None,
52
+ age=None,
53
+ species=str(Species.HUMAN),
54
+ handicap_weight=None,
55
+ father=None,
56
+ sex=str(Sex.MALE),
57
+ starting_position=str(position),
58
+ weight=None,
59
+ birth_address=None,
60
+ owner=None,
48
61
  )
@@ -8,13 +8,14 @@ import requests_cache
8
8
  from ...google.google_news_model import create_google_news_models
9
9
  from ...league import League
10
10
  from ...team_model import TeamModel
11
+ from ..position import Position
11
12
  from .afl_afl_odds_model import create_afl_afl_odds_model
12
13
  from .afl_afl_player_model import create_afl_afl_player_model
13
14
 
14
15
 
15
16
  def create_afl_afl_team_model(
16
17
  team_name: str,
17
- players: list[tuple[str, str, str, str]],
18
+ players: list[tuple[str, str, str, str, Position]],
18
19
  session: requests_cache.CachedSession,
19
20
  dt: datetime.datetime,
20
21
  ladder: list[str],
@@ -23,9 +24,9 @@ def create_afl_afl_team_model(
23
24
  """Create a team model from AFL AFL."""
24
25
  player_models = [
25
26
  create_afl_afl_player_model(
26
- identifier, player_number, " ".join([first_name, second_name])
27
+ identifier, player_number, " ".join([first_name, second_name]), position
27
28
  )
28
- for identifier, player_number, first_name, second_name in players
29
+ for identifier, player_number, first_name, second_name, position in players
29
30
  ]
30
31
  odds_models = []
31
32
  if odds is not None:
@@ -48,4 +49,7 @@ def create_afl_afl_team_model(
48
49
  offensive_rebounds=None,
49
50
  assists=None,
50
51
  turnovers=None,
52
+ coaches=[],
53
+ lbw=None,
54
+ end_dt=None,
51
55
  )
@@ -22,4 +22,6 @@ def create_afl_afl_venue_model(
22
22
  address=address_model,
23
23
  is_grass=None,
24
24
  is_indoor=None,
25
+ is_turf=None,
26
+ is_dirt=None,
25
27
  )
@@ -0,0 +1,95 @@
1
+ """AFL AFLTables coach model."""
2
+
3
+ # pylint: disable=too-many-locals
4
+ import datetime
5
+ import io
6
+ import os
7
+ import urllib.parse
8
+ from urllib.parse import urlparse
9
+
10
+ import pandas as pd
11
+ import pytest_is_running
12
+ import requests_cache
13
+ from bs4 import BeautifulSoup
14
+ from dateutil.parser import parse
15
+ from dateutil.relativedelta import relativedelta
16
+
17
+ from ....cache import MEMORY
18
+ from ...coach_model import CoachModel
19
+
20
+ _COACH_URL_CACHE: dict[str, str] = {}
21
+
22
+
23
+ def _create_afl_afltables_coach_model(
24
+ url: str, session: requests_cache.CachedSession, year: int, dt: datetime.datetime
25
+ ) -> CoachModel:
26
+ html = _COACH_URL_CACHE.get(url)
27
+ if html is None:
28
+ with session.cache_disabled():
29
+ response = session.get(url)
30
+ html = response.text
31
+ _COACH_URL_CACHE[url] = html
32
+ handle = io.StringIO()
33
+ handle.write(html)
34
+ handle.seek(0)
35
+ dfs = pd.read_html(handle)
36
+ df = dfs[0]
37
+ df = df[df.columns.values.tolist()[:2]]
38
+ year_ranges = df[df.columns.values.tolist()[1]].tolist()
39
+ names = df[df.columns.values.tolist()[0]].tolist()
40
+ name = None
41
+ for count, year_range in enumerate(year_ranges):
42
+ if "-" in year_range:
43
+ start_year, end_year = [int(x) for x in year_range.split("-")]
44
+ else:
45
+ start_year = end_year = int(year_range)
46
+ if start_year <= year >= end_year:
47
+ name = names[count].strip()
48
+ break
49
+ if name is None:
50
+ raise ValueError("name is null")
51
+ coach_url = None
52
+ soup = BeautifulSoup(html, "lxml")
53
+ for a in soup.find_all("a", href=True):
54
+ a_text = a.get_text().strip()
55
+ if a_text == name:
56
+ coach_url = urllib.parse.urljoin(url, a.get("href"))
57
+ break
58
+ if coach_url is None:
59
+ raise ValueError("coach is null")
60
+ o = urlparse(coach_url)
61
+ last_component = o.path.split("/")[-1]
62
+ identifier, _ = os.path.splitext(last_component)
63
+
64
+ response = session.get(coach_url)
65
+ response.raise_for_status()
66
+ soup = BeautifulSoup(response.text, "lxml")
67
+ birth_date = parse(soup.get_text().split("Born:")[1].strip().split()[0])
68
+
69
+ return CoachModel(
70
+ identifier=identifier,
71
+ name=name,
72
+ birth_date=birth_date,
73
+ age=relativedelta(birth_date, dt).years,
74
+ )
75
+
76
+
77
+ @MEMORY.cache(ignore=["session"])
78
+ def _cached_create_afl_afltables_coach_model(
79
+ url: str, session: requests_cache.CachedSession, year: int, dt: datetime.datetime
80
+ ) -> CoachModel:
81
+ return _create_afl_afltables_coach_model(url=url, session=session, year=year, dt=dt)
82
+
83
+
84
+ def create_afl_afltables_coach_model(
85
+ url: str, session: requests_cache.CachedSession, year: int, dt: datetime.datetime
86
+ ) -> CoachModel:
87
+ """Create a coach model from AFL tables."""
88
+ if not pytest_is_running.is_running():
89
+ return _cached_create_afl_afltables_coach_model(
90
+ url=url, session=session, year=year, dt=dt
91
+ )
92
+ with session.cache_disabled():
93
+ return _create_afl_afltables_coach_model(
94
+ url=url, session=session, year=year, dt=dt
95
+ )
@@ -469,6 +469,9 @@ def _create_afl_afltables_game_model(
469
469
  season_type=season_type,
470
470
  postponed=None,
471
471
  play_off=None,
472
+ distance=None,
473
+ dividends=[],
474
+ pot=None,
472
475
  )
473
476
 
474
477