idac: added version based stamp and time trial
This commit is contained in:
parent
c086b3f8cf
commit
d2175f5b0e
@ -734,7 +734,7 @@ python dbutils.py upgrade
|
|||||||
### TimeRelease Chapter:
|
### TimeRelease Chapter:
|
||||||
|
|
||||||
1. Story: 1, 2, 3, 4, 5, 6, 7, 8, 9, 19 (Chapter 10), 29 (Chapter 11)
|
1. Story: 1, 2, 3, 4, 5, 6, 7, 8, 9, 19 (Chapter 10), 29 (Chapter 11)
|
||||||
2. MF Ghost: 10, 11, 12, 13, 14, 15
|
2. MF Ghost: 10, 11, 12, 13, 14
|
||||||
3. Bunta: 15, 16, 17, 18, 20, 21, 21, 22
|
3. Bunta: 15, 16, 17, 18, 20, 21, 21, 22
|
||||||
4. Touhou Project Special Event: 23, 24, 25, 26, 27, 28
|
4. Touhou Project Special Event: 23, 24, 25, 26, 27, 28
|
||||||
5. Hatsune Miku Special Event: 36, 37, 38
|
5. Hatsune Miku Special Event: 36, 37, 38
|
||||||
|
@ -17,13 +17,15 @@ timerelease:
|
|||||||
stamp:
|
stamp:
|
||||||
enable: True
|
enable: True
|
||||||
enabled_stamps: # max 3 play stamps
|
enabled_stamps: # max 3 play stamps
|
||||||
- "touhou_remilia_scarlet"
|
150:
|
||||||
- "touhou_flandre_scarlet"
|
- "touhou_remilia_scarlet"
|
||||||
- "touhou_sakuya_izayoi"
|
- "touhou_flandre_scarlet"
|
||||||
|
- "touhou_sakuya_izayoi"
|
||||||
|
|
||||||
timetrial:
|
timetrial:
|
||||||
enable: True
|
enable: True
|
||||||
enabled_timetrial: "touhou_remilia_scarlet"
|
enabled_timetrial:
|
||||||
|
150: "touhou_remilia_scarlet"
|
||||||
|
|
||||||
battle_event:
|
battle_event:
|
||||||
enabled: True
|
enabled: True
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
from typing import Dict
|
||||||
from core.config import CoreConfig
|
from core.config import CoreConfig
|
||||||
|
|
||||||
|
|
||||||
@ -95,17 +96,28 @@ class IDACStampConfig:
|
|||||||
)
|
)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def enabled_stamps(self) -> list:
|
def enabled_stamps(self) -> Dict:
|
||||||
|
"""
|
||||||
|
In the form of:
|
||||||
|
<version as int>:
|
||||||
|
- <stamp name 1>
|
||||||
|
- <stamp name 2>
|
||||||
|
- <stamp name 3>
|
||||||
|
|
||||||
|
max 3 stamps per version
|
||||||
|
|
||||||
|
f.e.:
|
||||||
|
150:
|
||||||
|
- "touhou_remilia_scarlet"
|
||||||
|
- "touhou_flandre_scarlet"
|
||||||
|
- "touhou_sakuya_izayoi"
|
||||||
|
"""
|
||||||
return CoreConfig.get_config_field(
|
return CoreConfig.get_config_field(
|
||||||
self.__config,
|
self.__config,
|
||||||
"idac",
|
"idac",
|
||||||
"stamp",
|
"stamp",
|
||||||
"enabled_stamps",
|
"enabled_stamps",
|
||||||
default=[
|
default={},
|
||||||
"touhou_remilia_scarlet",
|
|
||||||
"touhou_flandre_scarlet",
|
|
||||||
"touhou_sakuya_izayoi",
|
|
||||||
],
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@ -120,13 +132,20 @@ class IDACTimetrialConfig:
|
|||||||
)
|
)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def enabled_timetrial(self) -> str:
|
def enabled_timetrial(self) -> Dict:
|
||||||
|
"""
|
||||||
|
In the form of:
|
||||||
|
<version as int>: <timetrial name>
|
||||||
|
|
||||||
|
f.e.:
|
||||||
|
150: "touhou_remilia_scarlet"
|
||||||
|
"""
|
||||||
return CoreConfig.get_config_field(
|
return CoreConfig.get_config_field(
|
||||||
self.__config,
|
self.__config,
|
||||||
"idac",
|
"idac",
|
||||||
"timetrial",
|
"timetrial",
|
||||||
"enabled_timetrial",
|
"enabled_timetrial",
|
||||||
default="touhou_remilia_scarlet",
|
default={},
|
||||||
)
|
)
|
||||||
|
|
||||||
class IDACTBattleGiftConfig:
|
class IDACTBattleGiftConfig:
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
from collections import defaultdict
|
||||||
from datetime import datetime, timedelta
|
from datetime import datetime, timedelta
|
||||||
import os
|
import os
|
||||||
from random import choice, randint
|
from random import choice, randint
|
||||||
@ -24,42 +25,52 @@ class IDACSeason2(IDACBase):
|
|||||||
self.game_config.timerelease.timerelease_avatar_gacha_no
|
self.game_config.timerelease.timerelease_avatar_gacha_no
|
||||||
)
|
)
|
||||||
|
|
||||||
# load the user configured play stamps (up to 3)
|
# load the user configured play stamps (up to 3) for each game version
|
||||||
self.stamp_info = []
|
self.stamp_info = defaultdict(list)
|
||||||
if self.game_config.stamp.enable:
|
if self.game_config.stamp.enable:
|
||||||
for stamp in self.game_config.stamp.enabled_stamps:
|
enabled_stamps = self.game_config.stamp.enabled_stamps
|
||||||
if not os.path.exists(f"./titles/idac/data/stamp/{stamp}.json"):
|
for game_ver in enabled_stamps.keys():
|
||||||
self.logger.warning(f"Stamp {stamp} is enabled but does not exist!")
|
for stamp in enabled_stamps[game_ver][:3]:
|
||||||
continue
|
if not os.path.exists(f"./titles/idac/data/stamp/{stamp}.json"):
|
||||||
|
self.logger.warning(
|
||||||
|
f"Stamp {stamp} is enabled but does not exist!"
|
||||||
|
)
|
||||||
|
continue
|
||||||
|
|
||||||
with open(
|
|
||||||
f"./titles/idac/data/stamp/{stamp}.json", encoding="UTF-8"
|
|
||||||
) as f:
|
|
||||||
self.logger.debug(f"Loading stamp {stamp}")
|
|
||||||
self.stamp_info.append(self._fix_dates(json.load(f)))
|
|
||||||
|
|
||||||
# load the user configured time trials (only one)
|
|
||||||
self.timetrial_event = {}
|
|
||||||
self.timetrial_event_id = None
|
|
||||||
if self.game_config.timetrial.enable:
|
|
||||||
timetrial = self.game_config.timetrial.enabled_timetrial
|
|
||||||
if timetrial is not None:
|
|
||||||
if not os.path.exists(f"./titles/idac/data/timetrial/{timetrial}.json"):
|
|
||||||
self.logger.warning(
|
|
||||||
f"Timetrial {timetrial} is enabled but does not exist!"
|
|
||||||
)
|
|
||||||
else:
|
|
||||||
self.logger.debug(f"Loading timetrial {timetrial}")
|
|
||||||
with open(
|
with open(
|
||||||
f"./titles/idac/data/timetrial/{timetrial}.json",
|
f"./titles/idac/data/stamp/{stamp}.json", encoding="UTF-8"
|
||||||
encoding="UTF-8",
|
|
||||||
) as f:
|
) as f:
|
||||||
self.timetrial_event = self._fix_dates(json.load(f))
|
self.logger.debug(f"Loading stamp {stamp}")
|
||||||
|
self.stamp_info[game_ver].append(self._fix_dates(json.load(f)))
|
||||||
|
|
||||||
# required for saving
|
# load the user configured time trial (only one) for each game version
|
||||||
self.timetrial_event_id = self.timetrial_event.get(
|
self.timetrial_event = {}
|
||||||
"timetrial_event_id"
|
self.timetrial_event_id = {}
|
||||||
)
|
if self.game_config.timetrial.enable:
|
||||||
|
enabled_timetrial = self.game_config.timetrial.enabled_timetrial
|
||||||
|
for game_ver in enabled_timetrial.keys():
|
||||||
|
timetrial = enabled_timetrial[game_ver]
|
||||||
|
if timetrial is not None:
|
||||||
|
if not os.path.exists(
|
||||||
|
f"./titles/idac/data/timetrial/{timetrial}.json"
|
||||||
|
):
|
||||||
|
self.logger.warning(
|
||||||
|
f"Timetrial {timetrial} is enabled but does not exist!"
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
self.logger.debug(f"Loading timetrial {timetrial}")
|
||||||
|
with open(
|
||||||
|
f"./titles/idac/data/timetrial/{timetrial}.json",
|
||||||
|
encoding="UTF-8",
|
||||||
|
) as f:
|
||||||
|
self.timetrial_event[game_ver] = self._fix_dates(
|
||||||
|
json.load(f)
|
||||||
|
)
|
||||||
|
|
||||||
|
# required for saving
|
||||||
|
self.timetrial_event_id[game_ver] = self.timetrial_event.get(
|
||||||
|
game_ver
|
||||||
|
).get("timetrial_event_id")
|
||||||
|
|
||||||
# load the user configured round event (only one)
|
# load the user configured round event (only one)
|
||||||
asyncio.create_task(self._load_round_event())
|
asyncio.create_task(self._load_round_event())
|
||||||
@ -95,37 +106,55 @@ class IDACSeason2(IDACBase):
|
|||||||
if round is not None:
|
if round is not None:
|
||||||
path = f"./titles/idac/data/rounds/season{self.version+1}/{round}.json"
|
path = f"./titles/idac/data/rounds/season{self.version+1}/{round}.json"
|
||||||
if not os.path.exists(path):
|
if not os.path.exists(path):
|
||||||
self.logger.warning(f"Round info {round} is enabled but json file does not exist!")
|
self.logger.warning(
|
||||||
|
f"Round info {round} is enabled but json file does not exist!"
|
||||||
|
)
|
||||||
else:
|
else:
|
||||||
with open(path, encoding="UTF-8") as f:
|
with open(path, encoding="UTF-8") as f:
|
||||||
self.logger.debug(f"Loading round info {round}...")
|
self.logger.debug(f"Loading round info {round}...")
|
||||||
tmp = json.load(f)
|
tmp = json.load(f)
|
||||||
self.round_event_id = await self.data.rounds._try_load_round_event(tmp["round_event_id"], self.version, tmp)
|
self.round_event_id = (
|
||||||
|
await self.data.rounds._try_load_round_event(
|
||||||
|
tmp["round_event_id"], self.version, tmp
|
||||||
|
)
|
||||||
|
)
|
||||||
self.round_event.append(self._fix_dates(tmp))
|
self.round_event.append(self._fix_dates(tmp))
|
||||||
self.logger.debug(f"Loaded round id for database: {self.round_event_id}...")
|
self.logger.debug(
|
||||||
|
f"Loaded round id for database: {self.round_event_id}..."
|
||||||
|
)
|
||||||
|
|
||||||
# Load last round event
|
# Load last round event
|
||||||
round = self.game_config.round_event.last_round
|
round = self.game_config.round_event.last_round
|
||||||
if round is not None:
|
if round is not None:
|
||||||
path = f"./titles/idac/data/rounds/season{self.version+1}/{round}.json"
|
path = f"./titles/idac/data/rounds/season{self.version+1}/{round}.json"
|
||||||
if not os.path.exists(path):
|
if not os.path.exists(path):
|
||||||
self.logger.warning(f"Round info {round} is enabled but json file does not exist!")
|
self.logger.warning(
|
||||||
|
f"Round info {round} is enabled but json file does not exist!"
|
||||||
|
)
|
||||||
else:
|
else:
|
||||||
with open(path, encoding="UTF-8") as f:
|
with open(path, encoding="UTF-8") as f:
|
||||||
self.logger.debug(f"Loading round info {round}...")
|
self.logger.debug(f"Loading round info {round}...")
|
||||||
tmp = json.load(f)
|
tmp = json.load(f)
|
||||||
self.last_round_event_id = await self.data.rounds._try_load_round_event(tmp["round_event_id"], self.version, tmp)
|
self.last_round_event_id = (
|
||||||
|
await self.data.rounds._try_load_round_event(
|
||||||
|
tmp["round_event_id"], self.version, tmp
|
||||||
|
)
|
||||||
|
)
|
||||||
self.last_round_event.append(tmp)
|
self.last_round_event.append(tmp)
|
||||||
self.logger.debug(f"Loaded round id for database: {self.last_round_event_id}...")
|
self.logger.debug(
|
||||||
|
f"Loaded round id for database: {self.last_round_event_id}..."
|
||||||
|
)
|
||||||
|
|
||||||
# Load top five of last round event
|
# Load top five of last round event
|
||||||
|
|
||||||
# class LastRoundEventRanking(BaseModel):
|
# class LastRoundEventRanking(BaseModel):
|
||||||
# round_rank: int
|
# round_rank: int
|
||||||
# round_point: int
|
# round_point: int
|
||||||
# round_play_count: int
|
# round_play_count: int
|
||||||
|
|
||||||
ranking = await self.data.rounds.get_round_top_five(self.last_round_event_id)
|
ranking = await self.data.rounds.get_round_top_five(
|
||||||
|
self.last_round_event_id
|
||||||
|
)
|
||||||
if ranking is not None:
|
if ranking is not None:
|
||||||
rank_profile = {
|
rank_profile = {
|
||||||
"round_rank": 0,
|
"round_rank": 0,
|
||||||
@ -138,16 +167,19 @@ class IDACSeason2(IDACBase):
|
|||||||
"mytitle_id": 0,
|
"mytitle_id": 0,
|
||||||
"mytitle_effect_id": 0,
|
"mytitle_effect_id": 0,
|
||||||
"car_data": [],
|
"car_data": [],
|
||||||
"user_avatar": []
|
"user_avatar": [],
|
||||||
}
|
}
|
||||||
for user in ranking:
|
for user in ranking:
|
||||||
# get the user's profile
|
# get the user's profile
|
||||||
p = await self.data.profile.get_profile(user["user"], self.version)
|
user_id = user["user"]
|
||||||
|
p = await self.data.profile.get_profile(user_id, self.version)
|
||||||
user_data = p._asdict()
|
user_data = p._asdict()
|
||||||
arcade = await self.data.arcade.get_arcade(user_data["store"])
|
arcade = await self.data.arcade.get_arcade(user_data["store"])
|
||||||
|
|
||||||
user_data["store_name"] = (
|
user_data["store_name"] = (
|
||||||
self.core_cfg.server.name if arcade is None else arcade["name"]
|
self.core_cfg.server.name if arcade is None else arcade["name"]
|
||||||
)
|
)
|
||||||
|
|
||||||
rank_profile["username"] = user_data["username"]
|
rank_profile["username"] = user_data["username"]
|
||||||
rank_profile["country"] = user_data["country"]
|
rank_profile["country"] = user_data["country"]
|
||||||
rank_profile["store"] = user_data["store_name"]
|
rank_profile["store"] = user_data["store_name"]
|
||||||
@ -155,7 +187,7 @@ class IDACSeason2(IDACBase):
|
|||||||
rank_profile["mytitle_effect_id"] = user_data["mytitle_effect_id"]
|
rank_profile["mytitle_effect_id"] = user_data["mytitle_effect_id"]
|
||||||
|
|
||||||
# get the user's avatar
|
# get the user's avatar
|
||||||
a = await self.data.profile.get_profile_avatar(user["user"])
|
a = await self.data.profile.get_profile_avatar(user_id)
|
||||||
avatar_data = a._asdict()
|
avatar_data = a._asdict()
|
||||||
del avatar_data["id"]
|
del avatar_data["id"]
|
||||||
del avatar_data["user"]
|
del avatar_data["user"]
|
||||||
@ -170,7 +202,10 @@ class IDACSeason2(IDACBase):
|
|||||||
rank_profile["online_battle_rank"] = rank_data["online_battle_rank"]
|
rank_profile["online_battle_rank"] = rank_data["online_battle_rank"]
|
||||||
|
|
||||||
# get the user's car
|
# get the user's car
|
||||||
cars = await self.data.item.get_cars(self.version, user_id, only_pickup=True)
|
cars = await self.data.item.get_cars(
|
||||||
|
self.version, user_id, only_pickup=True
|
||||||
|
)
|
||||||
|
|
||||||
fulltune_count = 0
|
fulltune_count = 0
|
||||||
total_car_parts_count = 0
|
total_car_parts_count = 0
|
||||||
car_data = []
|
car_data = []
|
||||||
@ -183,7 +218,9 @@ class IDACSeason2(IDACBase):
|
|||||||
rank_profile["car_data"] = car_data
|
rank_profile["car_data"] = car_data
|
||||||
|
|
||||||
# get round info
|
# get round info
|
||||||
ri = await self.data.rounds.get_round_info_by_id(user["user"], self.last_round_event_id)
|
ri = await self.data.rounds.get_round_info_by_id(
|
||||||
|
user_id, self.last_round_event_id
|
||||||
|
)
|
||||||
if ri is not None:
|
if ri is not None:
|
||||||
ri = ri._asdict()
|
ri = ri._asdict()
|
||||||
rank_profile["round_rank"] = user["find_in_set_1"]
|
rank_profile["round_rank"] = user["find_in_set_1"]
|
||||||
@ -214,16 +251,16 @@ class IDACSeason2(IDACBase):
|
|||||||
|
|
||||||
output[key] = value
|
output[key] = value
|
||||||
return output
|
return output
|
||||||
|
|
||||||
|
def _headers_to_version(self, headers: Dict) -> int:
|
||||||
|
version = headers.get("device_version", "1.00.00")
|
||||||
|
return int(version.replace(".", "")[:-2])
|
||||||
|
|
||||||
def _special_story_type(self, headers: Dict):
|
def _special_story_type(self, headers: Dict):
|
||||||
version = headers["device_version"]
|
ver = self._headers_to_version(headers)
|
||||||
ver_str = version.replace(".", "")[:3]
|
|
||||||
|
|
||||||
# 4 = touhou project, 5 = hatsune miku
|
# 4 = touhou project, 5 = hatsune miku
|
||||||
return {
|
return {150: 4, 170: 5}.get(ver, 0)
|
||||||
"150": 4,
|
|
||||||
"170": 5
|
|
||||||
}.get(ver_str, 0)
|
|
||||||
|
|
||||||
async def handle_boot_getconfigdata_request(self, data: Dict, headers: Dict):
|
async def handle_boot_getconfigdata_request(self, data: Dict, headers: Dict):
|
||||||
"""
|
"""
|
||||||
@ -255,8 +292,7 @@ class IDACSeason2(IDACBase):
|
|||||||
34 = FullTune Ticket Fragment
|
34 = FullTune Ticket Fragment
|
||||||
35 = Underneon Lights
|
35 = Underneon Lights
|
||||||
"""
|
"""
|
||||||
version = headers["device_version"]
|
ver_str = self._headers_to_version(headers)
|
||||||
ver_str = version.replace(".", "")[:3]
|
|
||||||
|
|
||||||
if self.core_cfg.server.is_using_proxy:
|
if self.core_cfg.server.is_using_proxy:
|
||||||
domain_api_game = f"http://{self.core_cfg.server.hostname}/{ver_str}/"
|
domain_api_game = f"http://{self.core_cfg.server.hostname}/{ver_str}/"
|
||||||
@ -272,7 +308,7 @@ class IDACSeason2(IDACBase):
|
|||||||
datetime.strptime("2023-01-01", "%Y-%m-%d").timestamp()
|
datetime.strptime("2023-01-01", "%Y-%m-%d").timestamp()
|
||||||
),
|
),
|
||||||
"end_dt": int(datetime.strptime("2029-01-01", "%Y-%m-%d").timestamp()),
|
"end_dt": int(datetime.strptime("2029-01-01", "%Y-%m-%d").timestamp()),
|
||||||
"story_type": special_story_type
|
"story_type": special_story_type,
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
@ -309,7 +345,7 @@ class IDACSeason2(IDACBase):
|
|||||||
"last_round_event": self.last_round_event,
|
"last_round_event": self.last_round_event,
|
||||||
"last_round_event_ranking": self.last_round_event_ranking,
|
"last_round_event_ranking": self.last_round_event_ranking,
|
||||||
"round_event_exp": [],
|
"round_event_exp": [],
|
||||||
"stamp_info": self.stamp_info,
|
"stamp_info": self.stamp_info[ver_str],
|
||||||
# 0 = use default data, 1+ = server version of timereleasedata response
|
# 0 = use default data, 1+ = server version of timereleasedata response
|
||||||
"timerelease_no": self.timerelease_no,
|
"timerelease_no": self.timerelease_no,
|
||||||
# 0 = use default data, 1+ = server version of gachadata response
|
# 0 = use default data, 1+ = server version of gachadata response
|
||||||
@ -477,7 +513,7 @@ class IDACSeason2(IDACBase):
|
|||||||
"theory_close_version": "9.99.99",
|
"theory_close_version": "9.99.99",
|
||||||
# unlocks the version specific special mode
|
# unlocks the version specific special mode
|
||||||
"special_mode_data": special_mode_data,
|
"special_mode_data": special_mode_data,
|
||||||
"timetrial_event_data": self.timetrial_event,
|
"timetrial_event_data": self.timetrial_event[ver_str],
|
||||||
"number_lottery_data": [
|
"number_lottery_data": [
|
||||||
{
|
{
|
||||||
"m_number_lottery_win_number_no": 10,
|
"m_number_lottery_win_number_no": 10,
|
||||||
@ -619,9 +655,9 @@ class IDACSeason2(IDACBase):
|
|||||||
"""
|
"""
|
||||||
timerelease chapter:
|
timerelease chapter:
|
||||||
1 = Story: 1, 2, 3, 4, 5, 6, 7, 8, 9, 19 (Chapter 10), 29 (Chapter 11)
|
1 = Story: 1, 2, 3, 4, 5, 6, 7, 8, 9, 19 (Chapter 10), 29 (Chapter 11)
|
||||||
2 = MF Ghost: 10, 11, 12, 13, 14, 15
|
2 = MF Ghost: 10, 11, 12, 13, 14
|
||||||
3 = Bunta: 15, 16, 17, 18, 20, 21, 21, 22
|
3 = Bunta: 15, 16, 17, 18, 20, 21, 21, 22
|
||||||
4 = Touch Project Special Event: 23, 24, 25, 26, 27, 28
|
4 = Touhou Project Special Event: 23, 24, 25, 26, 27, 28
|
||||||
5 = Hatsune Miku Special Event: 36, 37, 38
|
5 = Hatsune Miku Special Event: 36, 37, 38
|
||||||
"""
|
"""
|
||||||
path = "./titles/idac/data/"
|
path = "./titles/idac/data/"
|
||||||
@ -709,11 +745,11 @@ class IDACSeason2(IDACBase):
|
|||||||
"shop_best_data": best_data,
|
"shop_best_data": best_data,
|
||||||
"rank_management_flag": 0,
|
"rank_management_flag": 0,
|
||||||
}
|
}
|
||||||
|
|
||||||
def _is_valid_version(self, db_version: str, cl_version: str) -> bool:
|
def _is_valid_version(self, db_version: str, cl_version: str) -> bool:
|
||||||
if len(db_version) < 7 or len(cl_version) < 7:
|
if len(db_version) < 7 or len(cl_version) < 7:
|
||||||
return False
|
return False
|
||||||
|
|
||||||
# convert the trings to int and compare
|
# convert the trings to int and compare
|
||||||
db_version = int(db_version.replace(".", "")[:7])
|
db_version = int(db_version.replace(".", "")[:7])
|
||||||
cl_version = int(cl_version.replace(".", "")[:7])
|
cl_version = int(cl_version.replace(".", "")[:7])
|
||||||
@ -975,15 +1011,17 @@ class IDACSeason2(IDACBase):
|
|||||||
vs_info["course_select_priority"] = data.get("course_select_priority")
|
vs_info["course_select_priority"] = data.get("course_select_priority")
|
||||||
return vs_info
|
return vs_info
|
||||||
|
|
||||||
async def _update_round_info(self, user_id: int, round_event_id: int, point: int, win: int) -> Dict:
|
async def _update_round_info(
|
||||||
|
self, user_id: int, round_event_id: int, point: int, win: int
|
||||||
|
) -> Dict:
|
||||||
# get the round info data from database
|
# get the round info data from database
|
||||||
round_info = []
|
round_info = []
|
||||||
ri = await self.data.rounds.get_round_info_by_id(user_id, round_event_id)
|
ri = await self.data.rounds.get_round_info_by_id(user_id, round_event_id)
|
||||||
if ri is not None:
|
if ri is not None:
|
||||||
tmp = ri._asdict()
|
tmp = ri._asdict()
|
||||||
|
|
||||||
del tmp["id"]
|
del tmp["id"]
|
||||||
|
|
||||||
# calculate new round points and info
|
# calculate new round points and info
|
||||||
tmp["point"] = 0 if tmp["point"] + point < 1 else tmp["point"] + point
|
tmp["point"] = 0 if tmp["point"] + point < 1 else tmp["point"] + point
|
||||||
tmp["count"] += 1
|
tmp["count"] += 1
|
||||||
@ -994,7 +1032,7 @@ class IDACSeason2(IDACBase):
|
|||||||
await self.data.rounds.put_round_event(user_id, round_event_id, tmp)
|
await self.data.rounds.put_round_event(user_id, round_event_id, tmp)
|
||||||
|
|
||||||
del tmp["play_dt"]
|
del tmp["play_dt"]
|
||||||
|
|
||||||
# get players new round ranking
|
# get players new round ranking
|
||||||
r = await self.data.rounds.get_round_rank_by_id(user_id, round_event_id)
|
r = await self.data.rounds.get_round_rank_by_id(user_id, round_event_id)
|
||||||
round_ranking = r._asdict()
|
round_ranking = r._asdict()
|
||||||
@ -1002,7 +1040,7 @@ class IDACSeason2(IDACBase):
|
|||||||
|
|
||||||
# TODO: get players historical earned points
|
# TODO: get players historical earned points
|
||||||
tmp["total_round_point"] = 0
|
tmp["total_round_point"] = 0
|
||||||
|
|
||||||
round_info.append(tmp)
|
round_info.append(tmp)
|
||||||
else:
|
else:
|
||||||
# new player of now-going round event
|
# new player of now-going round event
|
||||||
@ -1021,11 +1059,10 @@ class IDACSeason2(IDACBase):
|
|||||||
|
|
||||||
# TODO: get players historical earned points
|
# TODO: get players historical earned points
|
||||||
tmp["total_round_point"] = 0
|
tmp["total_round_point"] = 0
|
||||||
|
|
||||||
round_info.append(tmp)
|
round_info.append(tmp)
|
||||||
return round_info
|
return round_info
|
||||||
|
|
||||||
|
|
||||||
def _choose_gift_id(self) -> Dict:
|
def _choose_gift_id(self) -> Dict:
|
||||||
gift_data = self.battle_gift_event["gift_data"]
|
gift_data = self.battle_gift_event["gift_data"]
|
||||||
# calculate the total_rate based on the first_distribution_rate
|
# calculate the total_rate based on the first_distribution_rate
|
||||||
@ -1108,19 +1145,21 @@ class IDACSeason2(IDACBase):
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
# get the users'd round data
|
# get the users'd round data
|
||||||
|
|
||||||
round_info = []
|
round_info = []
|
||||||
ri = await self.data.rounds.get_round_info_by_id(user_id, self.round_event_id)
|
ri = await self.data.rounds.get_round_info_by_id(user_id, self.round_event_id)
|
||||||
if ri is not None:
|
if ri is not None:
|
||||||
r = await self.data.rounds.get_round_rank_by_id(user_id, self.round_event_id)
|
r = await self.data.rounds.get_round_rank_by_id(
|
||||||
|
user_id, self.round_event_id
|
||||||
|
)
|
||||||
round_ranking = r._asdict()
|
round_ranking = r._asdict()
|
||||||
tmp = ri._asdict()
|
tmp = ri._asdict()
|
||||||
del tmp["id"]
|
del tmp["id"]
|
||||||
del tmp["user"]
|
del tmp["user"]
|
||||||
del tmp["round_id"]
|
del tmp["round_id"]
|
||||||
del tmp["play_dt"]
|
del tmp["play_dt"]
|
||||||
|
|
||||||
tmp["rank"] = round_ranking["find_in_set_1"]
|
tmp["rank"] = round_ranking["find_in_set_1"]
|
||||||
# TODO: calculate this
|
# TODO: calculate this
|
||||||
tmp["total_round_point"] = 0
|
tmp["total_round_point"] = 0
|
||||||
@ -1282,10 +1321,12 @@ class IDACSeason2(IDACBase):
|
|||||||
del tmp["create_date_weekly"]
|
del tmp["create_date_weekly"]
|
||||||
stamp_event_data.append(tmp)
|
stamp_event_data.append(tmp)
|
||||||
|
|
||||||
|
ver_str = self._headers_to_version(headers)
|
||||||
|
|
||||||
# get the user's timetrial event data
|
# get the user's timetrial event data
|
||||||
timetrial_event_data = {}
|
timetrial_event_data = {}
|
||||||
timetrial = await self.data.item.get_timetrial_event(
|
timetrial = await self.data.item.get_timetrial_event(
|
||||||
user_id, self.timetrial_event_id
|
user_id, self.timetrial_event_id[ver_str]
|
||||||
)
|
)
|
||||||
if timetrial is not None:
|
if timetrial is not None:
|
||||||
timetrial_event_data = {
|
timetrial_event_data = {
|
||||||
@ -2031,9 +2072,11 @@ class IDACSeason2(IDACBase):
|
|||||||
data["play_dt"] = datetime.now()
|
data["play_dt"] = datetime.now()
|
||||||
await self.data.item.put_time_trial(self.version, user_id, data)
|
await self.data.item.put_time_trial(self.version, user_id, data)
|
||||||
|
|
||||||
|
ver_str = self._headers_to_version(headers)
|
||||||
|
|
||||||
# update the timetrial event points
|
# update the timetrial event points
|
||||||
await self.data.item.put_timetrial_event(
|
await self.data.item.put_timetrial_event(
|
||||||
user_id, self.timetrial_event_id, event_point
|
user_id, self.timetrial_event_id[ver_str], event_point
|
||||||
)
|
)
|
||||||
|
|
||||||
# update the tips play count
|
# update the tips play count
|
||||||
@ -2044,6 +2087,8 @@ class IDACSeason2(IDACBase):
|
|||||||
{"timetrial_play_count": tips["timetrial_play_count"] + 1},
|
{"timetrial_play_count": tips["timetrial_play_count"] + 1},
|
||||||
)
|
)
|
||||||
|
|
||||||
|
ver_str = self._headers_to_version(headers)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"status_code": "0",
|
"status_code": "0",
|
||||||
"course_rank": course_rank,
|
"course_rank": course_rank,
|
||||||
@ -2052,7 +2097,7 @@ class IDACSeason2(IDACBase):
|
|||||||
"car_use_count": [],
|
"car_use_count": [],
|
||||||
"maker_use_count": [],
|
"maker_use_count": [],
|
||||||
"timetrial_event_data": {
|
"timetrial_event_data": {
|
||||||
"timetrial_event_id": self.timetrial_event_id,
|
"timetrial_event_id": self.timetrial_event_id[ver_str],
|
||||||
"point": event_point,
|
"point": event_point,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -3060,7 +3105,7 @@ class IDACSeason2(IDACBase):
|
|||||||
}
|
}
|
||||||
|
|
||||||
async def handle_user_updateonlinebattle_request(self, data: Dict, headers: Dict):
|
async def handle_user_updateonlinebattle_request(self, data: Dict, headers: Dict):
|
||||||
#TODO: voiding cheaters' result. which will need to analysis historical battle results returned by the game.
|
# TODO: voiding cheaters' result. which will need to analysis historical battle results returned by the game.
|
||||||
return {
|
return {
|
||||||
"status_code": "0",
|
"status_code": "0",
|
||||||
"bothwin_penalty": 1,
|
"bothwin_penalty": 1,
|
||||||
@ -3136,7 +3181,9 @@ class IDACSeason2(IDACBase):
|
|||||||
{"online_battle_play_count": tips["online_battle_play_count"] + 1},
|
{"online_battle_play_count": tips["online_battle_play_count"] + 1},
|
||||||
)
|
)
|
||||||
|
|
||||||
round_info = await self._update_round_info(user_id, self.round_event_id, data.pop("round_point"), data.pop("win_flg"))
|
round_info = await self._update_round_info(
|
||||||
|
user_id, self.round_event_id, data.pop("round_point"), data.pop("win_flg")
|
||||||
|
)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"status_code": "0",
|
"status_code": "0",
|
||||||
@ -3237,7 +3284,9 @@ class IDACSeason2(IDACBase):
|
|||||||
"maker_use_count": [],
|
"maker_use_count": [],
|
||||||
}
|
}
|
||||||
|
|
||||||
async def handle_factory_numberlotterybefore_request(self, data: Dict, headers: Dict):
|
async def handle_factory_numberlotterybefore_request(
|
||||||
|
self, data: Dict, headers: Dict
|
||||||
|
):
|
||||||
user_id = headers["session"]
|
user_id = headers["session"]
|
||||||
win_list = []
|
win_list = []
|
||||||
lottery_count = 0
|
lottery_count = 0
|
||||||
@ -3254,23 +3303,21 @@ class IDACSeason2(IDACBase):
|
|||||||
for number in range(10):
|
for number in range(10):
|
||||||
if saved_value & 1:
|
if saved_value & 1:
|
||||||
# if the least significant bit is 1, add to the win_list
|
# if the least significant bit is 1, add to the win_list
|
||||||
win_list.append({
|
win_list.append(
|
||||||
"m_number_lottery_schedule_no": 1,
|
{"m_number_lottery_schedule_no": 1, "win_number": number * 1111}
|
||||||
"win_number": number * 1111
|
)
|
||||||
})
|
|
||||||
|
|
||||||
# right shift saved_value to check the next bit
|
# right shift saved_value to check the next bit
|
||||||
saved_value >>= 1
|
saved_value >>= 1
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"status_code": "0",
|
"status_code": "0",
|
||||||
"lottery_info": {
|
"lottery_info": {"lottery_count": lottery_count, "win_list": win_list},
|
||||||
"lottery_count": lottery_count,
|
|
||||||
"win_list": win_list
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async def handle_factory_numberlotteryresult_request(self, data: Dict, headers: Dict):
|
async def handle_factory_numberlotteryresult_request(
|
||||||
|
self, data: Dict, headers: Dict
|
||||||
|
):
|
||||||
user_id = headers["session"]
|
user_id = headers["session"]
|
||||||
win_number = data.pop("win_number")
|
win_number = data.pop("win_number")
|
||||||
lottery_count = data.pop("lottery_count")
|
lottery_count = data.pop("lottery_count")
|
||||||
@ -3289,20 +3336,23 @@ class IDACSeason2(IDACBase):
|
|||||||
# calculate the bit position to set based on the win_number
|
# calculate the bit position to set based on the win_number
|
||||||
shifted = win_number // 1111
|
shifted = win_number // 1111
|
||||||
saved_value += 1 << shifted
|
saved_value += 1 << shifted
|
||||||
|
|
||||||
# update the create_date timestamp when the last create_date is older than 24 hours
|
# update the create_date timestamp when the last create_date is older than 24 hours
|
||||||
if l and datetime.now() - l["create_date"] > timedelta(days=1):
|
if l and datetime.now() - l["create_date"] > timedelta(days=1):
|
||||||
create_date = datetime.now()
|
create_date = datetime.now()
|
||||||
|
|
||||||
# update the lottery data with the new saved_value and lottery_count
|
# update the lottery data with the new saved_value and lottery_count
|
||||||
await self.data.factory.put_lottery(user_id, self.version, saved_value, lottery_count, create_date)
|
await self.data.factory.put_lottery(
|
||||||
|
user_id, self.version, saved_value, lottery_count, create_date
|
||||||
|
)
|
||||||
|
|
||||||
if license_no != 10000 and is_end == 1:
|
if license_no != 10000 and is_end == 1:
|
||||||
# ithe lottery is ended, save car data
|
# ithe lottery is ended, save car data
|
||||||
await self.data.item.put_car(user_id, self.version, {
|
await self.data.item.put_car(
|
||||||
"style_car_id": style_car_id,
|
user_id,
|
||||||
"l_no": license_no
|
self.version,
|
||||||
})
|
{"style_car_id": style_car_id, "l_no": license_no},
|
||||||
|
)
|
||||||
|
|
||||||
# save each ticket data
|
# save each ticket data
|
||||||
for ticket in ticket_data:
|
for ticket in ticket_data:
|
||||||
@ -3311,6 +3361,4 @@ class IDACSeason2(IDACBase):
|
|||||||
# save remaining profile data
|
# save remaining profile data
|
||||||
await self.data.profile.put_profile(user_id, self.version, data)
|
await self.data.profile.put_profile(user_id, self.version, data)
|
||||||
|
|
||||||
return {
|
return {"status_code": "0"}
|
||||||
"status_code": "0"
|
|
||||||
}
|
|
||||||
|
Loading…
Reference in New Issue
Block a user