|
# retoor <retoor@molodetz.nl>
|
|
|
|
from __future__ import annotations
|
|
|
|
import random
|
|
|
|
from .. import economy
|
|
from .common import GameError, _lvl, conditional_update_farm
|
|
from .farm import ensure_farm, get_farm
|
|
|
|
|
|
INFRA_COLUMN = {i.key: f"infra_{i.key}" for i in economy.INFRASTRUCTURE}
|
|
|
|
|
|
def buy_infrastructure(user: dict, key: str) -> dict:
|
|
infra = economy.infra_for(key)
|
|
if not infra:
|
|
raise GameError("Unknown infrastructure.")
|
|
farm = ensure_farm(user["uid"])
|
|
column = INFRA_COLUMN[infra.key]
|
|
rows = conditional_update_farm(
|
|
farm["uid"],
|
|
set_clause=f"coins = coins - :cost, {column} = 1",
|
|
where_clause=(
|
|
f"COALESCE({column}, 0) = 0 AND coins >= :cost "
|
|
f"AND COALESCE(prestige, 0) >= :min_prestige"
|
|
),
|
|
params={"cost": infra.cost, "min_prestige": infra.min_prestige},
|
|
)
|
|
if rows == 0:
|
|
farm = get_farm(user["uid"])
|
|
if _lvl(farm, column):
|
|
raise GameError("You already own that infrastructure.")
|
|
if _lvl(farm, "prestige") < infra.min_prestige:
|
|
raise GameError(f"{infra.name} requires prestige {infra.min_prestige}.")
|
|
raise GameError("Not enough coins for that infrastructure.")
|
|
return {"key": infra.key, "spent": infra.cost}
|
|
|
|
|
|
def owns_infrastructure(farm: dict, key: str) -> bool:
|
|
column = INFRA_COLUMN.get(key)
|
|
return bool(column and _lvl(farm, column))
|
|
|
|
|
|
def roll_canary(coins_gain: int, plant_cost: int) -> int:
|
|
roll = random.random()
|
|
if roll < economy.CANARY_DOUBLE_CHANCE:
|
|
return coins_gain * 2
|
|
if roll < economy.CANARY_DOUBLE_CHANCE + economy.CANARY_FAIL_CHANCE:
|
|
return min(coins_gain, plant_cost)
|
|
return coins_gain
|