성장기록지
onCreate에 PersistableBundle이 추가되면 화면이 그려지지 않는 이유 본문
개요
검색화면 activity를 분리하며 코드를 작성하다
activity가 화면에 그려지지 않고. 로그를 찍어봐도 아무것도 찍히지 않는 현상을 맞이했다.
이유를 찾아보니
override fun onCreate(savedInstanceState: Bundle?)
위의 코드를 사용하지 않고
override fun onCreate(savedInstanceState: Bundle?, persistentState: PersistableBundle?)
아래의 코드로 작성해서 벌어진 일이였다.
그렇다면 왜 화면에 그려지지 않는지, PersistableBundle이 뭔지 알아보고자 한다.
PersistableBundle이란?
공식문서에서는 다음과 같이 설명한다.
문자열 키에서 다양한 유형의 값으로의 매핑.
이 클래스에서 지원하는 유형 세트는 의도적으로 디스크에서 안전하게 유지되고 복원될 수 있는 간단한 개체로 제한.
일반적인 Bundle은 물리 메모리 에서 관리되다가, 애플리케이션 종료 또는 액티비티 종료 상황이 되면 GC에 의해 수거되거나 메모리 할당 해제 된다.
하지만 PersistableBundle 은 이름처럼 지속가능한 Bundle이다.
따라서 물리 메모리가 아니라, 디스크 에서 관리된다.
내부코드를 살펴보자
public final class PersistableBundle
extends BaseBundle
implements Cloneable,Parcelable, XmlUtils.WriteMapCallback {
...
@Nullable
public static byte[] toDiskStableBytes(@NonNull PersistableBundle bundle) throws IOException {
final ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
bundle.writeToStream(outputStream);
return outputStream.toByteArray();
}
public void writeToStream(@NonNull OutputStream outputStream) throws IOException {
TypedXmlSerializer serializer = Xml.newFastSerializer();
serializer.setOutput(outputStream, UTF_8.name());
serializer.startTag(null, "bundle");
try {
saveToXml(serializer);
} catch (XmlPullParserException e) {
throw new IOException(e);
}
serializer.endTag(null, "bundle");
serializer.flush();
}
public void saveToXml(XmlSerializer out) throws IOException, XmlPullParserException {
saveToXml(XmlUtils.makeTyped(out));
}
...
}
PersistableBundle의 핵심 메서드는 위 3가지이다.
toDiskStableBytes(PersistableBundle) 을 호출하면, PersistableBundle 을 OutputStream을 통해 Disk 에 쓰여진다는 사실을 알 수 있다.
이 때, writeToStream(OutputStream), saveToXml(XmlSerializer) 가 호출되는데, 이름에서 유추할 수 있는 것처럼 Xml 형태로 Disk에 읽기 쓰기된다.
따라서 앱 종료 후에도 영속적으로 저장해야 하는 간단한 데이터는 PersistableBundle를 통해 관리할 수 있다.
onCreate(Bundle, PersistableBundle) 호출 시기
그렇다면 언제 이 함수는 호출되는 걸까?
우선 해당 onCreate는 아래와같이 지속가능모드가 persistAcrossReboots일 경우 호출이 가능하다.
<activity
android:name=".MainActivity"
android:persistableMode="persistAcrossReboots"/>
하지만 일반적으로 Disk에 저장하기 위해서는 Database 또는 가벼운 데이터의 경우 SharedPreference나 DataStore에 자주 저장하기 때문에, PersistableBundle는 자주 쓰이지 않는다고 한다.
정리
기본적으로는 PersistableBundle이 호출되지 않고, 실제 개발 시에는 영속적 데이터 저장이 필요할 경우
DB, SharedPreferences, DataStore 사용을 권장하므로, onCreate 등의 메서드 사용 시 유의가 필요하다.
'개인 프로젝트' 카테고리의 다른 글
Room을 활용한 쇼핑 상품 북마크 기능 (기능 구현 과정) (0) | 2025.02.09 |
---|---|
Room을 활용한 쇼핑 상품 북마크 기능(Room 구조 구현) (0) | 2025.02.08 |
Jetpack Room의 TypeConverter 적용하기 (0) | 2025.02.05 |
Flow debounce와 프로젝트 적용(검색 기능 api 호출 최적화) (1) | 2025.02.01 |
Paging 학습 및 프로젝트 적용 (1) | 2025.01.28 |