Implemented Space details blocs, services, params, and models.

This commit is contained in:
Faris Armoush
2025-06-16 15:24:05 +03:00
parent b0aea94b91
commit aa141ef54d
7 changed files with 283 additions and 0 deletions

View File

@ -0,0 +1,27 @@
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/models/space_details_model.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/params/load_spaces_param.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/services/space_details_service.dart';
import 'package:syncrow_web/services/api/http_service.dart';
class RemoteSpaceDetailsService implements SpaceDetailsService {
final HTTPService _httpService;
RemoteSpaceDetailsService({
required HTTPService httpService,
}) : _httpService = httpService;
@override
Future<SpaceDetailsModel> getSpaceDetails(LoadSpacesParam param) async {
try {
final response = await _httpService.get(
path: 'endpoint',
expectedResponseModel: (data) {
return SpaceDetailsModel.fromJson(data as Map<String, dynamic>);
},
);
return response;
} catch (e) {
throw Exception('Failed to fetch space details: $e');
}
}
}

View File

@ -0,0 +1,166 @@
import 'package:equatable/equatable.dart';
class SpaceDetailsModel extends Equatable {
final String uuid;
final String spaceName;
final String icon;
final List<ProductAllocation> productAllocations;
final List<Subspace> subspaces;
const SpaceDetailsModel({
required this.uuid,
required this.spaceName,
required this.icon,
required this.productAllocations,
required this.subspaces,
});
factory SpaceDetailsModel.fromJson(Map<String, dynamic> json) {
return SpaceDetailsModel(
uuid: json['uuid'] as String,
spaceName: json['spaceName'] as String,
icon: json['icon'] as String,
productAllocations: (json['productAllocations'] as List)
.map((e) => ProductAllocation.fromJson(e as Map<String, dynamic>))
.toList(),
subspaces: (json['subspaces'] as List)
.map((e) => Subspace.fromJson(e as Map<String, dynamic>))
.toList(),
);
}
Map<String, dynamic> toJson() {
return {
'uuid': uuid,
'spaceName': spaceName,
'icon': icon,
'productAllocations': productAllocations.map((e) => e.toJson()).toList(),
'subspaces': subspaces.map((e) => e.toJson()).toList(),
};
}
@override
List<Object?> get props => [uuid, spaceName, icon, productAllocations, subspaces];
}
class ProductAllocation extends Equatable {
final Product product;
final Tag tag;
const ProductAllocation({
required this.product,
required this.tag,
});
factory ProductAllocation.fromJson(Map<String, dynamic> json) {
return ProductAllocation(
product: Product.fromJson(json['product'] as Map<String, dynamic>),
tag: Tag.fromJson(json['tag'] as Map<String, dynamic>),
);
}
Map<String, dynamic> toJson() {
return {
'product': product.toJson(),
'tag': tag.toJson(),
};
}
@override
List<Object?> get props => [product, tag];
}
class Product extends Equatable {
final String uuid;
final String name;
const Product({
required this.uuid,
required this.name,
});
factory Product.fromJson(Map<String, dynamic> json) {
return Product(
uuid: json['uuid'] as String,
name: json['name'] as String,
);
}
Map<String, dynamic> toJson() {
return {
'uuid': uuid,
'name': name,
};
}
@override
List<Object?> get props => [uuid, name];
}
class Tag extends Equatable {
final String uuid;
final String name;
final String createdAt;
final String updatedAt;
const Tag({
required this.uuid,
required this.name,
required this.createdAt,
required this.updatedAt,
});
factory Tag.fromJson(Map<String, dynamic> json) {
return Tag(
uuid: json['uuid'] as String,
name: json['name'] as String,
createdAt: json['createdAt'] as String,
updatedAt: json['updatedAt'] as String,
);
}
Map<String, dynamic> toJson() {
return {
'uuid': uuid,
'name': name,
'createdAt': createdAt,
'updatedAt': updatedAt,
};
}
@override
List<Object?> get props => [uuid, name, createdAt, updatedAt];
}
class Subspace extends Equatable {
final String uuid;
final String name;
final List<ProductAllocation> productAllocations;
const Subspace({
required this.uuid,
required this.name,
required this.productAllocations,
});
factory Subspace.fromJson(Map<String, dynamic> json) {
return Subspace(
uuid: json['uuid'] as String,
name: json['name'] as String,
productAllocations: (json['productAllocations'] as List)
.map((e) => ProductAllocation.fromJson(e as Map<String, dynamic>))
.toList(),
);
}
Map<String, dynamic> toJson() {
return {
'uuid': uuid,
'name': name,
'productAllocations': productAllocations.map((e) => e.toJson()).toList(),
};
}
@override
List<Object?> get props => [uuid, name, productAllocations];
}

View File

@ -0,0 +1,3 @@
class LoadSpacesParam {
const LoadSpacesParam();
}

View File

@ -0,0 +1,6 @@
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/models/space_details_model.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/params/load_spaces_param.dart';
abstract class SpaceDetailsService {
Future<SpaceDetailsModel> getSpaceDetails(LoadSpacesParam param);
}

View File

@ -0,0 +1,34 @@
import 'package:bloc/bloc.dart';
import 'package:equatable/equatable.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/models/space_details_model.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/params/load_spaces_param.dart';
import 'package:syncrow_web/pages/space_management_v2/modules/space_details/domain/services/space_details_service.dart';
import 'package:syncrow_web/services/api/api_exception.dart';
part 'space_details_event.dart';
part 'space_details_state.dart';
class SpaceDetailsBloc extends Bloc<SpaceDetailsEvent, SpaceDetailsState> {
final SpaceDetailsService _spaceDetailsService;
SpaceDetailsBloc(this._spaceDetailsService) : super(SpaceDetailsInitial()) {
on<LoadSpaceDetails>(_onLoadSpaceDetails);
}
Future<void> _onLoadSpaceDetails(
LoadSpaceDetails event,
Emitter<SpaceDetailsState> emit,
) async {
emit(SpaceDetailsLoading());
try {
final spaceDetails = await _spaceDetailsService.getSpaceDetails(
event.param,
);
emit(SpaceDetailsLoaded(spaceDetails));
} on APIException catch (e) {
emit(SpaceDetailsFailure(e.message));
} catch (e) {
emit(SpaceDetailsFailure(e.toString()));
}
}
}

View File

@ -0,0 +1,17 @@
part of 'space_details_bloc.dart';
sealed class SpaceDetailsEvent extends Equatable {
const SpaceDetailsEvent();
@override
List<Object> get props => [];
}
class LoadSpaceDetails extends SpaceDetailsEvent {
const LoadSpaceDetails(this.param);
final LoadSpacesParam param;
@override
List<Object> get props => [param];
}

View File

@ -0,0 +1,30 @@
part of 'space_details_bloc.dart';
sealed class SpaceDetailsState extends Equatable {
const SpaceDetailsState();
@override
List<Object> get props => [];
}
final class SpaceDetailsInitial extends SpaceDetailsState {}
final class SpaceDetailsLoading extends SpaceDetailsState {}
final class SpaceDetailsLoaded extends SpaceDetailsState {
final SpaceDetailsModel spaceDetails;
const SpaceDetailsLoaded(this.spaceDetails);
@override
List<Object> get props => [spaceDetails];
}
final class SpaceDetailsFailure extends SpaceDetailsState {
final String message;
const SpaceDetailsFailure(this.message);
@override
List<Object> get props => [message];
}