feat(#160): suppressions dashboard — poubelle, confirmations et sans_enfant.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -4,6 +4,7 @@ import 'package:p_tits_pas/models/user.dart';
|
||||
import 'package:p_tits_pas/models/pending_family.dart';
|
||||
import 'package:p_tits_pas/services/user_service.dart';
|
||||
import 'package:p_tits_pas/widgets/admin/dossier_list_card.dart';
|
||||
import 'package:p_tits_pas/widgets/admin/common/suppression_confirm_dialog.dart';
|
||||
import 'package:p_tits_pas/widgets/admin/validation_dossier_modal.dart';
|
||||
|
||||
/// Section « dossiers à valider » (liste unifiée AM + familles). Ticket #107 / #153.
|
||||
@@ -15,6 +16,8 @@ class PendingValidationWidget extends StatefulWidget {
|
||||
final bool compactWhenEmpty;
|
||||
/// Numéros des dossiers pending (pour exclure de « Tous les dossiers »).
|
||||
final ValueChanged<Set<String>>? onPendingNumerosChanged;
|
||||
/// Afficher la poubelle (#160) — mêmes règles que dossiers validés.
|
||||
final bool canDelete;
|
||||
|
||||
const PendingValidationWidget({
|
||||
super.key,
|
||||
@@ -22,6 +25,7 @@ class PendingValidationWidget extends StatefulWidget {
|
||||
this.searchQuery = '',
|
||||
this.compactWhenEmpty = false,
|
||||
this.onPendingNumerosChanged,
|
||||
this.canDelete = false,
|
||||
});
|
||||
|
||||
@override
|
||||
@@ -141,6 +145,97 @@ class _PendingValidationWidgetState extends State<PendingValidationWidget> {
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> _confirmDeletePending({
|
||||
required String numeroDossier,
|
||||
required String namesLine,
|
||||
required bool isFamille,
|
||||
}) async {
|
||||
final num = numeroDossier.trim();
|
||||
if (num.isEmpty) return;
|
||||
|
||||
var people = <SuppressionPersonLine>[];
|
||||
String? fallbackSummary;
|
||||
try {
|
||||
final dossier = await UserService.getDossier(num);
|
||||
if (dossier.isFamily) {
|
||||
final f = dossier.asFamily;
|
||||
people = suppressionPeopleFromDossier(
|
||||
isFamille: true,
|
||||
parents: f.parents
|
||||
.map((p) => (
|
||||
nom: p.nom ?? '',
|
||||
prenom: p.prenom ?? '',
|
||||
email: p.email,
|
||||
))
|
||||
.toList(),
|
||||
enfants: f.enfants
|
||||
.map((e) => (
|
||||
nom: e.lastName ?? '',
|
||||
prenom: e.firstName ?? '',
|
||||
))
|
||||
.toList(),
|
||||
);
|
||||
} else {
|
||||
final am = dossier.asAm.user;
|
||||
people = suppressionPeopleFromDossier(
|
||||
isFamille: false,
|
||||
parents: const [],
|
||||
enfants: const [],
|
||||
amName: formatDossierPersonLabel(
|
||||
nom: am.nom,
|
||||
prenom: am.prenom,
|
||||
email: am.email,
|
||||
),
|
||||
);
|
||||
}
|
||||
} catch (_) {
|
||||
fallbackSummary = isFamille
|
||||
? 'Tous les parents et enfants rattachés seront supprimés.'
|
||||
: 'Le compte AM sera supprimé ; les enfants accueillis '
|
||||
'seront conservés.';
|
||||
for (final part in namesLine.split(' - ')) {
|
||||
final label = part.trim();
|
||||
if (label.isEmpty) continue;
|
||||
people.add(SuppressionPersonLine(
|
||||
label: label,
|
||||
icon: isFamille
|
||||
? Icons.supervisor_account_outlined
|
||||
: Icons.face,
|
||||
role: isFamille ? 'Parent' : 'AM',
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
if (!mounted) return;
|
||||
final confirmed = await showDossierSuppressionConfirmDialog(
|
||||
context,
|
||||
numeroDossier: num,
|
||||
isFamille: isFamille,
|
||||
people: people,
|
||||
fallbackSummary: fallbackSummary,
|
||||
);
|
||||
if (!confirmed || !mounted) return;
|
||||
try {
|
||||
final result = await UserService.deleteDossier(num);
|
||||
if (!mounted) return;
|
||||
final msg = (result['message'] ?? 'Dossier supprimé.').toString();
|
||||
ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(msg)));
|
||||
await _load();
|
||||
widget.onRefresh?.call();
|
||||
} catch (e) {
|
||||
if (!mounted) return;
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
e is Exception
|
||||
? e.toString().replaceFirst('Exception: ', '')
|
||||
: 'Erreur suppression',
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
bool _matchesQuery(String haystack) {
|
||||
final q = widget.searchQuery.trim().toLowerCase();
|
||||
if (q.isEmpty) return true;
|
||||
@@ -286,12 +381,21 @@ class _PendingValidationWidgetState extends State<PendingValidationWidget> {
|
||||
}
|
||||
|
||||
Widget _buildAMCard(AppUser user) {
|
||||
final names = _amNamesLine(user);
|
||||
final num = user.numeroDossier ?? '';
|
||||
return DossierListCard(
|
||||
numeroDossier: user.numeroDossier ?? '',
|
||||
namesLine: _amNamesLine(user),
|
||||
numeroDossier: num,
|
||||
namesLine: names,
|
||||
isFamille: false,
|
||||
photoUrl: user.photoUrl,
|
||||
onOpen: () => _onOpenValidation(numeroDossier: user.numeroDossier),
|
||||
onDelete: widget.canDelete
|
||||
? () => _confirmDeletePending(
|
||||
numeroDossier: num,
|
||||
namesLine: names,
|
||||
isFamille: false,
|
||||
)
|
||||
: null,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -306,6 +410,13 @@ class _PendingValidationWidgetState extends State<PendingValidationWidget> {
|
||||
namesLine: names,
|
||||
isFamille: true,
|
||||
onOpen: () => _onOpenValidation(numeroDossier: family.numeroDossier),
|
||||
onDelete: widget.canDelete
|
||||
? () => _confirmDeletePending(
|
||||
numeroDossier: num,
|
||||
namesLine: names,
|
||||
isFamille: true,
|
||||
)
|
||||
: null,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user