67 lines
2.7 KiB
Dart
67 lines
2.7 KiB
Dart
import 'dart:convert';
|
|
import 'package:http/http.dart' as http;
|
|
import 'package:miler/Models/summary/pickupstats.dart';
|
|
import 'package:miler/data/api_config.dart';
|
|
import 'package:flutter/foundation.dart';
|
|
|
|
class SummaryProvider {
|
|
Future<PickupStats?> fetchSummaryStats(int userId) => _fetchSummaryStatsNew();
|
|
|
|
/// `GET /miler/earnings?period=daily|weekly|monthly`
|
|
///
|
|
/// → `data: { completed_stops, cancelled_stops, total_stops, total_kms,
|
|
/// total_earnings, total_bonus }`.
|
|
///
|
|
/// ── The success rate is read, not derived ──
|
|
///
|
|
/// `cancelled_stops` and `total_stops` did not exist, so the page computed a
|
|
/// success rate from `completed_stops` alone — which is a rate with no
|
|
/// denominator, and it read 100% on a day with three cancellations. Both
|
|
/// counts ship now and the figures come off the response.
|
|
///
|
|
/// The three period calls stay three calls: the endpoint answers for one
|
|
/// period at a time, and the page shows all three.
|
|
Future<PickupStats?> _fetchSummaryStatsNew() async {
|
|
Future<({int done, int cancelled, int total})> stops(String period) async {
|
|
try {
|
|
final uri = Uri.parse(
|
|
ApiConfig.url('/miler/earnings'),
|
|
).replace(queryParameters: {'period': period});
|
|
final res = await http.get(uri, headers: await ApiConfig.authHeaders());
|
|
if (res.statusCode >= 200 && res.statusCode < 300) {
|
|
final decoded = json.decode(res.body);
|
|
final d = (decoded is Map && decoded['data'] is Map)
|
|
? decoded['data'] as Map
|
|
: {};
|
|
int n(String key) => int.tryParse('${d[key] ?? 0}') ?? 0;
|
|
final done = n('completed_stops');
|
|
final cancelled = n('cancelled_stops');
|
|
// A server that has not shipped `total_stops` yet answers 0, and a
|
|
// total below the completed count is not a total — fall back to what
|
|
// is certainly true rather than printing a rate over nothing.
|
|
final reported = n('total_stops');
|
|
final total = reported >= done + cancelled
|
|
? reported
|
|
: done + cancelled;
|
|
return (done: done, cancelled: cancelled, total: total);
|
|
}
|
|
} catch (_) {}
|
|
return (done: 0, cancelled: 0, total: 0);
|
|
}
|
|
|
|
final today = await stops('daily');
|
|
final week = await stops('weekly');
|
|
final month = await stops('monthly');
|
|
return PickupStats(
|
|
today: today.done,
|
|
week: week.done,
|
|
month: month.done,
|
|
total: month.total,
|
|
// Was hardcoded to zero because nothing reported it. It is the month's
|
|
// figure, to match `total` — the two are one fraction and must come from
|
|
// one period or the rate is nonsense.
|
|
cancelled: month.cancelled,
|
|
);
|
|
}
|
|
}
|