Skip to content

Commit 0483d44

Browse files
authored
Remove unnecessary features to decrease maintenance/complexity overhead. + Cleanup & more repo usage. (osuAkatsuki#612)
* Start to remove unnecessary complex code & unnecessary features * remove usage of `__all__`, use players repo in players obj, general cleanups * remove more unnecessary code * app host/port required -- remove deprecated vals * unused import * remove deprecated env vars from docker compoes files * re-add warn on lack of internet connectivity * use better word * move internet check into startup dialog
1 parent 250cbfc commit 0483d44

21 files changed

+80
-367
lines changed

app/api/domains/osu.py

+8-1
Original file line numberDiff line numberDiff line change
@@ -1593,9 +1593,16 @@ async def get_screenshot(
15931593
status_code=status.HTTP_404_NOT_FOUND,
15941594
)
15951595

1596+
if extension in ("jpg", "jpeg"):
1597+
media_type = "image/jpeg"
1598+
elif extension == "png":
1599+
media_type = "image/png"
1600+
else:
1601+
media_type = None
1602+
15961603
return FileResponse(
15971604
path=screenshot_path,
1598-
media_type=app.utils.get_media_type(extension),
1605+
media_type=media_type,
15991606
)
16001607

16011608

app/api/init_api.py

+7-3
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,10 @@
22
from __future__ import annotations
33

44
import asyncio
5+
import io
56
import os
67
import pprint
8+
import sys
79
from collections.abc import AsyncIterator
810
from contextlib import asynccontextmanager
911
from typing import Any
@@ -69,11 +71,13 @@ def openapi(self) -> dict[str, Any]:
6971

7072
@asynccontextmanager
7173
async def lifespan(asgi_app: BanchoAPI) -> AsyncIterator[Never]:
72-
app.utils.setup_runtime_environment()
73-
app.utils.ensure_supported_platform()
74-
app.utils.ensure_directory_structure()
74+
if isinstance(sys.stdout, io.TextIOWrapper):
75+
sys.stdout.reconfigure(encoding="utf-8")
76+
77+
app.utils.ensure_persistent_volumes_are_available()
7578

7679
app.state.loop = asyncio.get_running_loop()
80+
7781
if app.utils.is_running_as_admin():
7882
log(
7983
"Running the server with root privileges is not recommended.",

app/bg_loops.py

-2
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010
from app.logging import Ansi
1111
from app.logging import log
1212

13-
__all__ = ("initialize_housekeeping_tasks",)
14-
1513
OSU_CLIENT_MIN_PING_INTERVAL = 300000 // 1000 # defined by osu!
1614

1715

app/commands.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
from collections.abc import Sequence
1616
from dataclasses import dataclass
1717
from datetime import datetime
18+
from datetime import timedelta
1819
from functools import wraps
1920
from pathlib import Path
2021
from time import perf_counter_ns as clock_ns
@@ -64,7 +65,6 @@
6465
from app.repositories import tourney_pool_maps as tourney_pool_maps_repo
6566
from app.repositories import tourney_pools as tourney_pools_repo
6667
from app.usecases.performance import ScoreParams
67-
from app.utils import seconds_readable
6868

6969
if TYPE_CHECKING:
7070
from app.objects.channel import Channel
@@ -1258,7 +1258,7 @@ async def server(ctx: Context) -> str | None:
12581258

12591259
return "\n".join(
12601260
(
1261-
f"{build_str} | uptime: {seconds_readable(uptime)}",
1261+
f"{build_str} | uptime: {timedelta(seconds=uptime)}",
12621262
f"cpu: {cpu_info_str}",
12631263
f"ram: {ram_info}",
12641264
f"search mirror: {mirror_search_url} | download mirror: {mirror_download_url}",

app/constants/clientflags.py

-2
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@
66
from app.utils import escape_enum
77
from app.utils import pymysql_encode
88

9-
__all__ = ("ClientFlags",)
10-
119

1210
@unique
1311
@pymysql_encode(escape_enum)

app/constants/gamemodes.py

-2
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,6 @@
88
from app.utils import escape_enum
99
from app.utils import pymysql_encode
1010

11-
__all__ = ("GAMEMODE_REPR_LIST", "GameMode")
12-
1311
GAMEMODE_REPR_LIST = (
1412
"vn!std",
1513
"vn!taiko",

app/constants/mods.py

-4
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,6 @@
77
from app.utils import escape_enum
88
from app.utils import pymysql_encode
99

10-
__all__ = ("Mods",)
11-
12-
# NOTE: the order of some of these = stupid
13-
1410

1511
@unique
1612
@pymysql_encode(escape_enum)

app/constants/privileges.py

-2
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,6 @@
77
from app.utils import escape_enum
88
from app.utils import pymysql_encode
99

10-
__all__ = ("Privileges", "ClientPrivileges", "ClanPrivileges")
11-
1210

1311
@unique
1412
@pymysql_encode(escape_enum)

app/constants/regexes.py

-3
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,6 @@
22

33
import re
44

5-
__all__ = ("OSU_VERSION", "USERNAME", "EMAIL", "BEST_OF")
6-
7-
85
OSU_VERSION = re.compile(
96
r"^b(?P<date>\d{8})(?:\.(?P<revision>\d))?"
107
r"(?P<stream>beta|cuttingedge|dev|tourney)?$",

app/discord.py

-14
Original file line numberDiff line numberDiff line change
@@ -10,20 +10,6 @@
1010

1111
from app.state import services
1212

13-
# NOTE: this module currently only implements discord webhooks
14-
15-
__all__ = (
16-
"Footer",
17-
"Image",
18-
"Thumbnail",
19-
"Video",
20-
"Provider",
21-
"Author",
22-
"Field",
23-
"Embed",
24-
"Webhook",
25-
)
26-
2713

2814
class Footer:
2915
def __init__(self, text: str, **kwargs: Any) -> None:

app/objects/achievement.py

-2
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@
66
if TYPE_CHECKING:
77
from app.objects.score import Score
88

9-
__all__ = ("Achievement",)
10-
119

1210
class Achievement:
1311
"""A class to represent a single osu! achievement."""

app/objects/channel.py

-2
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010
if TYPE_CHECKING:
1111
from app.objects.player import Player
1212

13-
__all__ = ("Channel",)
14-
1513

1614
class Channel:
1715
"""An osu! chat channel.

app/objects/clan.py

-2
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,6 @@
1111
if TYPE_CHECKING:
1212
from app.objects.player import Player
1313

14-
__all__ = ("Clan",)
15-
1614

1715
class Clan:
1816
"""A class to represent a single bancho.py clan."""

app/objects/player.py

+32-36
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@
1010
from enum import unique
1111
from functools import cached_property
1212
from typing import TYPE_CHECKING
13-
from typing import Any
1413
from typing import TypedDict
1514
from typing import cast
1615

@@ -36,6 +35,7 @@
3635
from app.objects.score import Grade
3736
from app.objects.score import Score
3837
from app.repositories import logs as logs_repo
38+
from app.repositories import players as players_repo
3939
from app.repositories import stats as stats_repo
4040
from app.state.services import Geolocation
4141
from app.utils import escape_enum
@@ -238,7 +238,6 @@ def __init__(
238238

239239
self.id = id
240240
self.name = name
241-
self.safe_name = self.make_safe(self.name)
242241
self.priv = priv
243242
self.pw_bcrypt = pw_bcrypt
244243
self.token = token
@@ -282,8 +281,6 @@ def _noop_enqueue(data: bytes) -> None:
282281

283282
self.pres_filter = PresenceFilter.Nil
284283

285-
# XXX: below is mostly implementation-specific & internal stuff
286-
287284
# store most recent score for each gamemode.
288285
self.recent_scores: dict[GameMode, Score | None] = {
289286
mode: None for mode in GameMode
@@ -297,6 +294,10 @@ def _noop_enqueue(data: bytes) -> None:
297294
def __repr__(self) -> str:
298295
return f"<{self.name} ({self.id})>"
299296

297+
@property
298+
def safe_name(self) -> str:
299+
return make_safe_name(self.name)
300+
300301
@property
301302
def is_online(self) -> bool:
302303
return bool(self.token != "")
@@ -384,11 +385,6 @@ def generate_token() -> str:
384385
"""Generate a random uuid as a token."""
385386
return str(uuid.uuid4())
386387

387-
@staticmethod
388-
def make_safe(name: str) -> str:
389-
"""Return a name safe for usage in sql."""
390-
return make_safe_name(name)
391-
392388
def logout(self) -> None:
393389
"""Log `self` out of the server."""
394390
# invalidate the user's token.
@@ -421,45 +417,45 @@ def logout(self) -> None:
421417

422418
async def update_privs(self, new: Privileges) -> None:
423419
"""Update `self`'s privileges to `new`."""
420+
424421
self.priv = new
422+
if "bancho_priv" in vars(self):
423+
del self.bancho_priv # wipe cached_property
425424

426-
await app.state.services.database.execute(
427-
"UPDATE users SET priv = :priv WHERE id = :user_id",
428-
{"priv": self.priv, "user_id": self.id},
425+
await players_repo.update(
426+
id=self.id,
427+
priv=self.priv,
429428
)
430429

431-
if "bancho_priv" in self.__dict__:
432-
del self.bancho_priv # wipe cached_property
433-
434430
async def add_privs(self, bits: Privileges) -> None:
435431
"""Update `self`'s privileges, adding `bits`."""
432+
436433
self.priv |= bits
434+
if "bancho_priv" in vars(self):
435+
del self.bancho_priv # wipe cached_property
437436

438-
await app.state.services.database.execute(
439-
"UPDATE users SET priv = :priv WHERE id = :user_id",
440-
{"priv": self.priv, "user_id": self.id},
437+
await players_repo.update(
438+
id=self.id,
439+
priv=self.priv,
441440
)
442441

443-
if "bancho_priv" in self.__dict__:
444-
del self.bancho_priv # wipe cached_property
445-
446442
if self.is_online:
447443
# if they're online, send a packet
448444
# to update their client-side privileges
449445
self.enqueue(app.packets.bancho_privileges(self.bancho_priv))
450446

451447
async def remove_privs(self, bits: Privileges) -> None:
452448
"""Update `self`'s privileges, removing `bits`."""
449+
453450
self.priv &= ~bits
451+
if "bancho_priv" in vars(self):
452+
del self.bancho_priv # wipe cached_property
454453

455-
await app.state.services.database.execute(
456-
"UPDATE users SET priv = :priv WHERE id = :user_id",
457-
{"priv": self.priv, "user_id": self.id},
454+
await players_repo.update(
455+
id=self.id,
456+
priv=self.priv,
458457
)
459458

460-
if "bancho_priv" in self.__dict__:
461-
del self.bancho_priv # wipe cached_property
462-
463459
if self.is_online:
464460
# if they're online, send a packet
465461
# to update their client-side privileges
@@ -542,9 +538,9 @@ async def silence(self, admin: Player, duration: float, reason: str) -> None:
542538
"""Silence `self` for `duration` seconds, and log to sql."""
543539
self.silence_end = int(time.time() + duration)
544540

545-
await app.state.services.database.execute(
546-
"UPDATE users SET silence_end = :silence_end WHERE id = :user_id",
547-
{"silence_end": self.silence_end, "user_id": self.id},
541+
await players_repo.update(
542+
id=self.id,
543+
silence_end=self.silence_end,
548544
)
549545

550546
await logs_repo.create(
@@ -570,9 +566,9 @@ async def unsilence(self, admin: Player, reason: str) -> None:
570566
"""Unsilence `self`, and log to sql."""
571567
self.silence_end = int(time.time())
572568

573-
await app.state.services.database.execute(
574-
"UPDATE users SET silence_end = :silence_end WHERE id = :user_id",
575-
{"silence_end": self.silence_end, "user_id": self.id},
569+
await players_repo.update(
570+
id=self.id,
571+
silence_end=self.silence_end,
576572
)
577573

578574
await logs_repo.create(
@@ -1006,9 +1002,9 @@ async def stats_from_sql_full(self, db_conn: databases.core.Connection) -> None:
10061002

10071003
def update_latest_activity_soon(self) -> None:
10081004
"""Update the player's latest activity in the database."""
1009-
task = app.state.services.database.execute(
1010-
"UPDATE users SET latest_activity = UNIX_TIMESTAMP() WHERE id = :user_id",
1011-
{"user_id": self.id},
1005+
task = players_repo.update(
1006+
id=self.id,
1007+
latest_activity=int(time.time()),
10121008
)
10131009
app.state.loop.create_task(task)
10141010

app/settings.py

+2-16
Original file line numberDiff line numberDiff line change
@@ -2,30 +2,16 @@
22

33
import os
44
import tomllib
5-
from datetime import date
65

76
from dotenv import load_dotenv
87

98
from app.settings_utils import read_bool
109
from app.settings_utils import read_list
11-
from app.settings_utils import support_deprecated_vars
1210

1311
load_dotenv()
1412

15-
APP_HOST = support_deprecated_vars(
16-
new_name="APP_HOST",
17-
deprecated_name="SERVER_ADDR",
18-
until=date(2024, 1, 1),
19-
)
20-
APP_PORT = None
21-
_app_port = support_deprecated_vars(
22-
new_name="APP_PORT",
23-
deprecated_name="SERVER_PORT",
24-
until=date(2024, 1, 1),
25-
allow_empty_string=True,
26-
)
27-
if _app_port:
28-
APP_PORT = int(_app_port)
13+
APP_HOST = os.environ["APP_HOST"]
14+
APP_PORT = int(os.environ["APP_PORT"])
2915

3016
DB_HOST = os.environ["DB_HOST"]
3117
DB_PORT = int(os.environ["DB_PORT"])

0 commit comments

Comments
 (0)