90 lines
3.4 KiB
Python
90 lines
3.4 KiB
Python
import os
|
|
import re
|
|
from typing import Dict, Optional
|
|
|
|
class Tja:
|
|
def __init__(self, text: str):
|
|
self.text = text
|
|
self.title: Optional[str] = None
|
|
self.subtitle: Optional[str] = None
|
|
self.wave: Optional[str] = None
|
|
self.offset: Optional[float] = None
|
|
self.courses: Dict[str, Dict[str, Optional[int]]] = {}
|
|
self._parse()
|
|
|
|
def _parse(self) -> None:
|
|
lines = self.text.split("\n")
|
|
current_course: Optional[str] = None
|
|
for raw in lines:
|
|
line = raw.strip()
|
|
if not line:
|
|
continue
|
|
if ":" in line:
|
|
k, v = line.split(":", 1)
|
|
key = k.strip().upper()
|
|
val = v.strip()
|
|
if key == "TITLE":
|
|
self.title = val or None
|
|
elif key == "SUBTITLE":
|
|
self.subtitle = val or None
|
|
elif key == "WAVE":
|
|
self.wave = val or None
|
|
elif key == "OFFSET":
|
|
try:
|
|
self.offset = float(val)
|
|
except ValueError:
|
|
self.offset = None
|
|
elif key == "COURSE":
|
|
course_map = {
|
|
"EASY": "easy",
|
|
"NORMAL": "normal",
|
|
"HARD": "hard",
|
|
"ONI": "oni",
|
|
"EDIT": "ura",
|
|
"URA": "ura",
|
|
}
|
|
current_course = course_map.get(val.strip().upper())
|
|
if current_course and current_course not in self.courses:
|
|
self.courses[current_course] = {"stars": None, "branch": False}
|
|
elif key == "LEVEL" and current_course:
|
|
try:
|
|
stars = int(re.split(r"\s+", val)[0])
|
|
except ValueError:
|
|
stars = None
|
|
self.courses[current_course]["stars"] = stars
|
|
else:
|
|
if current_course and (line.startswith("BRANCHSTART") or line.startswith("#BRANCHSTART")):
|
|
self.courses[current_course]["branch"] = True
|
|
|
|
def to_mongo(self, song_id: str, created_ns: int) -> Dict:
|
|
ext = None
|
|
if self.wave:
|
|
base = os.path.basename(self.wave)
|
|
_, e = os.path.splitext(base)
|
|
if e:
|
|
ext = e.lstrip(".").lower()
|
|
if not ext:
|
|
ext = "mp3"
|
|
courses_out: Dict[str, Optional[Dict[str, Optional[int]]]] = {}
|
|
for name in ["easy", "normal", "hard", "oni", "ura"]:
|
|
courses_out[name] = self.courses.get(name) or None
|
|
return {
|
|
"id": song_id,
|
|
"type": "tja",
|
|
"title": self.title,
|
|
"subtitle": self.subtitle,
|
|
"title_lang": {"ja": self.title, "en": None, "cn": None, "tw": None, "ko": None},
|
|
"subtitle_lang": {"ja": self.subtitle, "en": None, "cn": None, "tw": None, "ko": None},
|
|
"courses": courses_out,
|
|
"enabled": False,
|
|
"category_id": None,
|
|
"music_type": ext,
|
|
"offset": self.offset or 0,
|
|
"skin_id": None,
|
|
"preview": 0,
|
|
"volume": 1.0,
|
|
"maker_id": None,
|
|
"hash": None,
|
|
"order": song_id,
|
|
"created_ns": created_ns,
|
|
} |