Gift-Code-Web/models/honkai.py

117 lines
3.8 KiB
Python
Raw Normal View History

2023-06-11 02:40:09 +00:00
import re
2023-06-22 06:34:26 +00:00
from pytz import timezone
2023-06-10 14:20:58 +00:00
from datetime import datetime
from typing import List
from httpx import get
from bs4 import BeautifulSoup, Tag
from .code import Code, Reward
2023-07-05 03:17:18 +00:00
url = "https://honkai.gg/codes/"
2023-06-10 14:20:58 +00:00
reward_map = {
"Stellar Jade": "星琼",
"Credit": "信用点",
"Credits": "信用点",
"Traveler's Guide": "漫游指南",
2023-07-05 03:17:18 +00:00
"Travelers Guide": "漫游指南",
2023-06-10 14:20:58 +00:00
"Refined Aether": "提纯以太",
"Adventure Log": "冒险记录",
"Dust of Alacrity": "疾速粉尘",
"Condensed Aether": "凝缩以太",
"Cosmic Fried Rice": "大宇宙炒饭",
2023-07-12 14:49:34 +00:00
"Travel Encounters": "旅情见闻",
2023-11-20 13:09:25 +00:00
"Energy Drink": "能量饮料",
"Startaro Bubble": "星芋啵啵",
"Lost Gold Fragments": "遗失碎金",
2024-01-13 06:08:18 +00:00
"Hypnotic Hammer": "安眠锤",
"Camo Paint": "迷彩油漆",
"Dry Emergency Light": "干制应急灯",
2024-02-06 03:38:15 +00:00
"Flaming Potent Tea": "烈焰浓茶",
"Steamed Puffergoat Milk": "热浮羊奶",
"Bottled Soda": "罐装快乐水",
2023-06-10 14:20:58 +00:00
}
def parse_reward(reward: List[str]) -> Reward:
try:
name = reward_map.get(reward[0])
if not name:
2023-06-11 02:40:09 +00:00
# 判断是否为中文
if not re.search("[\u4e00-\u9fa5]", reward[0]):
print("Unknown reward: ", reward[0])
2023-06-10 14:20:58 +00:00
name = reward[0]
return Reward(
name=name,
cnt=int(reward[1]),
)
2023-06-11 02:40:09 +00:00
except Exception as e:
2023-06-10 14:20:58 +00:00
print("Bad reward data: ", reward)
2023-06-11 02:40:09 +00:00
raise e
2023-06-10 14:20:58 +00:00
def parse_code(tr: Tag) -> Code:
tds = tr.find_all("td")
code = tds[0].text.strip()
2023-07-05 03:17:18 +00:00
try:
2023-10-12 11:42:56 +00:00
data = str(tds[2]).split("<br/>")
expire = data[1]
2023-07-12 14:49:34 +00:00
except (IndexError, TypeError):
_, expire = datetime(1970, 1, 1, 1, 0, 0, 0), datetime(2099, 12, 31, 23, 59, 59, 999999)
2023-07-05 03:17:18 +00:00
if isinstance(expire, str):
2023-07-12 14:49:34 +00:00
try:
expire = expire.split(": ")[1].replace("</td>", "")
2023-11-20 13:09:25 +00:00
if "Unknown" in expire:
2023-07-12 14:49:34 +00:00
expire = datetime(2099, 12, 31, 23, 59, 59, 999999)
2024-02-06 03:38:15 +00:00
elif "Expired" in expire:
expire = datetime(1970, 1, 1, 1, 0, 0, 0)
2023-11-20 13:09:25 +00:00
elif "," in expire:
2023-07-12 14:49:34 +00:00
expire = datetime.strptime(expire, "%B %d, %Y")
2023-11-20 13:09:25 +00:00
else:
expire = datetime.strptime(expire, "%B %d")
expire = expire.replace(year=datetime.now().year)
2023-07-12 14:49:34 +00:00
except IndexError:
2023-07-05 03:17:18 +00:00
expire = datetime(2099, 12, 31, 23, 59, 59, 999999)
2023-07-12 14:49:34 +00:00
expire = timezone("Asia/Shanghai").localize(expire)
expire = int(expire.timestamp() * 1000)
2023-06-10 14:20:58 +00:00
rewards = []
2023-07-05 03:17:18 +00:00
for reward in str(tds[1]).split("<br/>"):
2023-11-20 13:09:25 +00:00
reward_soup = BeautifulSoup(reward, "lxml")
2024-01-13 06:08:18 +00:00
reward_text = " ".join(reward_soup.text.strip().split()).replace("×", "x")
2023-11-20 13:09:25 +00:00
reward_div = []
if " x " in reward_text:
reward_div = reward_text.split(" x ")
elif " x" in reward_text:
reward_div = reward_text.split(" x")
2023-06-11 02:40:09 +00:00
if len(reward_div) < 2:
print("Bad td data: ", tds[1])
continue
2023-06-10 14:20:58 +00:00
parsed_reward = parse_reward(reward_div)
if parsed_reward:
rewards.append(parsed_reward)
2023-06-11 02:40:09 +00:00
if not rewards:
for reward in tds[1].find_all("a"):
reward_a = reward.text.strip().split(" x ")
if len(reward_a) < 2:
print("Bad a data: ", tds[1])
continue
parsed_reward = parse_reward(reward_a)
if parsed_reward:
rewards.append(parsed_reward)
2023-06-10 14:20:58 +00:00
return Code(code=code, reward=rewards, expire=expire)
def get_code():
html = get(url).text
soup = BeautifulSoup(html, "lxml")
tables = soup.find_all("table")
codes = []
for table in tables:
trs = table.find_all("tr")[1:]
for tr in trs:
2024-02-06 03:38:15 +00:00
if not tr.text:
continue
2023-06-10 14:20:58 +00:00
codes.append(parse_code(tr))
codes.sort(key=lambda x: x.expire, reverse=True)
return codes