Files
votianlt/app/lib/models/job_progress.dart
T
Sven 5e6044e4b1 fix: Stationsabschluss absichern und Kundenformulare anpassen
Sperrt nachträgliche Aufgabenabschlüsse in App und Backend und zeigt erledigte Aufträge trotz offener optionaler Aufgaben grün an. Ergänzt Regressionstests, die Anredeauswahl und optionale Steuerangaben für Kunden. Enthält App-Version 0.9.25, Backend-Version 0.9.26 und das aktualisierte Frontend-Bundle.
2026-10-06 15:09:51 +02:00

53 lines
1.7 KiB
Dart

import 'job.dart';
import 'task.dart';
/// Combines server state with work confirmed locally while offline.
class JobProgress {
final Job job;
final Map<String, bool> taskStatuses;
final Set<int> completedStationOrders;
JobProgress(
this.job, {
this.taskStatuses = const {},
Set<int> localCompletedStations = const {},
}) : completedStationOrders = {
...job.completedStationOrders,
...localCompletedStations,
};
bool isTaskCompleted(Task task) =>
task.completed || taskStatuses[task.id] == true;
bool get isCancelled => job.status.toUpperCase() == 'CANCELLED';
bool get isCompleted {
if (isCancelled) return false;
if (const {'COMPLETED', 'DONE'}.contains(job.status.toUpperCase())) {
return true;
}
// Same rule as the backend: explicit final-station confirmation and all
// mandatory tasks completed. Open optional tasks do not prevent completion.
final lastStationOrder =
job.deliveryStations.isEmpty
? 0
: job.deliveryStations
.map((station) => station.stationOrder)
.reduce((a, b) => a > b ? a : b);
return completedStationOrders.contains(lastStationOrder) &&
job.tasks.where((task) => !task.optional).every(isTaskCompleted);
}
bool isStationClosed(int stationOrder) =>
isCancelled ||
isCompleted ||
completedStationOrders.contains(stationOrder);
bool canCompleteTask(Task task) =>
!isStationClosed(task.stationOrder ?? 0) && !isTaskCompleted(task);
int get completedTaskCount => job.tasks.where(isTaskCompleted).length;
bool get hasProgress =>
completedTaskCount > 0 || completedStationOrders.isNotEmpty;
}