from __future__ import annotations

from decimal import Decimal
from threading import Lock, Thread

class Budget:
    def __init__(self, limit):
        self.limit = Decimal(limit)
        self.reserved = Decimal("0")
        self.lock = Lock()

    def reserve(self, amount):
        amount = Decimal(amount)
        if amount <= 0:
            raise ValueError("amount must be positive")
        with self.lock:
            if self.reserved + amount > self.limit:
                return False
            self.reserved += amount
            return True

budget = Budget("20")
results = []
threads = [Thread(target=lambda: results.append(budget.reserve("15")))
           for _ in range(2)]
for thread in threads:
    thread.start()
for thread in threads:
    thread.join()
assert sorted(results) == [False, True]
assert budget.reserved == Decimal("15")
print("single-process reservation test passed")
