Refactoring

This commit is contained in:
DahoudG
2025-09-17 17:54:06 +00:00
parent 12d514d866
commit 63fe107f98
165 changed files with 54220 additions and 276 deletions

View File

@@ -0,0 +1,443 @@
import 'dart:convert';
import 'package:flutter_test/flutter_test.dart';
import 'package:http/http.dart' as http;
import 'package:mockito/annotations.dart';
import 'package:mockito/mockito.dart';
import 'package:unionflow_mobile_apps/core/error/exceptions.dart';
import 'package:unionflow_mobile_apps/core/network/api_client.dart';
import 'package:unionflow_mobile_apps/features/solidarite/data/datasources/solidarite_remote_data_source.dart';
import 'package:unionflow_mobile_apps/features/solidarite/data/models/demande_aide_model.dart';
import '../../../../fixtures/fixture_reader.dart';
import 'solidarite_remote_data_source_test.mocks.dart';
@GenerateMocks([ApiClient])
void main() {
group('SolidariteRemoteDataSource', () {
late SolidariteRemoteDataSourceImpl dataSource;
late MockApiClient mockApiClient;
setUp(() {
mockApiClient = MockApiClient();
dataSource = SolidariteRemoteDataSourceImpl(apiClient: mockApiClient);
});
group('creerDemandeAide', () {
final tDemandeModel = DemandeAideModel.fromJson(
json.decode(fixture('demande_aide.json')),
);
test('doit effectuer un POST vers /api/solidarite/demandes avec les bonnes données', () async {
// arrange
when(mockApiClient.post(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response(fixture('demande_aide.json'), 201));
// act
final result = await dataSource.creerDemandeAide(tDemandeModel);
// assert
verify(mockApiClient.post(
'/api/solidarite/demandes',
data: tDemandeModel.toJson(),
));
expect(result, equals(tDemandeModel));
});
test('doit lancer ServerException quand le code de réponse n\'est pas 201', () async {
// arrange
when(mockApiClient.post(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response('Erreur serveur', 500));
// act & assert
expect(
() => dataSource.creerDemandeAide(tDemandeModel),
throwsA(isA<ServerException>()),
);
});
test('doit lancer ValidationException quand le code de réponse est 400', () async {
// arrange
when(mockApiClient.post(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response('Données invalides', 400));
// act & assert
expect(
() => dataSource.creerDemandeAide(tDemandeModel),
throwsA(isA<ValidationException>()),
);
});
test('doit lancer NetworkException en cas d\'erreur réseau', () async {
// arrange
when(mockApiClient.post(any, data: anyNamed('data')))
.thenThrow(const NetworkException('Pas de connexion'));
// act & assert
expect(
() => dataSource.creerDemandeAide(tDemandeModel),
throwsA(isA<NetworkException>()),
);
});
});
group('obtenirDemandeAide', () {
const tId = 'demande-123';
final tDemandeModel = DemandeAideModel.fromJson(
json.decode(fixture('demande_aide.json')),
);
test('doit effectuer un GET vers /api/solidarite/demandes/{id}', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response(fixture('demande_aide.json'), 200));
// act
final result = await dataSource.obtenirDemandeAide(tId);
// assert
verify(mockApiClient.get('/api/solidarite/demandes/$tId'));
expect(result, equals(tDemandeModel));
});
test('doit lancer NotFoundException quand le code de réponse est 404', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('Non trouvé', 404));
// act & assert
expect(
() => dataSource.obtenirDemandeAide(tId),
throwsA(isA<NotFoundException>()),
);
});
test('doit lancer ServerException quand le code de réponse n\'est pas 200', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('Erreur serveur', 500));
// act & assert
expect(
() => dataSource.obtenirDemandeAide(tId),
throwsA(isA<ServerException>()),
);
});
});
group('rechercherDemandesAide', () {
final tDemandesJson = json.decode(fixture('demandes_aide_list.json'));
final tDemandesModels = (tDemandesJson['content'] as List)
.map((json) => DemandeAideModel.fromJson(json))
.toList();
test('doit effectuer un GET vers /api/solidarite/demandes avec les paramètres de recherche', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response(fixture('demandes_aide_list.json'), 200));
// act
final result = await dataSource.rechercherDemandesAide(
organisationId: 'org-1',
typeAide: 'AIDE_FINANCIERE_MEDICALE',
statut: 'EN_ATTENTE',
demandeurId: 'user-1',
urgente: true,
page: 0,
taille: 20,
);
// assert
verify(mockApiClient.get(
'/api/solidarite/demandes?organisationId=org-1&typeAide=AIDE_FINANCIERE_MEDICALE&statut=EN_ATTENTE&demandeurId=user-1&urgente=true&page=0&size=20',
));
expect(result, equals(tDemandesModels));
});
test('doit construire l\'URL correctement avec des paramètres null', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response(fixture('demandes_aide_list.json'), 200));
// act
await dataSource.rechercherDemandesAide(
organisationId: null,
typeAide: null,
statut: null,
demandeurId: null,
urgente: null,
page: 0,
taille: 20,
);
// assert
verify(mockApiClient.get('/api/solidarite/demandes?page=0&size=20'));
});
test('doit retourner une liste vide quand aucune demande n\'est trouvée', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('{"content": [], "totalElements": 0}', 200));
// act
final result = await dataSource.rechercherDemandesAide(
page: 0,
taille: 20,
);
// assert
expect(result, isEmpty);
});
test('doit lancer ServerException quand le code de réponse n\'est pas 200', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('Erreur serveur', 500));
// act & assert
expect(
() => dataSource.rechercherDemandesAide(page: 0, taille: 20),
throwsA(isA<ServerException>()),
);
});
});
group('mettreAJourDemandeAide', () {
final tDemandeModel = DemandeAideModel.fromJson(
json.decode(fixture('demande_aide.json')),
);
test('doit effectuer un PUT vers /api/solidarite/demandes/{id}', () async {
// arrange
when(mockApiClient.put(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response(fixture('demande_aide.json'), 200));
// act
final result = await dataSource.mettreAJourDemandeAide(tDemandeModel);
// assert
verify(mockApiClient.put(
'/api/solidarite/demandes/${tDemandeModel.id}',
data: tDemandeModel.toJson(),
));
expect(result, equals(tDemandeModel));
});
test('doit lancer NotFoundException quand le code de réponse est 404', () async {
// arrange
when(mockApiClient.put(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response('Non trouvé', 404));
// act & assert
expect(
() => dataSource.mettreAJourDemandeAide(tDemandeModel),
throwsA(isA<NotFoundException>()),
);
});
test('doit lancer ValidationException quand le code de réponse est 400', () async {
// arrange
when(mockApiClient.put(any, data: anyNamed('data')))
.thenAnswer((_) async => http.Response('Données invalides', 400));
// act & assert
expect(
() => dataSource.mettreAJourDemandeAide(tDemandeModel),
throwsA(isA<ValidationException>()),
);
});
});
group('supprimerDemandeAide', () {
const tId = 'demande-123';
test('doit effectuer un DELETE vers /api/solidarite/demandes/{id}', () async {
// arrange
when(mockApiClient.delete(any))
.thenAnswer((_) async => http.Response('', 204));
// act
await dataSource.supprimerDemandeAide(tId);
// assert
verify(mockApiClient.delete('/api/solidarite/demandes/$tId'));
});
test('doit lancer NotFoundException quand le code de réponse est 404', () async {
// arrange
when(mockApiClient.delete(any))
.thenAnswer((_) async => http.Response('Non trouvé', 404));
// act & assert
expect(
() => dataSource.supprimerDemandeAide(tId),
throwsA(isA<NotFoundException>()),
);
});
test('doit lancer ServerException quand le code de réponse n\'est pas 204', () async {
// arrange
when(mockApiClient.delete(any))
.thenAnswer((_) async => http.Response('Erreur serveur', 500));
// act & assert
expect(
() => dataSource.supprimerDemandeAide(tId),
throwsA(isA<ServerException>()),
);
});
});
group('soumettreDemandeAide', () {
const tId = 'demande-123';
final tDemandeModel = DemandeAideModel.fromJson(
json.decode(fixture('demande_aide.json')),
);
test('doit effectuer un POST vers /api/solidarite/demandes/{id}/soumettre', () async {
// arrange
when(mockApiClient.post(any))
.thenAnswer((_) async => http.Response(fixture('demande_aide.json'), 200));
// act
final result = await dataSource.soumettreDemandeAide(tId);
// assert
verify(mockApiClient.post('/api/solidarite/demandes/$tId/soumettre'));
expect(result, equals(tDemandeModel));
});
test('doit lancer NotFoundException quand le code de réponse est 404', () async {
// arrange
when(mockApiClient.post(any))
.thenAnswer((_) async => http.Response('Non trouvé', 404));
// act & assert
expect(
() => dataSource.soumettreDemandeAide(tId),
throwsA(isA<NotFoundException>()),
);
});
test('doit lancer ValidationException quand la demande ne peut pas être soumise', () async {
// arrange
when(mockApiClient.post(any))
.thenAnswer((_) async => http.Response('Demande incomplète', 400));
// act & assert
expect(
() => dataSource.soumettreDemandeAide(tId),
throwsA(isA<ValidationException>()),
);
});
});
group('obtenirDemandesUrgentes', () {
final tDemandesJson = json.decode(fixture('demandes_aide_urgentes.json'));
final tDemandesModels = (tDemandesJson as List)
.map((json) => DemandeAideModel.fromJson(json))
.toList();
test('doit effectuer un GET vers /api/solidarite/demandes/urgentes', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response(fixture('demandes_aide_urgentes.json'), 200));
// act
final result = await dataSource.obtenirDemandesUrgentes('org-1');
// assert
verify(mockApiClient.get('/api/solidarite/demandes/urgentes?organisationId=org-1'));
expect(result, equals(tDemandesModels));
});
test('doit retourner une liste vide quand aucune demande urgente n\'est trouvée', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('[]', 200));
// act
final result = await dataSource.obtenirDemandesUrgentes('org-1');
// assert
expect(result, isEmpty);
});
});
group('obtenirMesDemandes', () {
final tDemandesJson = json.decode(fixture('mes_demandes.json'));
final tDemandesModels = (tDemandesJson['content'] as List)
.map((json) => DemandeAideModel.fromJson(json))
.toList();
test('doit effectuer un GET vers /api/solidarite/demandes/mes-demandes', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response(fixture('mes_demandes.json'), 200));
// act
final result = await dataSource.obtenirMesDemandes(
demandeurId: 'user-1',
page: 0,
taille: 20,
);
// assert
verify(mockApiClient.get('/api/solidarite/demandes/mes-demandes?demandeurId=user-1&page=0&size=20'));
expect(result, equals(tDemandesModels));
});
});
group('gestion des erreurs réseau', () {
test('doit lancer NetworkException en cas de timeout', () async {
// arrange
when(mockApiClient.get(any))
.thenThrow(const NetworkException('Timeout'));
// act & assert
expect(
() => dataSource.obtenirDemandeAide('demande-123'),
throwsA(isA<NetworkException>()),
);
});
test('doit lancer NetworkException en cas d\'erreur de connexion', () async {
// arrange
when(mockApiClient.get(any))
.thenThrow(const NetworkException('Connexion refusée'));
// act & assert
expect(
() => dataSource.obtenirDemandeAide('demande-123'),
throwsA(isA<NetworkException>()),
);
});
});
group('gestion des réponses malformées', () {
test('doit lancer ServerException en cas de JSON invalide', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('JSON invalide', 200));
// act & assert
expect(
() => dataSource.obtenirDemandeAide('demande-123'),
throwsA(isA<ServerException>()),
);
});
test('doit lancer ServerException en cas de structure JSON inattendue', () async {
// arrange
when(mockApiClient.get(any))
.thenAnswer((_) async => http.Response('{"unexpected": "structure"}', 200));
// act & assert
expect(
() => dataSource.obtenirDemandeAide('demande-123'),
throwsA(isA<ServerException>()),
);
});
});
});
}