Files
devplacepy/tests/api/battles/actions.py
T

166 lines
5.6 KiB
Python
Raw Normal View History

# retoor <retoor@molodetz.nl>
import time
from datetime import datetime, timedelta, timezone
import requests
from devplacepy.database import get_table, refresh_snapshot
from devplacepy.services.opinionwar import rules
from tests.api.battles._helpers import (
JSON,
_create_war_post,
_fight,
_fighter_row,
_join,
_session_battles,
_user_row,
_war_row,
)
from tests.conftest import BASE_URL
def _warp_cooldown(war_uid, user_uid):
fighter = _fighter_row(war_uid, user_uid)
warped = (datetime.now(timezone.utc) - timedelta(hours=25)).isoformat()
get_table("opinion_war_fighters").update(
{"uid": fighter["uid"], "last_fight_at": warped}, ["uid"]
)
def test_join_and_switch(app_server):
s, name = _session_battles()
_, war = _create_war_post(s, f"join-{int(time.time() * 1000)}")
r = _join(s, war["uid"], "a")
assert r.status_code == 200
payload = r.json()
assert payload["ok"] is True
assert payload["data"]["war"]["viewer"]["faction"] == "a"
fighter = _fighter_row(war["uid"], _user_row(name)["uid"])
assert fighter["faction"] == "a"
r = _join(s, war["uid"], "b")
assert r.json()["data"]["war"]["viewer"]["faction"] == "b"
fighter = _fighter_row(war["uid"], _user_row(name)["uid"])
assert fighter["faction"] == "b"
def test_join_invalid_faction_422(app_server):
s, _ = _session_battles()
_, war = _create_war_post(s, f"badfaction-{int(time.time() * 1000)}")
r = s.post(
f"{BASE_URL}/battles/{war['uid']}/join",
data={"faction": "c"},
headers=JSON,
)
assert r.status_code in (400, 422)
def test_join_requires_login(app_server):
s, _ = _session_battles()
_, war = _create_war_post(s, f"anon-{int(time.time() * 1000)}")
r = requests.post(
f"{BASE_URL}/battles/{war['uid']}/join",
data={"faction": "a"},
allow_redirects=False,
)
assert r.status_code in (303, 401)
def test_fight_spends_coins_and_deals_level_damage(app_server):
s, name = _session_battles()
_, war = _create_war_post(s, f"fight-{int(time.time() * 1000)}")
_join(s, war["uid"], "a")
r = _fight(s, war["uid"])
assert r.status_code == 200
payload = r.json()
user = _user_row(name)
expected = rules.damage_for(user.get("level"))
assert payload["data"]["damage"] == expected
assert payload["data"]["war"]["hp_a"] == expected
war_row = _war_row(war["uid"])
assert int(war_row["hp_a"]) == expected
refresh_snapshot()
farm = get_table("game_farms").find_one(user_uid=user["uid"])
from devplacepy.services.game import economy
assert int(farm["coins"]) == economy.STARTING_COINS - rules.FIGHT_COST_COINS
def test_fight_cooldown_refused(app_server):
s, _ = _session_battles()
_, war = _create_war_post(s, f"cooldown-{int(time.time() * 1000)}")
_join(s, war["uid"], "a")
assert _fight(s, war["uid"]).status_code == 200
r = _fight(s, war["uid"])
assert r.status_code == 400
assert "24 hours" in r.json()["error"]["message"]
def test_fight_after_warped_cooldown_lands(app_server):
s, name = _session_battles()
_, war = _create_war_post(s, f"warp-{int(time.time() * 1000)}")
_join(s, war["uid"], "b")
assert _fight(s, war["uid"]).status_code == 200
_warp_cooldown(war["uid"], _user_row(name)["uid"])
r = _fight(s, war["uid"])
assert r.status_code == 200
fighter = _fighter_row(war["uid"], _user_row(name)["uid"])
assert int(fighter["fight_count"]) == 2
def test_fight_without_coins_refused_and_cooldown_kept(app_server):
s, name = _session_battles()
_, war = _create_war_post(s, f"broke-{int(time.time() * 1000)}")
_join(s, war["uid"], "a")
assert _fight(s, war["uid"]).status_code == 200
user = _user_row(name)
_warp_cooldown(war["uid"], user["uid"])
refresh_snapshot()
farm = get_table("game_farms").find_one(user_uid=user["uid"])
get_table("game_farms").update({"uid": farm["uid"], "coins": 0}, ["uid"])
r = _fight(s, war["uid"])
assert r.status_code == 400
assert "coins" in r.json()["error"]["message"]
fighter = _fighter_row(war["uid"], user["uid"])
assert int(fighter["fight_count"]) == 1
r = _fight(s, war["uid"])
assert r.status_code == 400
def test_fight_before_join_refused(app_server):
s, _ = _session_battles()
other, _ = _session_battles()
_, war = _create_war_post(s, f"nojoin-{int(time.time() * 1000)}")
r = _fight(other, war["uid"])
assert r.status_code == 400
assert "Join" in r.json()["error"]["message"]
def test_switch_keeps_dealt_damage(app_server):
s, name = _session_battles()
_, war = _create_war_post(s, f"defect-{int(time.time() * 1000)}")
_join(s, war["uid"], "a")
assert _fight(s, war["uid"]).status_code == 200
r = _join(s, war["uid"], "b")
war_state = r.json()["data"]["war"]
user = _user_row(name)
expected = rules.damage_for(user.get("level"))
assert war_state["hp_a"] == expected
assert war_state["hp_b"] == 0
fighter = _fighter_row(war["uid"], user["uid"])
assert fighter["faction"] == "b"
assert int(fighter["hp_a"]) == expected
def test_actions_on_resolved_war_refused(app_server):
s, _ = _session_battles()
other, _ = _session_battles()
_, war = _create_war_post(s, f"over-{int(time.time() * 1000)}")
_join(s, war["uid"], "a")
past = (datetime.now(timezone.utc) - timedelta(minutes=1)).isoformat()
get_table("opinion_wars").update({"uid": war["uid"], "ends_at": past}, ["uid"])
r = _fight(s, war["uid"])
assert r.status_code == 400
r = _join(other, war["uid"], "b")
assert r.status_code == 400