1
This commit is contained in:
@@ -0,0 +1,109 @@
|
||||
from pathlib import Path
|
||||
|
||||
import pytest
|
||||
|
||||
from core.basic.character import createCharacter
|
||||
from core.basic.equipment import get_equipment
|
||||
|
||||
|
||||
CHARACTER_ROOT = Path(__file__).resolve().parents[2] / "core" / "character" / "GF"
|
||||
DEFAULT_ALTER = "GF.swordman_male.weapon_master"
|
||||
RESULT_KEYS = {"uuid", "skills", "info", "suits", "buffer"}
|
||||
EQUIP_PARTS = {
|
||||
"武器",
|
||||
"副武器",
|
||||
"称号",
|
||||
"上衣",
|
||||
"头肩",
|
||||
"下装",
|
||||
"腰带",
|
||||
"鞋",
|
||||
"手镯",
|
||||
"项链",
|
||||
"戒指",
|
||||
"辅助装备",
|
||||
"魔法石",
|
||||
"耳环",
|
||||
}
|
||||
KNOWN_BROKEN_ALTERS = {
|
||||
"GF.extra.creator": "基础属性表缺少 外传1",
|
||||
"GF.extra.dark_knight": "基础属性表缺少 外传2",
|
||||
"GF.fighter_female.brawler_female": "输出类型未匹配到伤害系数",
|
||||
"GF.imperialknight.breaker": "基础属性表缺少 帝国骑士",
|
||||
"GF.knight.elven_knight": "职业模块导入时报 data 未初始化",
|
||||
"GF.priest_female.infighter_female": "基础属性表缺少 蓝拳圣使-圣职者(女)",
|
||||
}
|
||||
|
||||
|
||||
def _discover_alters() -> list[str]:
|
||||
alters = []
|
||||
for path in sorted(CHARACTER_ROOT.rglob("*.py")):
|
||||
if path.name == "__init__.py":
|
||||
continue
|
||||
text = path.read_text(encoding="utf-8")
|
||||
if "classChange" not in text:
|
||||
continue
|
||||
relative = path.relative_to(CHARACTER_ROOT).with_suffix("")
|
||||
alters.append("GF." + ".".join(relative.parts))
|
||||
return alters
|
||||
|
||||
|
||||
def _character_params():
|
||||
params = []
|
||||
for alter in _discover_alters():
|
||||
marks = []
|
||||
if alter in KNOWN_BROKEN_ALTERS:
|
||||
marks.append(pytest.mark.xfail(reason=KNOWN_BROKEN_ALTERS[alter], strict=True))
|
||||
params.append(pytest.param(alter, id=alter, marks=marks))
|
||||
return params
|
||||
|
||||
|
||||
def _equipment_part(equ) -> str | None:
|
||||
if equ.itemType == "武器":
|
||||
return "武器"
|
||||
if equ.itemDetailType in EQUIP_PARTS:
|
||||
return equ.itemDetailType
|
||||
return None
|
||||
|
||||
|
||||
def _equipment_params():
|
||||
params = []
|
||||
for equ in get_equipment("0").equs:
|
||||
part = _equipment_part(equ)
|
||||
if part is None:
|
||||
continue
|
||||
params.append(pytest.param(equ, part, id=f"{part}:{equ.id}:{equ.name}"))
|
||||
return params
|
||||
|
||||
|
||||
def _assert_calc_result_shape(result: dict):
|
||||
assert isinstance(result, dict)
|
||||
assert RESULT_KEYS.issubset(result)
|
||||
assert isinstance(result["skills"], list)
|
||||
assert isinstance(result["info"], list)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("alter", _character_params())
|
||||
def test_all_gf_characters_can_calculate_with_minimal_config(alter, minimal_calc_config):
|
||||
character = createCharacter(alter, "0")
|
||||
|
||||
assert character is not None, f"createCharacter returned None for alter={alter}"
|
||||
_assert_calc_result_shape(character.calc(minimal_calc_config))
|
||||
|
||||
|
||||
@pytest.mark.parametrize(("equ", "part"), _equipment_params())
|
||||
def test_all_equipment_can_calculate_when_equipped_once(equ, part, minimal_calc_config):
|
||||
config = minimal_calc_config.copy()
|
||||
config["equips"] = {
|
||||
part: value.copy()
|
||||
for part, value in minimal_calc_config["equips"].items()
|
||||
}
|
||||
config["equips"][part] = {
|
||||
**config["equips"][part],
|
||||
"id": equ.id,
|
||||
}
|
||||
|
||||
character = createCharacter(DEFAULT_ALTER, "0")
|
||||
|
||||
assert character is not None
|
||||
_assert_calc_result_shape(character.calc(config))
|
||||
Reference in New Issue
Block a user