--- id: android-lifecycle-aware-components title: Android Lifecycle-Aware Components category: Coding status: draft source_trust_level: B verification_status: conceptual created_at: 2026-05-09 updated_at: 2026-05-09 tags: [android, lifecycle, vibe-coding] tech_stack: { language: "Kotlin / Jetpack", applicable_to: ["Android"] } applied_in: [] aliases: [DefaultLifecycleObserver, lifecycleScope, repeatOnLifecycle] --- # Lifecycle-Aware Components > Activity / Fragment 의 lifecycle 상태에 자동 반응. 메모리 leak / 화면 회전 / 백그라운드 처리 사고의 90%를 막아줌. ## 📖 핵심 개념 - Lifecycle.State: INITIALIZED → CREATED → STARTED → RESUMED → DESTROYED. - 일반적으로 STARTED 이상에서만 UI 작업. - DefaultLifecycleObserver: lifecycle 메서드 override. ## 💻 코드 패턴 ### Observer 등록 ```kotlin class CameraController : DefaultLifecycleObserver { override fun onStart(owner: LifecycleOwner) { open() } override fun onStop(owner: LifecycleOwner) { close() } } // Fragment / Activity class CameraFragment : Fragment() { private val controller = CameraController() override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) viewLifecycleOwner.lifecycle.addObserver(controller) // viewLifecycleOwner — view 살아있는 동안 (Fragment 인스턴스보다 짧음) } } ``` ### repeatOnLifecycle — flow 수집 ```kotlin class ProfileFragment : Fragment() { override fun onViewCreated(...) { viewLifecycleOwner.lifecycleScope.launch { viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) { viewModel.user.collect { render(it) } } } } } ``` STARTED 이전 / STOP 이후 collect 안 함. 자동 cancel + restart. ### Compose 통합 ```kotlin @Composable fun ProfileScreen(viewModel: ProfileViewModel) { val user by viewModel.user.collectAsStateWithLifecycle() // STARTED 이상일 때만 collect } ``` ### Custom OnLifecycleEvent ```kotlin DisposableEffect(lifecycleOwner) { val observer = LifecycleEventObserver { _, event -> when (event) { Lifecycle.Event.ON_START -> startTracking() Lifecycle.Event.ON_STOP -> stopTracking() else -> {} } } lifecycleOwner.lifecycle.addObserver(observer) onDispose { lifecycleOwner.lifecycle.removeObserver(observer) } } ``` ## 🤔 의사결정 기준 | Owner | 사용처 | |---|---| | `viewLifecycleOwner` (Fragment) | view 가 살아있는 동안 (대부분) | | `lifecycle` (Activity/Fragment 자체) | 인스턴스 lifecycle (Fragment 인스턴스 > view) | | `LocalLifecycleOwner` (Compose) | composition 안에서 | | Service | LifecycleService 또는 manual | ## ❌ 안티패턴 - **Fragment 에서 `lifecycle` 대신 `viewLifecycleOwner` 안 씀**: view destroy 후에도 observer 동작 → leak. - **STARTED 가 아닌 CREATED 에서 UI 갱신**: view 가 아직 inflate 안 됨 → crash. - **lifecycleScope.launch 만, repeatOnLifecycle 없음**: 백그라운드에서도 collect → 메모리. - **observer 제거 안 함 (DisposableEffect 미사용)**: 의도적 추가만 하고 제거 누락. - **Compose 에서 collectAsState (lifecycle 무시)**: 백그라운드 수집. `collectAsStateWithLifecycle` 사용. ## 🤖 LLM 활용 힌트 - Fragment 코드는 viewLifecycleOwner 가 디폴트. - Compose 는 collectAsStateWithLifecycle + LocalLifecycleOwner. ## 🔗 관련 문서 - [[Android_Kotlin_Coroutines_Scopes]] - [[Android_Flow_StateFlow_SharedFlow]]