mirror of
https://git.hiabuto.net/C3MA/CCMA.git
synced 2026-08-24 22:45:18 +02:00
Allow deleting claims, creating standalone payments, and add a donations tab
Claims could previously only be cancelled (stornieren), which blocks once a payment is allocated. Add a hard delete that releases any linked payments/credits back to being unallocated instead of destroying them. Payments could only be created from within a claim, forcing immediate allocation. Add a bare payment creation flow in the Zahlungen tab so incoming transfers can be logged first and allocated later. Add a per-member Spenden tab (donations, backed by a new donations list on ContributionData) so amounts paid beyond the membership fee can be tracked and existing free payments allocated to them. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
a61ea3cb57
commit
42fb4c4224
@@ -18,6 +18,13 @@ CLAIM_STATUS_LABELS = {
|
||||
"cancelled": "STORNIERT",
|
||||
}
|
||||
|
||||
DONATION_STATUS_LABELS = {
|
||||
"open": "OFFEN",
|
||||
"partially_allocated": "TEILWEISE ZUGEORDNET",
|
||||
"allocated": "ZUGEORDNET",
|
||||
"overallocated": "ÜBERZUGEORDNET",
|
||||
}
|
||||
|
||||
|
||||
def decimal_value(value: Any, field_name: str = "Betrag") -> Decimal:
|
||||
text = str(value).strip().replace(",", ".")
|
||||
@@ -109,6 +116,38 @@ def claim_balance(data: ContributionData, claim: dict[str, Any]) -> Decimal:
|
||||
return (claim_total(claim) - allocated_total(data, str(claim.get("claim_id", "")))).quantize(CENT)
|
||||
|
||||
|
||||
def donation_allocated_total(data: ContributionData, donation_id: str) -> Decimal:
|
||||
return sum(
|
||||
(
|
||||
decimal_value(allocation.get("amount", "0"))
|
||||
for allocation in data.allocations
|
||||
if str(allocation.get("donation_id", "")) == donation_id
|
||||
),
|
||||
Decimal("0"),
|
||||
)
|
||||
|
||||
|
||||
def donation_amount(donation: dict[str, Any]) -> Decimal:
|
||||
return decimal_value(donation.get("amount", "0"))
|
||||
|
||||
|
||||
def donation_balance(data: ContributionData, donation: dict[str, Any]) -> Decimal:
|
||||
donation_id = str(donation.get("donation_id", ""))
|
||||
return (donation_amount(donation) - donation_allocated_total(data, donation_id)).quantize(CENT)
|
||||
|
||||
|
||||
def donation_status(data: ContributionData, donation: dict[str, Any]) -> str:
|
||||
balance = donation_balance(data, donation)
|
||||
allocated = donation_allocated_total(data, str(donation.get("donation_id", "")))
|
||||
if balance < 0:
|
||||
return "overallocated"
|
||||
if balance == 0:
|
||||
return "allocated"
|
||||
if allocated > 0:
|
||||
return "partially_allocated"
|
||||
return "open"
|
||||
|
||||
|
||||
def claim_status(data: ContributionData, claim: dict[str, Any], *, today: date | None = None) -> str:
|
||||
if str(claim.get("status", "")) == "cancelled":
|
||||
return "cancelled"
|
||||
|
||||
@@ -323,6 +323,7 @@ class ContributionData:
|
||||
credits: list[dict[str, Any]] = field(default_factory=list)
|
||||
allocations: list[dict[str, Any]] = field(default_factory=list)
|
||||
reminders: list[dict[str, Any]] = field(default_factory=list)
|
||||
donations: list[dict[str, Any]] = field(default_factory=list)
|
||||
schema_version: int = 1
|
||||
|
||||
def to_dict(self) -> dict[str, Any]:
|
||||
@@ -333,6 +334,7 @@ class ContributionData:
|
||||
"credits": self.credits,
|
||||
"allocations": self.allocations,
|
||||
"reminders": self.reminders,
|
||||
"donations": self.donations,
|
||||
}
|
||||
|
||||
@classmethod
|
||||
@@ -344,6 +346,7 @@ class ContributionData:
|
||||
credits=list(data.get("credits") or []),
|
||||
allocations=list(data.get("allocations") or []),
|
||||
reminders=list(data.get("reminders") or []),
|
||||
donations=list(data.get("donations") or []),
|
||||
)
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user