Added the abililty to retrieve all plays

This commit is contained in:
Yarne Coppens 2024-08-02 12:48:35 +02:00
parent 592c416820
commit 98cef3603c
3 changed files with 84 additions and 7 deletions

View file

@ -1,17 +1,18 @@
from pydantic import BaseModel from pydantic import BaseModel
from typing import Union
from datetime import date from datetime import date
class PlayPlayer(BaseModel): class PlayPlayer(BaseModel):
name: str name: str
username: str username: str
score: float score: Union[float, None]
first_play : bool first_play : bool
has_won : bool has_won : bool
class Play(BaseModel): class Play(BaseModel):
boardgame_id: int boardgame_id: int
players: list[PlayPlayer] players: list[PlayPlayer]
playdate: date play_date: date
duration: int #In minutes duration: int #In minutes
ignore_for_stats : bool ignore_for_stats : bool
location: str location: str

View file

@ -1,7 +1,7 @@
from typing import Union from typing import Union
from fastapi import FastAPI from fastapi import FastAPI
from src.classes import boardgame_classes from src.classes import boardgame_classes, play_classes
from src.modules import bgg_connection from src.modules import bgg_connection
app = FastAPI() app = FastAPI()
@ -26,3 +26,10 @@ def get_owned_collection():
def get_wishlist_collection(): def get_wishlist_collection():
requested_collection: list[boardgame_classes.WishlistBoardGame] = bgg_connection.get_user_wishlist_collection() requested_collection: list[boardgame_classes.WishlistBoardGame] = bgg_connection.get_user_wishlist_collection()
return requested_collection return requested_collection
@app.get("/plays", response_model=list[play_classes.Play])
def get_plays():
requested_plays: list[play_classes.Play] = bgg_connection.get_plays()
return requested_plays

View file

@ -4,10 +4,11 @@ from pydantic import HttpUrl
import requests import requests
from datetime import datetime from datetime import datetime
import time import time
import math
from src.classes import boardgame_classes from src.classes import boardgame_classes, play_classes
from src.modules import auth_manager from src.modules import auth_manager
from src.config import definitions
authenticated_session: requests.Session = requests.Session() authenticated_session: requests.Session = requests.Session()
@ -33,7 +34,7 @@ def get_boardgame(boardgame_id: int) -> boardgame_classes.BoardGame:
def get_multiple_boardgames(boardgame_ids: list[int]) -> list[boardgame_classes.BoardGame]: def get_multiple_boardgames(boardgame_ids: list[int]) -> list[boardgame_classes.BoardGame]:
def divide_list_in_chunks(list_to_divide: list[int], chunk_size: int = 20): def divide_list_in_chunks(list_to_divide: list[int], chunk_size: int = definitions.BGG_MAX_THING_BOARDGAMES):
for i in range(0, len(list_to_divide), chunk_size): for i in range(0, len(list_to_divide), chunk_size):
yield list_to_divide[i:i + chunk_size] yield list_to_divide[i:i + chunk_size]
@ -181,6 +182,51 @@ def convert_collection_xml_to_wishlist_boardgame(boardgame_extra_info: boardgame
return boardgame return boardgame
def convert_playplayer_xml_to_playplayer(playplayer_xml: ET.Element) -> play_classes.PlayPlayer:
score = playplayer_xml.get('score')
if score == '':
score = None
else:
score = float(score)
playplayer_dict = {
"name" : playplayer_xml.get('name'),
"username" : playplayer_xml.get('username'),
"score" : score,
"first_play" : bool(int(playplayer_xml.get('new'))),
"has_won" : bool(int(playplayer_xml.get('win')))
}
playplayer = play_classes.PlayPlayer(**playplayer_dict)
return playplayer
def convert_play_xml_to_play(play_xml: ET.Element) -> play_classes.Play:
date_string = play_xml.get('date')
play_date = datetime.strptime(date_string, '%Y-%m-%d').date()
playplayer_list: list[play_classes.PlayPlayer] = []
for play_player_xml in play_xml.find('players'):
playplayer_list.append(convert_playplayer_xml_to_playplayer(play_player_xml))
play_dict = {
"boardgame_id" : int(play_xml.find('item').get('objectid')),
"players" : playplayer_list,
"play_date" : play_date,
"duration" : int(play_xml.get('length')),
"ignore_for_stats" : bool(play_xml.get('nowinstats')),
"location" : play_xml.get('location')
}
play = play_classes.Play(**play_dict)
return play
#Creates list of board games from a collection '/collection' URL #Creates list of board games from a collection '/collection' URL
def get_boardgames_from_collection_url(collection_url: str, boardgame_type: boardgame_classes.BoardgameType) -> list[boardgame_classes.BoardGame]: def get_boardgames_from_collection_url(collection_url: str, boardgame_type: boardgame_classes.BoardgameType) -> list[boardgame_classes.BoardGame]:
collection_xml = url_to_xml_object(collection_url) collection_xml = url_to_xml_object(collection_url)
@ -239,6 +285,29 @@ def get_user_wishlist_collection() -> list[boardgame_classes.BoardGame]:
return wishlisted_boardgames return wishlisted_boardgames
def get_plays() -> list[play_classes.Play]:
first_page_url = 'https://boardgamegeek.com/xmlapi2/plays?username={}'.format(auth_manager.username)
plays_first_page_xml_object = url_to_xml_object(first_page_url)
amount_of_plays_total = float(plays_first_page_xml_object.get('total'))
amount_of_pages_needed = math.ceil(amount_of_plays_total/definitions.BGG_PLAY_PAGE_SIZE)
all_plays : list[play_classes.Play] = []
for page in range(amount_of_pages_needed):
url = 'https://boardgamegeek.com/xmlapi2/plays?username={}&page={}'.format(auth_manager.username, page)
plays_page_xml_object = url_to_xml_object(url)
for play_xml in plays_page_xml_object:
new_play = convert_play_xml_to_play(play_xml)
all_plays.append(new_play)
return all_plays
def load_authenticated_bgg_session(username: str, password: str) -> requests.Session: def load_authenticated_bgg_session(username: str, password: str) -> requests.Session:
global authenticated_session global authenticated_session