Flutter의 비동기 작업에 대해 알아보겠습니다.
Flutter에서는 Future와 Stream을 이용해 비동기 프로그래밍을 구현할 수 있습니다. 비동기와 동기를 간략하게 구분해보자면 동기는 직렬적으로 작업들을 실행하는 것이고, 비동기는 병렬적/직렬적으로 작업들을 실행시키는 것입니다.
비동기 작업은 네트워크 통신을 할 때 많이 사용합니다. 특정 api를 호출해서 받아온 데이터를 이용해 또다른 api를 호출하는 로직이 많기 때문입니다.
아래 Note 클래스에서는 데이터를 호출하고, 호출이 완료되면 callback함수를 호출하는 3개의 함수가 있습니다. 주목할 것은 end print를 가장 마지막에 실행시켰는데 start 다음에 출력되고 있습니다. 이는 동기 방식으로 코드를 실행했기 때문입니다. 실행은 순차적으로 했지만 종료까지 순차적으로는 진행되지 않고 있습니다. 데이터 호출 함수들에서는 Future.delay를 사용해서 0.6초 씩 시간을 지연시키고 있습니다.
class Note {
start() {
print("start");
_getUserData(() {
print("_getUserData complete");
_getPetData(() {
print("_getPetData complete");
_getProductData(() {
print("_getProductData complete");
});
});
});
print("end");
}
_getUserData(Function callback) {
Future.delayed(const Duration(milliseconds: 600), () => callback());
}
_getPetData(Function callback) {
Future.delayed(const Duration(milliseconds: 600), () => callback());
}
_getProductData(Function callback) {
Future.delayed(const Duration(milliseconds: 600), () => callback());
}
}
--------------print----------------------
I/flutter (21956): start
I/flutter (21956): end
I/flutter (21956): _getUserData complete
I/flutter (21956): _getPetData complete
I/flutter (21956): _getProductData complete
dart에서는 Future 클래스를 사용해서 이러한 문제들을 해결할 수 있습니다.
아래 FutureNote 클래스에서 함수의 return 타입으로 Future를, 중괄호 앞에는 async를 붙인 것을 볼 수 있습니다. 이렇게 Future로 선언한 함수를 호출할 때 앞에 await까지 붙여주면 해당 함수가 종료되기 전까지 다름 코드를 실행하기 않고 기다립니다.
print를 확인해보면 코드를 실행한 순서대로 print가 출력된 것을 볼 수 있습니다. 앞선 Note 클래스에서 end가 start바로 다음에 출력된 것과 대조적입니다.
class FutureNote {
Future start() async {
print("start");
await _getUserData();
await _getPetData();
await _getProductData();
print("end");
}
Future _getUserData() async {
Future.delayed(const Duration(milliseconds: 600),
() => print("_getUserData complete"));
}
Future _getPetData() async {
Future.delayed(
const Duration(milliseconds: 600), () => print("_getPetData complete"));
}
Future _getProductData() async {
Future.delayed(const Duration(milliseconds: 600),
() => print("_getProductData complete"));
}
}
--------------print----------------------
I/flutter (21956): start
I/flutter (21956): _getUserData complete
I/flutter (21956): _getPetData complete
I/flutter (21956): _getProductData complete
I/flutter (21956): end