feat(akte): Ablaufdatum in der Beladung-Tabelle
CI / backend-tests (push) Failing after 2m6s
CI / frontend-build (push) Successful in 18s

Bevorstehende Ablaufdaten waren nur im Dashboard und als
Einsatzbereitschafts-Grund sichtbar, nicht direkt an der jeweiligen
Beladungsposition in der Akte. Neue Spalte "Ablauf", rot bei
überfälligem, gelb bei <30 Tagen verbleibender Zeit.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01CVgbozhYmuEhiEJHffRXCV
This commit is contained in:
2026-09-06 23:48:31 +02:00
co-authored by Claude Sonnet 5
parent a18ec5bbce
commit cc016f09d3
5 changed files with 16 additions and 1 deletions
+2 -1
View File
@@ -1,5 +1,5 @@
import uuid
from datetime import datetime
from datetime import date, datetime
from decimal import Decimal
from pydantic import BaseModel, ConfigDict
@@ -27,6 +27,7 @@ class BeladungsPosition(BaseModel):
fach: str | None
sollmenge: Decimal
istmenge: Decimal
ablaufdatum: date | None
class AkteRead(BaseModel):
+1
View File
@@ -123,6 +123,7 @@ async def akte_fuer_objekt(db: AsyncSession, objekt_id: int) -> AkteRead | None:
if material.materialtyp == MaterialTyp.geraet_sn
else position.istmenge
),
ablaufdatum=position.ablaufdatum,
)
for position, material in beladung_result.all()
]
+1
View File
@@ -54,6 +54,7 @@ async def test_akte_buendelt_teilbereiche(client, db_session, objekt_mit_positio
assert body["beladung"][0]["material_id"] == _material.id
assert body["beladung"][0]["sollmenge"] == "10"
assert body["beladung"][0]["istmenge"] == "0"
assert body["beladung"][0]["ablaufdatum"] is None
@pytest.mark.asyncio
+1
View File
@@ -319,6 +319,7 @@ export interface BeladungsPosition {
fach: string | null;
sollmenge: string;
istmenge: string;
ablaufdatum: string | null;
}
export interface Akte {
+11
View File
@@ -10,6 +10,13 @@ import { ReadinessBadge } from "../components/status/ReadinessBadge";
import { GRUND_TEXT } from "../components/status/gruendeText";
import { EREIGNIS_LABEL } from "../components/status/ereignisText";
function ablaufFarbe(ablaufdatum: string): string | undefined {
const tage = (new Date(ablaufdatum).getTime() - Date.now()) / (1000 * 60 * 60 * 24);
if (tage < 0) return "var(--color-danger)";
if (tage < 30) return "var(--color-warning)";
return undefined;
}
const MANGEL_PRIORITAET_LABEL: Record<string, string> = {
niedrig: "Niedrig",
normal: "Normal",
@@ -120,6 +127,7 @@ export function AktePage() {
<th>Fach</th>
<th>Soll</th>
<th>Ist</th>
<th>Ablauf</th>
</tr>
</thead>
<tbody>
@@ -133,6 +141,9 @@ export function AktePage() {
<td className={Number(b.istmenge) < Number(b.sollmenge) ? "text-danger" : undefined}>
{b.istmenge} {b.einheit}
</td>
<td style={{ color: b.ablaufdatum ? ablaufFarbe(b.ablaufdatum) : undefined }}>
{b.ablaufdatum ? new Date(b.ablaufdatum).toLocaleDateString("de-DE") : ""}
</td>
</tr>
))}
</tbody>