visualizzazione file dei servizi e copia nei file del cliente

This commit is contained in:
2026-04-20 12:58:06 +02:00
parent 78012fdbf3
commit 8dc1c661ed
15 changed files with 397 additions and 72 deletions

View File

@@ -3,10 +3,12 @@ import 'package:file_picker/file_picker.dart';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flux/core/blocs/session/session_bloc.dart';
import 'package:flux/core/utils/string_extensions.dart';
import 'package:flux/features/services/data/services_repository.dart';
import 'package:flux/features/services/models/energy_service_model.dart';
import 'package:flux/features/services/models/entertainment_service_model.dart';
import 'package:flux/features/services/models/fin_service_model.dart';
import 'package:flux/features/services/models/service_file_model.dart';
import 'package:flux/features/services/models/service_model.dart';
import 'package:get_it/get_it.dart';
import 'package:collection/collection.dart';
@@ -130,7 +132,7 @@ class ServicesCubit extends Cubit<ServicesState> {
companyId: _sessionBloc.state.company!.id,
),
status: ServicesStatus.ready,
localAttachments: [],
files: [],
),
);
}
@@ -210,7 +212,7 @@ class ServicesCubit extends Cubit<ServicesState> {
final serviceToSave = state.currentService!.copyWith(isBozza: isBozza);
// 2. Salvataggio corazzato
await _repository.saveFullService(serviceToSave, state.localAttachments);
await _repository.saveFullService(serviceToSave, state.files);
// 3. Reset e ricaricamento
emit(state.copyWith(status: ServicesStatus.saved, currentService: null));
@@ -228,14 +230,90 @@ class ServicesCubit extends Cubit<ServicesState> {
// --- GESTIONE ALLEGATI LOCALI ---
void addAttachments(List<PlatformFile> files) {
// Aggiungiamo i nuovi file a quelli già presenti in memoria
final updatedList = [...state.localAttachments, ...files];
emit(state.copyWith(localAttachments: updatedList));
// Trasformiamo i PlatformFile in ServiceFileModel "temporanei"
final newAttachments = files.map((file) {
return ServiceFileModel(
id: '', // ID vuoto perché non ancora su DB
serviceId: state.currentService?.id ?? '',
name: file.name.fileNameWithoutExtension(),
extension: file.name.fileExtension(),
url: '', // URL vuoto perché non ancora caricato
fileSize: file.size,
localBytes: file.bytes, // Fondamentale per l'upload!
createdAt: DateTime.now(),
);
}).toList();
// Uniamo i file esistenti (remoti + locali già aggiunti) con i nuovi
final updatedList = [
...(state.currentService?.files ?? []),
...newAttachments,
];
emit(
state.copyWith(
currentService: state.currentService?.copyWith(files: updatedList),
),
);
}
void removeLocalAttachment(int index) {
final updatedList = List<PlatformFile>.from(state.localAttachments);
void removeAttachment(int index) {
if (state.currentService == null) return;
final updatedList = List<ServiceFileModel>.from(
state.currentService!.files,
);
updatedList.removeAt(index);
emit(state.copyWith(localAttachments: updatedList));
emit(
state.copyWith(
currentService: state.currentService?.copyWith(files: updatedList),
),
);
}
void saveAndCopyFileToCustomer(ServiceFileModel file) async {
final currentService = state.currentService;
if (currentService == null || currentService.customerId == null) {
// Magari mostra un errore: non posso copiare al cliente se non c'è un cliente!
return;
}
emit(state.copyWith(status: ServicesStatus.loading));
try {
// 1. Salviamo la pratica (Bozza o definitiva che sia)
// Questo assicura che il file sia stato caricato su Storage e censito su DB
await saveCurrentService(isBozza: currentService.isBozza);
// 2. Recuperiamo il file "aggiornato"
// Dopo il saveCurrentService, il file che prima era "locale" ora ha un URL.
// Lo cerchiamo nella lista aggiornata per nome o estensione.
final savedFile = state.currentService!.files.firstWhere(
(f) => f.name == file.name && f.extension == file.extension,
orElse: () => file,
);
if (savedFile.url.isEmpty) {
throw Exception("Errore: URL del file non trovato dopo il salvataggio.");
}
// 3. Chiamiamo il repository per la copia fisica nel database del cliente
// Passiamo l'URL del file e l'ID del cliente
await _repository.copyFileToCustomer(
file: savedFile,
customerId: currentService.customerId!,
);
// 4. Feedback all'utente
// Potresti emettere un successo o mostrare un toast
emit(state.copyWith(status: ServicesStatus.success));
} catch (e) {
emit(state.copyWith(
status: ServicesStatus.failure,
errorMessage: "Errore durante la copia del file: $e",
));
}
}
}

View File

@@ -10,7 +10,7 @@ class ServicesState extends Equatable {
final String query;
final DateTimeRange? dateRange;
final bool hasReachedMax;
final List<PlatformFile> localAttachments;
final List<ServiceFileModel> files;
const ServicesState({
required this.status,
@@ -20,7 +20,7 @@ class ServicesState extends Equatable {
this.query = '',
this.dateRange,
this.hasReachedMax = false,
this.localAttachments = const [],
this.files = const [],
});
ServicesState copyWith({
@@ -31,7 +31,7 @@ class ServicesState extends Equatable {
String? query,
DateTimeRange? dateRange,
bool? hasReachedMax,
List<PlatformFile>? localAttachments,
List<ServiceFileModel>? files,
}) {
return ServicesState(
status: status ?? this.status,
@@ -41,7 +41,7 @@ class ServicesState extends Equatable {
query: query ?? this.query,
dateRange: dateRange ?? this.dateRange,
hasReachedMax: hasReachedMax ?? this.hasReachedMax,
localAttachments: localAttachments ?? this.localAttachments,
files: files ?? this.files,
);
}
@@ -54,6 +54,6 @@ class ServicesState extends Equatable {
query,
dateRange,
hasReachedMax,
localAttachments,
files,
];
}