From 31e42eb996b2c79261ebc669a13623cb4012f0d5 Mon Sep 17 00:00:00 2001 From: Samuel Roach Date: Sun, 5 Jun 2022 18:12:11 +0100 Subject: [PATCH] Begin moving to lambda expressions and generalise the __str__ and __repr__ of models --- ergast_py/__init__.py | 6 +- ergast_py/ergast.py | 91 +++++++++++++++++------- ergast_py/models/average_speed.py | 10 +-- ergast_py/models/circuit.py | 10 +-- ergast_py/models/constructor.py | 10 +-- ergast_py/models/constructor_standing.py | 10 +-- ergast_py/models/driver.py | 11 +-- ergast_py/models/driver_standing.py | 10 +-- ergast_py/models/fastest_lap.py | 10 +-- ergast_py/models/lap.py | 10 +-- ergast_py/models/location.py | 10 +-- ergast_py/models/pit_stop.py | 10 +-- ergast_py/models/race.py | 11 +-- ergast_py/models/result.py | 10 +-- ergast_py/models/season.py | 10 +-- ergast_py/models/standings_list.py | 10 +-- ergast_py/models/status.py | 10 +-- ergast_py/models/timing.py | 10 +-- 18 files changed, 166 insertions(+), 93 deletions(-) diff --git a/ergast_py/__init__.py b/ergast_py/__init__.py index 2660a9c..a546ba8 100644 --- a/ergast_py/__init__.py +++ b/ergast_py/__init__.py @@ -8,8 +8,8 @@ Basic usage: >>> import ergast_py >>> e = ergast_py.Ergast() - >>> e.driver_str("alonso").get_drivers() - [Driver( + >>> e.driver_str("alonso").get_driver() + Driver( driverId=alonso, permanentNumber=14, code=ALO, @@ -17,7 +17,7 @@ Basic usage: givenName=Fernando, familyName=Alonso, dateOfBirth=1981-07-29, - nationality=Spanish)] + nationality=Spanish) Full documentation can be found at https://github.com/Samuel-Roach/ergast-py. diff --git a/ergast_py/ergast.py b/ergast_py/ergast.py index c61e4c1..47af2f2 100644 --- a/ergast_py/ergast.py +++ b/ergast_py/ergast.py @@ -1,4 +1,5 @@ from __future__ import annotations +from typing import Callable from ergast_py.models.driver import Driver from ergast_py.models.circuit import Circuit @@ -8,8 +9,6 @@ from ergast_py.models.status import Status from ergast_py.constants.status_type import StatusType from ergast_py.models.season import Season from ergast_py.models.race import Race -from ergast_py.models.lap import Lap -from ergast_py.models.pit_stop import PitStop from ergast_py.requester import Requester from ergast_py.type_constructor import TypeConstructor @@ -55,8 +54,8 @@ class Ergast(): self.params["season"] = year return self - def round(self, round: int="last") -> Ergast: - self.params["round"] = round + def round(self, round_no: int="last") -> Ergast: + self.params["round"] = round_no return self def driver(self, driver: Driver) -> Ergast: @@ -139,19 +138,27 @@ class Ergast(): # RETURN FUNCTIONS # + # Lambda queries + + def _get_items(self, get_items: Callable, construct_items: Callable): + items_json = get_items(self.params) + items = construct_items(items_json) + self.reset() + return items + + def _get_item(self, get_items: Callable, construct_items: Callable): + items = self._get_items(get_items, construct_items) + if len(items) == 1: + return items[0] + raise Warning("More than 1 element found") + # Race and Results Queries def get_circuits(self) -> list[Circuit]: - circuits_json = self.requester.get_circuits(self.params) - circuits = self.type_constructor.construct_circuits(circuits_json) - self.reset() - return circuits + return self._get_items(self.requester.get_circuits, self.type_constructor.construct_circuits) def get_circuit(self) -> Circuit: - circuits_json = self.requester.get_circuits(self.params) - circuits = self.type_constructor.construct_circuits(circuits_json) - self.reset() - return circuits[0] + return self._get_item(self.requester.get_circuits, self.type_constructor.construct_circuits) def get_constructors(self) -> list[Constructor]: constructors_json = self.requester.get_constructors(self.params) @@ -163,7 +170,10 @@ class Ergast(): constructors_json = self.requester.get_constructors(self.params) constructors = self.type_constructor.construct_constructors(constructors_json) self.reset() - return constructors[0] + if len(constructors) == 1: + return constructors[0] + else: + raise Exception("More than 1 item found") def get_drivers(self) -> list[Driver]: drivers_json = self.requester.get_drivers(self.params) @@ -175,7 +185,10 @@ class Ergast(): drivers_json = self.requester.get_drivers(self.params) drivers = self.type_constructor.construct_drivers(drivers_json) self.reset() - return drivers[0] + if len(drivers) == 1: + return drivers[0] + else: + raise Exception("More than 1 item found") def get_qualifyings(self) -> list[Race]: qualify_json = self.requester.get_qualifying(self.params) @@ -187,7 +200,10 @@ class Ergast(): qualify_json = self.requester.get_qualifying(self.params) qualifying = self.type_constructor.construct_races(qualify_json) self.reset() - return qualifying[0] + if len(qualifying) == 1: + return qualifying[0] + else: + raise Exception("More than 1 item found") def get_sprints(self) -> list[Race]: sprint_json = self.requester.get_sprints(self.params) @@ -199,7 +215,10 @@ class Ergast(): sprint_json = self.requester.get_sprints(self.params) sprint = self.type_constructor.construct_races(sprint_json) self.reset() - return sprint[0] + if len(sprint) == 1: + return sprint[0] + else: + raise Exception("More than 1 item found") def get_results(self) -> list[Race]: results_json = self.requester.get_results(self.params) @@ -211,7 +230,10 @@ class Ergast(): results_json = self.requester.get_results(self.params) results = self.type_constructor.construct_races(results_json) self.reset() - return results[0] + if len(results) == 1: + return results[0] + else: + raise Exception("More than 1 item found") def get_races(self) -> list[Race]: races_json = self.requester.get_races(self.params) @@ -223,7 +245,10 @@ class Ergast(): races_json = self.requester.get_races(self.params) races = self.type_constructor.construct_races(races_json) self.reset() - return races[0] + if len(races) == 1: + return races[0] + else: + raise Exception("More than 1 item found") def get_seasons(self) -> list[Season]: seasons_json = self.requester.get_seasons(self.params) @@ -235,7 +260,10 @@ class Ergast(): seasons_json = self.requester.get_seasons(self.params) seasons = self.type_constructor.construct_seasons(seasons_json) self.reset() - return seasons[0] + if len(seasons) == 1: + return seasons[0] + else: + raise Exception("More than 1 item found") def get_statuses(self) -> list[Status]: statuses_json = self.requester.get_statuses(self.params) @@ -247,7 +275,10 @@ class Ergast(): statuses_json = self.requester.get_statuses(self.params) statuses = self.type_constructor.construct_statuses(statuses_json) self.reset() - return statuses[0] + if len(statuses) == 1: + return statuses[0] + else: + raise Exception("More than 1 item found") # Standings Queries @@ -261,7 +292,10 @@ class Ergast(): standings_lists_json = self.requester.get_driver_standings(self.params) standings_lists = self.type_constructor.construct_standings_lists(standings_lists_json) self.reset() - return standings_lists[0] + if len(standings_lists) == 1: + return standings_lists[0] + else: + raise Exception("More than 1 item found") def get_constructor_standings(self) -> list[StandingsList]: standings_lists_json = self.requester.get_constructor_standings(self.params) @@ -273,7 +307,10 @@ class Ergast(): standings_lists_json = self.requester.get_constructor_standings(self.params) standings_lists = self.type_constructor.construct_standings_lists(standings_lists_json) self.reset() - return standings_lists[0] + if len(standings_lists) == 1: + return standings_lists[0] + else: + raise Exception("More than 1 item found") # Laps and Pit Stops Queries @@ -287,7 +324,10 @@ class Ergast(): laps_json = self.requester.get_laps(self.params) laps = self.type_constructor.construct_races(laps_json) self.reset() - return laps[0] + if len(laps) == 1: + return laps[0] + else: + raise Exception("More than 1 item found") def get_pit_stops(self) -> list[Race]: pit_stops_json = self.requester.get_pit_stops(self.params) @@ -299,4 +339,7 @@ class Ergast(): pit_stops_json = self.requester.get_pit_stops(self.params) pit_stops = self.type_constructor.construct_races(pit_stops_json) self.reset() - return pit_stops[0] \ No newline at end of file + if len(pit_stops) == 1: + return pit_stops[0] + else: + raise Exception("More than 1 item found") \ No newline at end of file diff --git a/ergast_py/models/average_speed.py b/ergast_py/models/average_speed.py index cda74f8..e21be93 100644 --- a/ergast_py/models/average_speed.py +++ b/ergast_py/models/average_speed.py @@ -14,8 +14,10 @@ class AverageSpeed: self.speed = speed pass - def __str__(self): - return f"AverageSpeed(units={self.units}, speed={self.speed})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"AverageSpeed(units={self.units}, speed={self.speed})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/circuit.py b/ergast_py/models/circuit.py index 51f4676..cdafc68 100644 --- a/ergast_py/models/circuit.py +++ b/ergast_py/models/circuit.py @@ -19,8 +19,10 @@ class Circuit: self.location = location pass - def __str__(self): - return f"Circuit(circuitId={self.circuitId}, url={self.url}, circuitName={self.circuitName}, location={self.location})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Circuit(circuitId={self.circuitId}, url={self.url}, circuitName={self.circuitName}, location={self.location})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/constructor.py b/ergast_py/models/constructor.py index 4892811..b997ed8 100644 --- a/ergast_py/models/constructor.py +++ b/ergast_py/models/constructor.py @@ -18,8 +18,10 @@ class Constructor: self.nationality = nationality pass - def __str__(self): - return f"Constructor(constructorId={self.constructorId}, url={self.url}, name={self.name}, nationality={self.nationality})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Constructor(constructorId={self.constructorId}, url={self.url}, name={self.name}, nationality={self.nationality})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/constructor_standing.py b/ergast_py/models/constructor_standing.py index 114bb2b..49b288a 100644 --- a/ergast_py/models/constructor_standing.py +++ b/ergast_py/models/constructor_standing.py @@ -22,8 +22,10 @@ class ConstructorStanding: self.constructor = constructor pass - def __str__(self): - return f"ConstructorStanding(position={self.position}, positionText={self.positionText}, points={self.points}, wins={self.wins}, constructor={self.constructor})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"ConstructorStanding(position={self.position}, positionText={self.positionText}, points={self.points}, wins={self.wins}, constructor={self.constructor})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/driver.py b/ergast_py/models/driver.py index 2729d84..bf265a1 100644 --- a/ergast_py/models/driver.py +++ b/ergast_py/models/driver.py @@ -29,9 +29,10 @@ class Driver: self.nationality = nationality pass - def __str__(self): - return f"Driver(driverId={self.driverId}, permanentNumber={self.permanentNumber}, code={self.code}, url={self.url}, givenName={self.givenName}, familyName={self.familyName}, dateOfBirth={self.dateOfBirth}, nationality={self.nationality})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Driver(driverId={self.driverId}, permanentNumber={self.permanentNumber}, code={self.code}, url={self.url}, givenName={self.givenName}, familyName={self.familyName}, dateOfBirth={self.dateOfBirth}, nationality={self.nationality})" - \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/driver_standing.py b/ergast_py/models/driver_standing.py index b538130..747166f 100644 --- a/ergast_py/models/driver_standing.py +++ b/ergast_py/models/driver_standing.py @@ -26,8 +26,10 @@ class DriverStanding: self.constructors = constructors pass - def __str__(self): - return f"DriverStanding(position={self.position}, positionText={self.positionText}, points={self.points}, wins={self.wins}, driver={self.driver}, constructors={self.constructors})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"DriverStanding(position={self.position}, positionText={self.positionText}, points={self.points}, wins={self.wins}, driver={self.driver}, constructors={self.constructors})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/fastest_lap.py b/ergast_py/models/fastest_lap.py index 322729a..29bc08c 100644 --- a/ergast_py/models/fastest_lap.py +++ b/ergast_py/models/fastest_lap.py @@ -20,8 +20,10 @@ class FastestLap: self.averageSpeed = averageSpeed pass - def __str__(self): - return f"FastestLap(rank={self.rank}, lap={self.lap}, time={self.time}, averageSpeed={self.averageSpeed})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"FastestLap(rank={self.rank}, lap={self.lap}, time={self.time}, averageSpeed={self.averageSpeed})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/lap.py b/ergast_py/models/lap.py index c2d6546..248be80 100644 --- a/ergast_py/models/lap.py +++ b/ergast_py/models/lap.py @@ -16,8 +16,10 @@ class Lap: self.timings = timings pass - def __str__(self): - return f"Lap(number={self.number}, timings={self.timings})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Lap(number={self.number}, timings={self.timings})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/location.py b/ergast_py/models/location.py index 7d51e55..d5825e5 100644 --- a/ergast_py/models/location.py +++ b/ergast_py/models/location.py @@ -18,8 +18,10 @@ class Location: self.country = country pass - def __str__(self): - return f"Location(latitude={self.latitude},longitude={self.longitude}, locality={self.locality}, country={self.country})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Location(latitude={self.latitude},longitude={self.longitude}, locality={self.locality}, country={self.country})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/pit_stop.py b/ergast_py/models/pit_stop.py index 57db2e6..bddf890 100644 --- a/ergast_py/models/pit_stop.py +++ b/ergast_py/models/pit_stop.py @@ -22,8 +22,10 @@ class PitStop: self.duration = duration pass - def __str__(self): - return f"PitStop(driverId={self.driverId}, lap={self.lap}, stop={self.stop}, localTime={self.localTime}, duration={self.duration})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"PitStop(driverId={self.driverId}, lap={self.lap}, stop={self.stop}, localTime={self.localTime}, duration={self.duration})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/race.py b/ergast_py/models/race.py index e5c5b49..c70e197 100644 --- a/ergast_py/models/race.py +++ b/ergast_py/models/race.py @@ -53,9 +53,10 @@ class Race: self.laps = laps pass - def __str__(self): - return f"Race(season={self.season}, round={self.round}, url={self.url}, raceName={self.raceName}, circuit={self.circuit}, date={self.date}, results={self.results}, firstPractice={self.firstPractice}, secondPractice={self.secondPractice}, thirdPractice={self.thirdPractice}, sprint={self.sprint}, sprintResults={self.sprintResults}, qualifying={self.qualifying}, qualifyingResults={self.qualifyingResults}, pitStops={self.pitStops}, laps={self.laps})" - - def __repr__(self): - return f"Race(season={self.season}, round={self.round}, url={self.url}, raceName={self.raceName}, circuit={self.circuit}, date={self.date}, results={self.results}, firstPractice={self.firstPractice}, secondPractice={self.secondPractice}, thirdPractice={self.thirdPractice}, sprint={self.sprint}, sprintResults={self.sprintResults}, qualifying={self.qualifying}, qualifyingResults={self.qualifyingResults}, pitStops={self.pitStops}, laps={self.laps})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" diff --git a/ergast_py/models/result.py b/ergast_py/models/result.py index d0717f5..f89cb5e 100644 --- a/ergast_py/models/result.py +++ b/ergast_py/models/result.py @@ -45,8 +45,10 @@ class Result: self.q3 = q3 pass - def __str__(self): - return f"Result(number={self.number}, position={self.position}, positionText={self.positionText}, points={self.points}, driver={self.driver}, constructor={self.constructor}, grid={self.grid}, laps={self.laps}, status={self.status}, time={self.time}, fastestLap={self.fastestLap}, q1={self.q1}, q2={self.q2}, q3={self.q3})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Result(number={self.number}, position={self.position}, positionText={self.positionText}, points={self.points}, driver={self.driver}, constructor={self.constructor}, grid={self.grid}, laps={self.laps}, status={self.status}, time={self.time}, fastestLap={self.fastestLap}, q1={self.q1}, q2={self.q2}, q3={self.q3})" + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/season.py b/ergast_py/models/season.py index 6396e6e..20134ea 100644 --- a/ergast_py/models/season.py +++ b/ergast_py/models/season.py @@ -14,8 +14,10 @@ class Season: self.url = url pass - def __str__(self): - return f"Season(season={self.season}, url={self.url})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Season(season={self.season}, url={self.url})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/standings_list.py b/ergast_py/models/standings_list.py index aed1c47..af154e4 100644 --- a/ergast_py/models/standings_list.py +++ b/ergast_py/models/standings_list.py @@ -21,8 +21,10 @@ class StandingsList: self.constructorStandings = constructorStandings pass - def __str__(self): - return f"StandingsList(season={self.season}, round={self.round}, driverStandings={self.driverStandings}, constructorStandings={self.constructorStandings})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"StandingsList(season={self.season}, round={self.round}, driverStandings={self.driverStandings}, constructorStandings={self.constructorStandings})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/status.py b/ergast_py/models/status.py index 58f39c7..4148e34 100644 --- a/ergast_py/models/status.py +++ b/ergast_py/models/status.py @@ -16,8 +16,10 @@ class Status: self.status = status pass - def __str__(self): - return f"Status(statusId={self.statusId}, count={self.count}, status={self.status})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Status(statusId={self.statusId}, count={self.count}, status={self.status})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file diff --git a/ergast_py/models/timing.py b/ergast_py/models/timing.py index 1bd6320..6aaae04 100644 --- a/ergast_py/models/timing.py +++ b/ergast_py/models/timing.py @@ -17,8 +17,10 @@ class Timing: self.time = time pass - def __str__(self): - return f"Timing(driverId={self.driverId}, position={self.position}, time={self.time})" + def __str__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" - def __repr__(self): - return f"Timing(driverId={self.driverId}, position={self.position}, time={self.time})" \ No newline at end of file + def __repr__(self) -> str: + members = ', '.join(f"{key}={value}" for key, value in self.__dict__.items()) + return f"{type(self).__name__}({members})" \ No newline at end of file