Skip to content

Commit

Permalink
Feat:[공통] Pagination 마지막 페이지 체크 로직 보완 #85
Browse files Browse the repository at this point in the history
- is_last_page 적용
- 개별 PaginationResponse가 기본 PaginationResponse를 implements -> extends 하도록 변경
  • Loading branch information
juan-rybczinski committed Feb 15, 2024
1 parent ff7d0d2 commit 49665d4
Show file tree
Hide file tree
Showing 13 changed files with 62 additions and 126 deletions.
29 changes: 14 additions & 15 deletions lib/core/pagination/pagination_response.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ class PaginationResponse<T> {
required this.page,
required this.size,
required this.items,
required this.isLastPage,
});

PaginationResponse.fromJson(
Expand All @@ -13,27 +14,25 @@ class PaginationResponse<T> {
size = json['size'] as int,
items = (json['items'] as List<dynamic>)
.map((e) => fromJson.call(e))
.toList();
.toList(),
isLastPage = json['is_last_page'] as bool;

final int page;
final int size;
final List<T> items;
final bool isLastPage;

@override
bool operator ==(Object other) {
if (identical(this, other)) return true;

return other is PaginationResponse &&
other.items == items &&
other.page == page &&
other.size == size;
}
bool operator ==(Object other) =>
identical(this, other) ||
other is PaginationResponse &&
runtimeType == other.runtimeType &&
page == other.page &&
size == other.size &&
items == other.items &&
isLastPage == other.isLastPage;

@override
int get hashCode => items.hashCode ^ page.hashCode ^ size.hashCode;

Map<String, dynamic> toJson() => {
'page': page,
'size': size,
};
int get hashCode =>
page.hashCode ^ size.hashCode ^ items.hashCode ^ isLastPage.hashCode;
}
42 changes: 6 additions & 36 deletions lib/features/pet/domain/breeds_pagination_response.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,45 +2,15 @@ import 'package:pets_next_door_flutter/core/pagination/pagination_response.dart'
import 'package:pets_next_door_flutter/features/pet/domain/breed.dart';

/// Metadata used when fetching movies with the paginated search API.
class BreedsPaginationResponse implements PaginationResponse<Breed> {
class BreedsPaginationResponse extends PaginationResponse<Breed> {
BreedsPaginationResponse({
required this.page,
required this.size,
required this.items,
required super.page,
required super.size,
required super.items,
required super.isLastPage,
});

BreedsPaginationResponse.fromJson(
Map<String, dynamic> json,
) : page = json['page'] as int,
size = json['size'] as int,
items = (json['items'] as List<dynamic>)
.map((e) => Breed.fromJson(e))
.toList();

@override
final int page;

@override
final int size;

@override
final List<Breed> items;

@override
bool operator ==(Object other) {
if (identical(this, other)) return true;

return other is BreedsPaginationResponse &&
other.page == page &&
other.size == size;
}

@override
int get hashCode => page.hashCode ^ size.hashCode;

@override
Map<String, dynamic> toJson() {
// TODO: implement toJson
throw UnimplementedError();
}
) : super.fromJson(json, (e) => Breed.fromJson(e));
}
4 changes: 2 additions & 2 deletions lib/features/pet/repository/pet_repository.dart
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breed.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_request.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_response.dart';
import 'package:pets_next_door_flutter/features/pet/entities/pet_data_entity.dart';

abstract interface class PetRepository {
Future<Result<List<Breed>>> getBreeds({
Future<Result<BreedsPaginationResponse>> getBreeds({
required BreedsPaginationRequest breedsPaginationRequest,
});

Expand Down
6 changes: 3 additions & 3 deletions lib/features/pet/repository/pet_repository_impl.dart
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/pet/data/remote/pet_remote_data_source.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breed.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_request.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_response.dart';
import 'package:pets_next_door_flutter/features/pet/entities/pet_data_entity.dart';
import 'package:pets_next_door_flutter/features/pet/repository/pet_repository.dart';

Expand All @@ -13,12 +13,12 @@ final class PetRepositoryImpl implements PetRepository {
final PetRemoteDataSource _petRemoteDataSource;

@override
Future<Result<List<Breed>>> getBreeds(
Future<Result<BreedsPaginationResponse>> getBreeds(
{required BreedsPaginationRequest breedsPaginationRequest}) async {
try {
final breedsData = await _petRemoteDataSource.getBreeds(
breedsPaginationRequest: breedsPaginationRequest);
return Result.success(breedsData.items);
return Result.success(breedsData);
} on Exception catch (e) {
return Result.failure(e);
}
Expand Down
9 changes: 5 additions & 4 deletions lib/features/pet/usecases/get_breeds_use_case.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breed.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_request.dart';
import 'package:pets_next_door_flutter/features/pet/domain/breeds_pagination_response.dart';
import 'package:pets_next_door_flutter/features/pet/repository/pet_repository.dart';

final class GetBreedsUseCase {
Expand All @@ -10,9 +10,10 @@ final class GetBreedsUseCase {

final PetRepository _petRepository;

Future<Result<List<Breed>>> call({
Future<Result<BreedsPaginationResponse>> call({
required BreedsPaginationRequest breedsPaginationRequest,
}) async {
return _petRepository.getBreeds(breedsPaginationRequest: breedsPaginationRequest);
return _petRepository.getBreeds(
breedsPaginationRequest: breedsPaginationRequest);
}
}
}
41 changes: 6 additions & 35 deletions lib/features/sos/data/dto/sos_pagination_response_dto.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,44 +2,15 @@ import 'package:pets_next_door_flutter/core/pagination/pagination_response.dart'
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_post_dto.dart';

/// Metadata used when fetching movies with the paginated search API.
class SosPostPaginationResponseDto implements PaginationResponse<SosPostDto> {
class SosPostPaginationResponseDto extends PaginationResponse<SosPostDto> {
SosPostPaginationResponseDto({
required this.page,
required this.size,
required this.items,
required super.page,
required super.size,
required super.items,
required super.isLastPage,
});

SosPostPaginationResponseDto.fromJson(
Map<String, dynamic> json,
) : page = json['page'] as int,
size = json['size'] as int,
items = (json['items'] as List<dynamic>)
.map((e) => SosPostDto.fromJson(e))
.toList();

@override
final int page;

@override
final int size;

@override
final List<SosPostDto> items;

@override
bool operator ==(Object other) {
if (identical(this, other)) return true;

return other is SosPostPaginationResponseDto &&
other.page == page &&
other.size == size;
}

@override
int get hashCode => page.hashCode ^ size.hashCode;

@override
Map<String, dynamic> toJson() {
throw UnimplementedError();
}
) : super.fromJson(json, (e) => SosPostDto.fromJson(e));
}
4 changes: 2 additions & 2 deletions lib/features/sos/repositories/sos_post_repository.dart
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_request_dto.dart';
import 'package:pets_next_door_flutter/features/sos/entities/sos_post_entity.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_response_dto.dart';

abstract interface class SosPostRepository {
Future<Result<List<SosPostEntity>>> getSosPosts(
Future<Result<SosPostPaginationResponseDto>> getSosPosts(
SosPostPaginationRequestDto request);
}
10 changes: 3 additions & 7 deletions lib/features/sos/repositories/sos_post_repository_impl.dart
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_request_dto.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_response_dto.dart';
import 'package:pets_next_door_flutter/features/sos/data/remote/sos_post_remote_data_source.dart';
import 'package:pets_next_door_flutter/features/sos/entities/sos_post_entity.dart';
import 'package:pets_next_door_flutter/features/sos/repositories/sos_post_repository.dart';

final class SosPostRepositoryImpl implements SosPostRepository {
Expand All @@ -12,17 +12,13 @@ final class SosPostRepositoryImpl implements SosPostRepository {
final SosPostRemoteDataSource _sosPostRemoteDataSource;

@override
Future<Result<List<SosPostEntity>>> getSosPosts(
Future<Result<SosPostPaginationResponseDto>> getSosPosts(
SosPostPaginationRequestDto request) async {
try {
final sosPostResponse =
await _sosPostRemoteDataSource.getSosPosts(request);

return Result.success(
sosPostResponse.items
.map((postDto) => SosPostEntity.fromDto(postDto))
.toList(),
);
return Result.success(sosPostResponse);
} on Exception catch (e) {
return Result.failure(e);
}
Expand Down
4 changes: 2 additions & 2 deletions lib/features/sos/usecases/get_sos_post_use_case.dart
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import 'package:pets_next_door_flutter/core/enums/sort_type_filter.enum.dart';
import 'package:pets_next_door_flutter/core/utils/result.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_request_dto.dart';
import 'package:pets_next_door_flutter/features/sos/entities/sos_post_entity.dart';
import 'package:pets_next_door_flutter/features/sos/data/dto/sos_pagination_response_dto.dart';
import 'package:pets_next_door_flutter/features/sos/repositories/sos_post_repository.dart';

final class GetSosPostsUseCase {
Expand All @@ -11,7 +11,7 @@ final class GetSosPostsUseCase {

final SosPostRepository _sosPostRepository;

Future<Result<List<SosPostEntity>>> call({
Future<Result<SosPostPaginationResponseDto>> call({
required int size,
required int page,
required SortTypeFilter sortType,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import 'package:riverpod_annotation/riverpod_annotation.dart';

part 'breeds_paging_controller_provider.g.dart';

const breedsPagingSize = 20;
const pagingSize = 20;

@riverpod
class BreedsPagingController extends _$BreedsPagingController {
Expand All @@ -24,22 +24,20 @@ class BreedsPagingController extends _$BreedsPagingController {

Future<void> fetchPage(int pageKey) async {
try {
final newBreeds = await getBreedsUseCase.call(
final newPage = await getBreedsUseCase.call(
breedsPaginationRequest: new BreedsPaginationRequest(
page: pageKey,
size: breedsPagingSize,
size: pagingSize,
petType: ref.read(petStateProvider.notifier).state.petType!,
),
);

newBreeds.fold(
onSuccess: (breeds) {
final isLastPage = breeds.length < breedsPagingSize;

if (isLastPage) {
state.appendLastPage(breeds);
newPage.fold(
onSuccess: (page) {
if (page.isLastPage) {
state.appendLastPage(page.items);
} else {
state.appendPage(breeds, pageKey + 1);
state.appendPage(page.items, pageKey + 1);
}
},
onFailure: (e) => print('::: Fold Error ::: $e'),
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -23,20 +23,21 @@ class SosPagingController extends _$SosPagingController {

Future<void> fetchPage(int pageKey) async {
try {
final newPosts = await getSosPostUseCase.call(
final newPage = await getSosPostUseCase.call(
size: _pagingSize,
page: pageKey,
sortType: ref.read(sosPostFilterProvider).sortFilter,
);

newPosts.fold(
onSuccess: (breeds) {
final isLastPage = breeds.length < _pagingSize;

if (isLastPage) {
state.appendLastPage(breeds);
newPage.fold(
onSuccess: (page) {
final sosPostList = page.items
.map((sosPost) => SosPostEntity.fromDto(sosPost))
.toList();
if (page.isLastPage) {
state.appendLastPage(sosPostList);
} else {
state.appendPage(breeds, pageKey + 1);
state.appendPage(sosPostList, pageKey + 1);
}
},
onFailure: (e) => print('::: Fold Error ::: $e'),
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit 49665d4

Please sign in to comment.