Spaces:
Running
Running
| import pytest | |
| from random import Random | |
| from draft import backbone_deck, draft_anchor_indexes, draft_deck, draft_deck_from_packs, draft_order, validated_pack_choice | |
| class DraftClient: | |
| # Initialize call tracking for draft generation. | |
| def __init__(self) -> None: | |
| self.calls = 0 | |
| self.deck_sizes: list[int] = [] | |
| # Return one legal earth card and record deck-aware call order. | |
| def create_card(self, payload: dict[str, object]) -> dict[str, object]: | |
| self.calls += 1 | |
| self.deck_sizes.append(len(payload["current_deck"])) # type: ignore[arg-type] | |
| return {"name": f"Ward {self.calls}", "effects": [{"primitive_id": "ward"}]} | |
| class DraftPackClient: | |
| # Initialize call tracking for pack generation. | |
| def __init__(self) -> None: | |
| self.calls = 0 | |
| self.deck_sizes: list[int] = [] | |
| self.anchor_sizes: list[int] = [] | |
| # Return one legal earth pack and record deck-aware call order. | |
| def create_pack(self, payload: dict[str, object]) -> dict[str, object]: | |
| self.calls += 1 | |
| self.deck_sizes.append(len(payload["current_deck"])) # type: ignore[arg-type] | |
| self.anchor_sizes.append(len(payload["draft_anchors"])) # type: ignore[arg-type] | |
| return { | |
| "cards": [ | |
| {"name": f"Ward {self.calls}A", "effects": [{"primitive_id": "ward"}]}, | |
| {"name": f"Ward {self.calls}B", "effects": [{"primitive_id": "block"}]}, | |
| {"name": f"Ward {self.calls}C", "effects": [{"primitive_id": "conditional"}]}, | |
| ] | |
| } | |
| # Verify backbone decks are six fixed text cards. | |
| def test_backbone_deck_has_standard_cards() -> None: | |
| deck = backbone_deck("ice", "cyberpunk") | |
| assert len(deck) == 6 | |
| assert deck[0].name == "Attack (weak)" | |
| assert deck[0].school == "ice" | |
| assert deck[5].rules_text() == "Draw 1 card." | |
| # Verify synergy drafting makes nine deck-aware model calls. | |
| def test_draft_deck_adds_nine_synergy_cards() -> None: | |
| client = DraftClient() | |
| deck = draft_deck(client, "earth", "dark fantasy", (1, 2, 3, 4, 5, 1, 2, 3, 4)) | |
| assert len(deck) == 15 | |
| assert client.deck_sizes == [6, 7, 8, 9, 10, 11, 12, 13, 14] | |
| assert deck[-1].name == "Ward 9" | |
| # Verify pack drafting adds the selected candidate from each pack. | |
| def test_draft_deck_from_packs_adds_selected_cards() -> None: | |
| client = DraftPackClient() | |
| choices: list[int] = [] | |
| # Always choose the second card in the pack. | |
| def choose_index(current_deck: tuple[object, ...], pack: tuple[object, ...]) -> int: | |
| assert len(pack) == 3 | |
| choices.append(len(current_deck)) | |
| return 1 | |
| deck = draft_deck_from_packs(client, "earth", "dark fantasy", (1, 2, 3, 4, 5, 1, 2, 3, 4), choose_index, rng=Random(0)) | |
| assert len(deck) == 15 | |
| assert client.deck_sizes == [6, 7, 8, 9, 10, 11, 12, 13, 14] | |
| assert client.anchor_sizes[:2] == [0, 1] | |
| assert client.anchor_sizes[2:] == [2, 2, 2, 2, 2, 2, 2] | |
| assert choices == [6, 7, 8, 9, 10, 11, 12, 13, 14] | |
| assert deck[-1].name == "Ward 9B" | |
| # Verify anchor indexes are two random synergy positions. | |
| def test_draft_anchor_indexes() -> None: | |
| anchors = draft_anchor_indexes(9, Random(0)) | |
| assert len(anchors) == 2 | |
| assert anchors <= set(range(9)) | |
| with pytest.raises(ValueError, match="at least two"): | |
| draft_anchor_indexes(1, Random(0)) | |
| # Verify draft order drafts anchors before remaining cards. | |
| def test_draft_order_starts_with_anchors() -> None: | |
| assert draft_order(5, frozenset((3, 1))) == (1, 3, 0, 2, 4) | |
| # Verify draft rejects incomplete synergy cost schedules. | |
| def test_draft_deck_requires_nine_costs() -> None: | |
| with pytest.raises(ValueError, match="exactly nine"): | |
| draft_deck(DraftClient(), "earth", "dark fantasy", (1,)) | |
| with pytest.raises(ValueError, match="exactly nine"): | |
| draft_deck_from_packs(DraftPackClient(), "earth", "dark fantasy", (1,), lambda _, __: 0) | |
| # Verify draft pack choices must point into the pack. | |
| def test_validated_pack_choice_rejects_bad_index() -> None: | |
| pack = backbone_deck("earth", "dark fantasy")[:3] | |
| assert validated_pack_choice(2, pack) == 2 | |
| with pytest.raises(ValueError, match="outside"): | |
| validated_pack_choice(3, pack) | |
| with pytest.raises(ValueError, match="outside"): | |
| validated_pack_choice(-1, pack) | |