728x90
Dart Completer (커스텀 비동기 처리)
Dart에서 Completer 는 Future를 수동으로 제어할 수 있는 객체입니다.
즉, 비동기 작업을 직접 완료하거나, 실패 처리할 때 사용됩니다.
1. Completer란?
- Future는 일반적으로 비동기 작업이 자동으로 완료되지만,
- Completer를 사용하면 개발자가 Future를 수동으로 완료(complete)하거나 오류 처리(completeError)할 수 있음.
- 비동기 작업의 흐름을 개발자가 직접 제어할 때 유용.
2. Completer 기본 사용법
2.1. Completer를 사용하여 비동기 데이터 반환
import 'dart:async';
Future<String> fetchData() {
Completer<String> completer = Completer();
Future.delayed(Duration(seconds: 2), () {
completer.complete("데이터 로드 완료!");
});
return completer.future;
}
void main() async {
print("로딩 중...");
String result = await fetchData();
print(result);
}
로딩 중...
(2초 후)
데이터 로드 완료!
- Completer를 사용하면 Future가 언제 완료될지 직접 제어 가능
2.2. Completer를 사용한 오류 처리 (completeError)
import 'dart:async';
Future<String> fetchDataWithError() {
Completer<String> completer = Completer();
Future.delayed(Duration(seconds: 2), () {
completer.completeError("데이터 가져오기 실패!"); // 오류 발생
});
return completer.future;
}
void main() async {
print("로딩 중...");
try {
String result = await fetchDataWithError();
print(result);
} catch (e) {
print("오류 발생: $e");
}
}
로딩 중...
(2초 후)
오류 발생: 데이터 가져오기 실패!
- completeError()를 사용하면 수동으로 Future의 오류를 발생시킬 수 있음
3. Completer의 활용 예제
3.1. Completer를 사용하여 HTTP 요청 처리
Dart의 http 패키지를 사용하여 비동기 네트워크 요청을 Completer로 처리할 수 있습니다.
import 'dart:async';
import 'package:http/http.dart' as http;
Future fetchDataFromApi() {
Completer completer = Completer();
http.get(Uri.parse("https://jsonplaceholder.typicode.com/todos/1")).then((response) {
if (response.statusCode == 200) {
completer.complete(response.body);
} else {
completer.completeError("API 요청 실패: ${response.statusCode}");
}
});
return completer.future;
}
void main() async {
print("API 요청 중...");
try {
String data = await fetchDataFromApi();
print("API 응답: $data");
} catch (e) {
print("오류 발생: $e");
}
}
- API 요청의 성공/실패 여부를 Completer를 사용해 수동으로 처리 가능
http 패키지 설치하기
1. pubspec.yaml 파일 수정dependencies: http: ^1.3.0 # 또는 최신 버전
최신 버전 확인을 원하면 다음 링크에서 확인하세요: https://pub.dev/packages/http
2. 테미널에서 패키지 설치
dart pub get
3.2. Completer를 사용하여 사용자 입력 대기
사용자의 입력을 비동기적으로 받아야 할 때 Completer를 활용하면 편리합니다.
import 'dart:async';
import 'dart:io';
Future<String> getUserInput() {
Completer<String> completer = Completer();
print("이름을 입력하세요:");
stdin.readLineSync(); // 동기 입력
Future.delayed(Duration(seconds: 1), () {
completer.complete("사용자 입력 완료!");
});
return completer.future;
}
void main() async {
print("입력 대기 중...");
String result = await getUserInput();
print(result);
}
- 사용자의 입력을 받는 동안 다른 작업을 수행할 수 있음
3.3. Completer를 사용한 비동기 타이머
비동기적으로 특정 시간이 지나면 완료되는 작업을 Completer로 만들 수 있습니다.
import 'dart:async';
Future<void> delayedTask(int seconds) {
Completer<void> completer = Completer();
Timer(Duration(seconds: seconds), () {
print("$seconds초 후 작업 완료!");
completer.complete();
});
return completer.future;
}
void main() async {
print("작업 시작...");
await delayedTask(3);
print("모든 작업 완료!");
}
작업 시작...
(3초 후)
3초 후 작업 완료!
모든 작업 완료!
- 특정 시간이 지나면 완료되는 Future를 생성할 수 있음
4. Completer와 StreamController 비교
기능 | Completer | StreamController |
데이터 처리 | 단일 값 (한 번만 완료) | 여러 개의 데이터 처리 가능 |
용도 | 비동기 작업 수동 완료 | 실시간 데이터 스트리밍 |
데이터 추가 방식 | complete() 사용 | sink.add() 사용 |
예제 | API 요청, 비동기 작업 | WebSocket, 실시간 데이터 |
- Completer는 단일 비동기 작업을 제어할 때 사용
- StreamController는 연속적인 데이터 스트리밍이 필요할 때 사용
Completer 요약
기능 | 설명 |
Completer 생성 | Completer<Type> completer = Completer(); |
Future 반환 | completer.future; |
complete() 사용 | completer.complete("완료됨"); |
completeError() 사용 | completer.completeError("오류 발생"); |
활용 예제 | API 요청, 사용자 입력 대기, 타이머 작업 |
728x90
'Flutter for Beginners' 카테고리의 다른 글
Dart 3.0의 향상된 switch 문 (0) | 2025.03.04 |
---|---|
Dart 3.0의 레코드 (Records) (0) | 2025.03.04 |
Dart의 Stream (비동기 데이터 스트림) (0) | 2025.03.04 |
Dart 비동기 프로그래밍 (0) | 2025.02.28 |
Dart 개발자 가이드 (코딩 스타일 & 협업 가이드) (0) | 2025.02.25 |