Skip to content

Commit

Permalink
feat: Add initial mimo support
Browse files Browse the repository at this point in the history
  • Loading branch information
seriaati committed Dec 9, 2024
1 parent 80c9dec commit 3b2387b
Show file tree
Hide file tree
Showing 4 changed files with 131 additions and 2 deletions.
70 changes: 68 additions & 2 deletions genshin/client/components/hoyolab.py
Original file line number Diff line number Diff line change
Expand Up @@ -238,8 +238,74 @@ async def fetch_mi18n(
self, filename: str, game: types.Game, *, lang: typing.Optional[str] = None
) -> typing.Mapping[str, str]:
"""Fetch a mi18n file."""
data = await self.request(
return await self.request(
routes.MI18N_URL.get_url(types.Region.OVERSEAS, game) / f"{filename}/{filename}-{lang or self.lang}.json",
cache=client_cache.cache_key("mi18n", filename=filename, game=game, lang=lang or self.lang),
)
return data

def _get_mimo_data(
self, game: typing.Optional[typing.Union[types.Game, typing.Literal["hoyolab"]]] = None
) -> typing.Tuple[int, int]:
"""Get the game and version IDs for Mimo tasks."""
game = game or self.game
if game is None:
raise ValueError("No game specified.")

if game == "hoyolab":
game_id = 5
version_id = 23
elif game is types.Game.ZZZ:
game_id = 8
version_id = 13
elif game is types.Game.STARRAIL:
game_id = 6
version_id = 27
else:
raise ValueError(f"{game!r} is not supported.")

return game_id, version_id

@base.region_specific(types.Region.OVERSEAS)
async def get_mimo_tasks(
self,
*,
game: typing.Optional[typing.Union[types.Game, typing.Literal["hoyolab"]]] = None,
lang: typing.Optional[str] = None,
) -> typing.Sequence[models.MimoTask]:
"""Get a list of Traveling Mimo missions (tasks)."""
game_id, version_id = self._get_mimo_data(game)
data = await self.request(
routes.MIMO_URL.get_url() / "task-list",
params=dict(game_id=game_id, lang=lang or self.lang, version_id=version_id),
)
return [models.MimoTask(**i) for i in data["task_list"]]

@base.region_specific(types.Region.OVERSEAS)
async def claim_mimo_task_reward(
self,
task_id: int,
*,
game: typing.Optional[typing.Union[types.Game, typing.Literal["hoyolab"]]] = None,
lang: typing.Optional[str] = None,
) -> None:
"""Claim a Traveling Mimo mission (task) reward."""
game_id, version_id = self._get_mimo_data(game)
await self.request(
routes.MIMO_URL.get_url() / "receive-point",
params=dict(task_id=task_id, game_id=game_id, lang=lang or self.lang, version_id=version_id),
)

async def finish_mimo_task(
self,
task_id: int,
*,
game: typing.Optional[typing.Union[types.Game, typing.Literal["hoyolab"]]] = None,
lang: typing.Optional[str] = None,
) -> None:
"""Finish a Traveling Mimo mission (task) reward."""
game_id, version_id = self._get_mimo_data(game)
await self.request(
routes.MIMO_URL.get_url() / "finish-task",
data=dict(task_id=task_id, game_id=game_id, lang=lang or self.lang, version_id=version_id),
method="POST",
)
2 changes: 2 additions & 0 deletions genshin/client/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -338,3 +338,5 @@ def get_url(self, region: types.Region, game: types.Game) -> yarl.URL:
),
chinese=dict(),
)

MIMO_URL = Route("https://sg-public-api.hoyolab.com/event/e2023mimotravel")
1 change: 1 addition & 0 deletions genshin/models/hoyolab/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,4 @@
from .announcements import *
from .private import *
from .record import *
from .mimo import *
60 changes: 60 additions & 0 deletions genshin/models/hoyolab/mimo.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
import typing

import pydantic
from genshin.models.model import APIModel, Aliased
import enum

__all__ = ("MimoTask", "MimoTaskStatus")


class MimoTaskStatus(enum.IntEnum):
"""Mimo task status."""

FINISHED = 1
ONGOING = 2
CLAIMED = 3


class MimoTaskType(enum.IntEnum):
"""Mimo task type."""

FINISHABLE = 1
COMMUNITY = 3
DAILY_LOGIN = 12
CONSECUTIVE_LOGIN = 13
IN_GAME = 16


class MimoTask(APIModel):
"""Mimo task."""

id: int = Aliased("task_id")
name: str = Aliased("task_name")
time_type: int
point: int
progress: int
total_progress: int

status: MimoTaskStatus
jump_url: str
window_text: str
type: typing.Union[int, MimoTaskType] = Aliased("task_type")
af_url: str

@pydantic.field_validator("type", mode="before")
def __transform_task_type(cls, v: int) -> typing.Union[int, MimoTaskType]:
try:
return MimoTaskType(v)
except ValueError:
return v


class MimoShopItem(APIModel):
"""Mimo shop item."""

id: int = Aliased("award_id")
status: int
icon: str
name: str
cost: int
stock: int

0 comments on commit 3b2387b

Please sign in to comment.