Импорт (/imports, /instruments/pending) и фаза 4 (/goals, /income, /rebalance, /tax, аналитика-хаб с benchmarks_card) — по docs/ai/import-contract.md и docs/ai/phase4-contract.md. file_picker для загрузки отчёта.
51 lines
1.6 KiB
Dart
51 lines
1.6 KiB
Dart
import 'package:flutter/material.dart';
|
|
|
|
/// Russian labels for the stable string keys the import contract sends.
|
|
const brokerLabels = {
|
|
'sber': 'Сбер',
|
|
'vtb': 'ВТБ',
|
|
'tinvest': 'Т-Инвестиции',
|
|
'csv': 'CSV',
|
|
};
|
|
|
|
String brokerLabel(String? broker) => brokerLabels[broker] ?? broker ?? '—';
|
|
|
|
const parseStatusLabels = {
|
|
'uploaded': 'загружен',
|
|
'parsed': 'разобран',
|
|
'committed': 'импортирован',
|
|
'failed': 'ошибка',
|
|
};
|
|
|
|
String parseStatusLabel(String status) => parseStatusLabels[status] ?? status;
|
|
|
|
/// The colour of a `parse_status` chip: only `failed` is an error, and only `committed`
|
|
/// means the events are actually in the ledger.
|
|
Color parseStatusColor(BuildContext context, String status) {
|
|
final scheme = Theme.of(context).colorScheme;
|
|
return switch (status) {
|
|
'committed' => Colors.green,
|
|
'failed' => scheme.error,
|
|
'parsed' => scheme.primary,
|
|
_ => scheme.outline,
|
|
};
|
|
}
|
|
|
|
Widget parseStatusChip(BuildContext context, String status) {
|
|
final color = parseStatusColor(context, status);
|
|
return Chip(
|
|
visualDensity: VisualDensity.compact,
|
|
label: Text(parseStatusLabel(status)),
|
|
backgroundColor: color.withValues(alpha: 0.15),
|
|
labelStyle: TextStyle(color: color),
|
|
side: BorderSide(color: color.withValues(alpha: 0.4)),
|
|
);
|
|
}
|
|
|
|
String formatBytes(int? bytes) {
|
|
if (bytes == null) return '';
|
|
if (bytes < 1024) return '$bytes Б';
|
|
if (bytes < 1024 * 1024) return '${(bytes / 1024).round()} КБ';
|
|
return '${(bytes / (1024 * 1024)).toStringAsFixed(1).replaceAll('.', ',')} МБ';
|
|
}
|