뚝딱뚝딱 모바일

[Flutter][Warning] Don't use 'BuildContext's across async gaps. 본문

Flutter 지식

[Flutter][Warning] Don't use 'BuildContext's across async gaps.

규석 2023. 12. 21. 18:34

안녕하세요!

오늘 글은 Error가 아닌 Warning이긴 하지만, 알아두시면 좋을 것 같아 적게 되었습니다.


어떤 상황에서 뜨나?

주로, 비동기적 상황에서 context를 사용하려할 때 뜹니다.

someFutureFunction().then((_) async {
  String example = await awaitFunction();
  context.read<SampleBloc>().add(SampleEvent()); // Bloc 코드
});

예시 코드입니다. 이렇게 async 함수 안에서 await 후에 context를 사용하는 코드가 존재한다면, 노란 밑줄이 코드 밑에 쳐지면서 Warning이 생겨납니다.

해결법

사실 해결법은 매우 쉽습니다. context를 사용하는 코드 부분을 mounted가 true일 때만, 실행해 주면 됩니다.

someFutureFunction().then((_) async {
  String example = await awaitFunction();
  if (mounted) {
    context.read<SampleBloc>().add(SampleEvent()); // Bloc 코드
  }
});

그럼 이 Warning은 왜 일어나는 거고, 왜 mounted가 true일 때는 안 뜨는 건지 알아보겠습니다.

먼저, mounted에 대해 알아보겠습니다.

mounted

 

mounted property - State class - widgets library - Dart API

 

api.flutter.dev

mounted는 State<T extends StatefulWidget> (이하 State)에 소속된 변수입니다. 코드를 살펴보면, 이렇게 되어있습니다.

bool get mounted => _element != null;

State 객체가 생성될 때, true가 되며, Dispose 후엔 false가 됩니다.

 

위의 Warning이 뜨는 이유를 이제 아시겠나요?

await를 통해 어떠한 작업이 완료될 때까지 기다리는 동안, 이 State 객체가 트리에서 사라질 수 있습니다. 

 

예를 들자면 A라는 화면이 있고 B라는 작업을 기다려야 하는데, B 작업이 끝나기도 전에 사용자가 A 화면에서 뒤로 가기를 할 수 있습니다. 물론, 이러한 상황이 일어나지 않게, B 작업이 진행되는 동안에는 State 객체가 Dispose 되는 경우를 막아주면 되겠지만, 컴파일러는 그 사실을 알 수 없습니다. 그렇기 때문에, mounted로 State객체가 살아있는지 확인 후 context 사용을 권장하려고 이 Warning이 뜨는 것입니다. 혹여나 날 수 있는 Error를 줄이기 위한 Warning인 거죠.

 

Warning이라서 무시하고 넘어가지 말고, 한번 짚어주고 가시면 좋을 것 같습니다.