Fix: Folgezähler-Button auch bei Single-Meter-Verträgen anzeigen

Bei Folgeverträgen / Bestandsverträgen ohne ContractMeter-Eintrag
war der "Folgezähler hinzufügen"-Button unsichtbar, weil er nur
im Multi-Meter-Zweig gerendert wurde.

Zusätzlich im addSuccessorMeter-Backend: bei Single-Meter-Verträgen
wird der bisherige energyDetails.meterId jetzt als ContractMeter
position 0 backfillt und als removed markiert, damit die Kette
lückenlos ist und der alte Zähler im Vertrag dokumentiert bleibt.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-05-30 14:03:01 +02:00
parent ad4c2bae1d
commit 34e106f253
2 changed files with 41 additions and 14 deletions
+26 -5
View File
@@ -551,19 +551,40 @@ export async function addSuccessorMeter(req: AuthRequest, res: Response): Promis
}
const ecdId = contract.energyDetails.id;
const existingMeters = contract.energyDetails.contractMeters;
const existingMeters = [...contract.energyDetails.contractMeters];
const switchAt = installedAt ? new Date(installedAt) : new Date();
// Backfill: Bei Single-Meter-Verträgen (kein ContractMeter-Eintrag) den
// bisherigen `energyDetails.meterId` als position 0 nachtragen, damit die
// Folgezähler-Kette lückenlos ist und der alte Zähler nicht aus dem
// Vertrag verschwindet, wenn `energyDetails.meterId` gleich auf den Neuen
// gedreht wird.
if (existingMeters.length === 0 && contract.energyDetails.meterId) {
const backfilled = await prisma.contractMeter.create({
data: {
energyContractDetailsId: ecdId,
meterId: contract.energyDetails.meterId,
position: 0,
installedAt: null,
},
});
existingMeters.push(backfilled);
}
const nextPosition = existingMeters.length > 0
? Math.max(...existingMeters.map(m => m.position)) + 1
: 0;
// Vorherigen Zähler als gewechselt markieren
if (existingMeters.length > 0 && finalReadingPrevious !== undefined) {
if (existingMeters.length > 0) {
const prevMeter = existingMeters[existingMeters.length - 1];
await prisma.contractMeter.update({
where: { id: prevMeter.id },
data: {
removedAt: installedAt ? new Date(installedAt) : new Date(),
finalReading: parseFloat(finalReadingPrevious),
removedAt: switchAt,
finalReading: finalReadingPrevious !== undefined
? parseFloat(finalReadingPrevious)
: prevMeter.finalReading,
},
});
}
@@ -573,7 +594,7 @@ export async function addSuccessorMeter(req: AuthRequest, res: Response): Promis
energyContractDetailsId: ecdId,
meterId: parseInt(meterId),
position: nextPosition,
installedAt: installedAt ? new Date(installedAt) : new Date(),
installedAt: switchAt,
},
include: { meter: { include: { readings: true } } },
});
@@ -2675,15 +2675,6 @@ export default function ContractDetail() {
/>
)
))}
{/* Folgezähler hinzufügen */}
{hasPermission('contracts:update') && !isCustomer && (
<SuccessorMeterButton
contractId={contractId}
customerId={c.customerId}
meterType={c.type as 'ELECTRICITY' | 'GAS'}
existingMeterIds={c.energyDetails.contractMeters.map((cm: ContractMeter) => cm.meterId)}
/>
)}
</>
) : c.energyDetails.meter ? (
<MeterReadingsSection
@@ -2695,6 +2686,21 @@ export default function ContractDetail() {
/>
) : null}
{/* Folgezähler hinzufügen auch bei Verträgen ohne ContractMeter-Eintrag
(z. B. Folgeverträge oder Bestandsverträge im Single-Meter-Modell). */}
{hasPermission('contracts:update') && !isCustomer && (c.energyDetails.meter || (c.energyDetails.contractMeters && c.energyDetails.contractMeters.length > 0)) && (
<SuccessorMeterButton
contractId={contractId}
customerId={c.customerId}
meterType={c.type as 'ELECTRICITY' | 'GAS'}
existingMeterIds={
c.energyDetails.contractMeters && c.energyDetails.contractMeters.length > 0
? c.energyDetails.contractMeters.map((cm: ContractMeter) => cm.meterId)
: c.energyDetails.meter ? [c.energyDetails.meter.id] : []
}
/>
)}
{/* Verbrauchsberechnung & Kostenvorschau */}
<EnergyConsumptionCalculation
contractType={c.type as 'ELECTRICITY' | 'GAS'}